not running debounced updates while network requests in flight

This commit is contained in:
2024-11-19 09:05:43 -07:00
parent 0ce31312ac
commit 5f6e7718bd
6 changed files with 40 additions and 10 deletions

View File

@@ -3,6 +3,8 @@ import { trpcAppRouter } from "@/services/serverFunctions/router/app";
import { fetchRequestHandler } from "@trpc/server/adapters/fetch"; import { fetchRequestHandler } from "@trpc/server/adapters/fetch";
const handler = async (request: Request) => { const handler = async (request: Request) => {
await new Promise(r => setTimeout(r, 1000)); // delay for testing
return fetchRequestHandler({ return fetchRequestHandler({
endpoint: "/api/trpc", endpoint: "/api/trpc",
req: request, req: request,

View File

@@ -31,7 +31,7 @@ export default function EditAssignment({
const router = useRouter(); const router = useRouter();
const { courseName } = useCourseContext(); const { courseName } = useCourseContext();
const [settings] = useLocalCourseSettingsQuery(); const [settings] = useLocalCourseSettingsQuery();
const [assignment, { dataUpdatedAt: serverDataUpdatedAt }] = const [assignment, { dataUpdatedAt: serverDataUpdatedAt, isFetching: assignmentIsFetching }] =
useAssignmentQuery(moduleName, assignmentName); useAssignmentQuery(moduleName, assignmentName);
const updateAssignment = useUpdateAssignmentMutation(); const updateAssignment = useUpdateAssignmentMutation();
@@ -55,6 +55,11 @@ export default function EditAssignment({
const handler = setTimeout(() => { const handler = setTimeout(() => {
try { try {
if (assignmentIsFetching || updateAssignment.isPending) {
console.log("network requests in progress, not updating assignments");
return;
}
const updatedAssignment: LocalAssignment = const updatedAssignment: LocalAssignment =
localAssignmentMarkdown.parseMarkdown(text); localAssignmentMarkdown.parseMarkdown(text);
if ( if (
@@ -62,7 +67,7 @@ export default function EditAssignment({
localAssignmentMarkdown.toMarkdown(updatedAssignment) localAssignmentMarkdown.toMarkdown(updatedAssignment)
) { ) {
if (clientIsAuthoritative) { if (clientIsAuthoritative) {
console.log("updating assignment"); console.log("updating assignment, client is authoritative");
updateAssignment updateAssignment
.mutateAsync({ .mutateAsync({
assignment: updatedAssignment, assignment: updatedAssignment,
@@ -109,6 +114,7 @@ export default function EditAssignment({
clientDataUpdatedAt, clientDataUpdatedAt,
clientIsAuthoritative, clientIsAuthoritative,
courseName, courseName,
assignmentIsFetching,
moduleName, moduleName,
router, router,
serverUpdatedAt, serverUpdatedAt,

View File

@@ -24,7 +24,7 @@ export default function EditPage({
}) { }) {
const router = useRouter(); const router = useRouter();
const { courseName } = useCourseContext(); const { courseName } = useCourseContext();
const [page, { dataUpdatedAt }] = usePageQuery( const [page, { dataUpdatedAt, isFetching }] = usePageQuery(
moduleName, moduleName,
pageName pageName
); );
@@ -42,6 +42,11 @@ export default function EditPage({
useEffect(() => { useEffect(() => {
const delay = 500; const delay = 500;
const handler = setTimeout(() => { const handler = setTimeout(() => {
if (isFetching || updatePage.isPending) {
console.log("network requests in progress, not updating page");
return;
}
try { try {
const updatedPage = localPageMarkdownUtils.parseMarkdown(text); const updatedPage = localPageMarkdownUtils.parseMarkdown(text);
if ( if (
@@ -89,6 +94,7 @@ export default function EditPage({
}, [ }, [
clientIsAuthoritative, clientIsAuthoritative,
courseName, courseName,
isFetching,
moduleName, moduleName,
page, page,
pageName, pageName,

View File

@@ -65,10 +65,8 @@ export default function EditQuiz({
}) { }) {
const router = useRouter(); const router = useRouter();
const { courseName } = useCourseContext(); const { courseName } = useCourseContext();
const [quiz, { dataUpdatedAt: serverDataUpdatedAt }] = useQuizQuery( const [quiz, { dataUpdatedAt: serverDataUpdatedAt, isFetching }] =
moduleName, useQuizQuery(moduleName, quizName);
quizName
);
const updateQuizMutation = useUpdateQuizMutation(); const updateQuizMutation = useUpdateQuizMutation();
const { clientIsAuthoritative, text, textUpdate, monacoKey } = const { clientIsAuthoritative, text, textUpdate, monacoKey } =
useAuthoritativeUpdates({ useAuthoritativeUpdates({
@@ -82,6 +80,10 @@ export default function EditQuiz({
useEffect(() => { useEffect(() => {
const delay = 1000; const delay = 1000;
const handler = setTimeout(async () => { const handler = setTimeout(async () => {
if (isFetching || updateQuizMutation.isPending) {
console.log("network requests in progress, not updating page");
return;
}
try { try {
if ( if (
quizMarkdownUtils.toMarkdown(quiz) !== quizMarkdownUtils.toMarkdown(quiz) !==
@@ -128,6 +130,7 @@ export default function EditQuiz({
}, [ }, [
clientIsAuthoritative, clientIsAuthoritative,
courseName, courseName,
isFetching,
moduleName, moduleName,
quiz, quiz,
quizName, quizName,

View File

@@ -12,8 +12,12 @@ export function useAuthoritativeUpdates({
const [clientDataUpdatedAt, setClientDataUpdatedAt] = const [clientDataUpdatedAt, setClientDataUpdatedAt] =
useState(serverUpdatedAt); useState(serverUpdatedAt);
const [updateMonacoKey, setUpdateMonacoKey] = useState(1); const [updateMonacoKey, setUpdateMonacoKey] = useState(1);
const clientIsAuthoritative = useMemo(() => {
const authority = serverUpdatedAt <= clientDataUpdatedAt + 500;
console.log("client is authoritative", authority);
return authority;
}, [clientDataUpdatedAt, serverUpdatedAt]); // if it is close, it might be the second-to-last update changing the first (by file update delays), add some buffer...
// console.log("client is authoritative", clientIsAuthoritative);
const textUpdate = useCallback((t: string, updateMonaco: boolean = false) => { const textUpdate = useCallback((t: string, updateMonaco: boolean = false) => {
setText(t); setText(t);
setClientDataUpdatedAt(Date.now()); setClientDataUpdatedAt(Date.now());
@@ -22,13 +26,20 @@ export function useAuthoritativeUpdates({
return useMemo( return useMemo(
() => ({ () => ({
clientIsAuthoritative: serverUpdatedAt <= clientDataUpdatedAt, clientIsAuthoritative,
serverUpdatedAt, serverUpdatedAt,
clientDataUpdatedAt, clientDataUpdatedAt,
textUpdate, textUpdate,
text, text,
monacoKey: updateMonacoKey, monacoKey: updateMonacoKey,
}), }),
[clientDataUpdatedAt, serverUpdatedAt, text, textUpdate, updateMonacoKey] [
clientDataUpdatedAt,
clientIsAuthoritative,
serverUpdatedAt,
text,
textUpdate,
updateMonacoKey,
]
); );
} }

View File

@@ -71,6 +71,8 @@ export const assignmentsFileStorageService = {
const assignmentMarkdown = const assignmentMarkdown =
assignmentMarkdownSerializer.toMarkdown(assignment); assignmentMarkdownSerializer.toMarkdown(assignment);
console.log(`Saving assignment ${filePath}`); console.log(`Saving assignment ${filePath}`);
await fs.writeFile(filePath, assignmentMarkdown); await fs.writeFile(filePath, assignmentMarkdown);
}, },
async delete({ async delete({