Skip to content

Extract autosave timer scheduling from App.vue#88

Merged
Renakoni merged 1 commit into
mainfrom
refactor/autosave-scheduling
Jul 10, 2026
Merged

Extract autosave timer scheduling from App.vue#88
Renakoni merged 1 commit into
mainfrom
refactor/autosave-scheduling

Conversation

@Renakoni

Copy link
Copy Markdown
Owner

Summary

Third PR of the semantic-decomposition series: moves the idle-autosave timer mechanics out of App.vue into a createAutosaveScheduler factory in features/document-session. Behavior-preserving; per the TODO constraint, the actual save workflows are not touched — they are injected as plain triggers.

Boundary

The scheduler owns:

  • per-target scheduling with debounced rescheduling (a new schedule replaces the pending timer, never stacks),
  • cancellation for each target,
  • the guard predicates (canRunIdleLocalDraftAutosave = autosave + local-drafts setting; canRunIdleAndroidDocumentAutosave = autosave), exported because editor-sync status text in App still consults them,
  • the mid-session settings resync previously inlined in the documentSettings watch: disabling local drafts clears the draft timer, disabling autosave clears both, and re-enabling autosave or changing the delay reschedules a dirty document for its current target while actively editing.

App destructures the same function names, so every existing call site (editor sync scheduling, the save entry points clearing their own timer, editor teardown, draft flows) is textually unchanged, and the settings watch body becomes a one-line delegation. State stays in App and is passed as refs; editing-activity is a getter.

One mechanical note: the module uses bare setTimeout/clearTimeout instead of the previous window.-prefixed forms — identical behavior in the WebView, and it lets the module run under fake timers in tests.

Testing

  • New autosaveScheduler.test.ts (8 tests, fake timers): exact-delay firing, debounced rescheduling, per-target guards, cancellation, disable-clears-both, delay-change rescheduling a dirty Android document, re-enable scheduling a dirty draft, and no-op when not actively editing.
  • Full unit suite 284/284, ESLint, vue-tsc, production build green.
  • Contract E2E 19/19: mobile-local-draft-lifecycle (editor-input autosave, the four lifecycle flush paths, back-button prompt), mobile-android-document-lifecycle (save-failure recovery, read-only flows), mobile-documents-settings (local-draft setting disabled).

Moves the idle-autosave timer mechanics for local drafts and Android
documents into a createAutosaveScheduler factory in
features/document-session: per-target scheduling with debounced
rescheduling, cancellation, the autosave/localDrafts guard predicates,
and the mid-session resync applied when document settings change
(disable clears pending timers; re-enable or a delay change reschedules
a dirty document for its current target).

The save workflows are untouched and injected as plain triggers, per the
TODO constraint. App destructures the same function names, so every
existing call site (editor sync, save entry points, editor teardown,
draft flows) is unchanged, and the settings watch body becomes a
one-line delegation. The only mechanical difference is bare
setTimeout/clearTimeout instead of the window-prefixed forms, which is
behavior-identical in the WebView and makes the module testable under
fake timers.
@Renakoni Renakoni merged commit 79adfbc into main Jul 10, 2026
5 checks passed
@Renakoni Renakoni deleted the refactor/autosave-scheduling branch July 10, 2026 11:27
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant