Commit Graph
1 Commits
Author SHA1 Message Date
John O'Keefe d584f17092 fix(sync): bail out of deferred sync tasks when the document is gone
Every push and pull runs deferred — updateProgress and getProgress hand
their work to UIManager:scheduleIn(0.5), and API replies are consumed in
UIManager:nextTick closures — so by the time the task runs, the ReaderUI
may have released its document (close/teardown race) or a slow async
load may not have attached it yet (the CRE full-render window: "cached
rendering is invalid" leaves the reader document-less for seconds on
big EPUBs). The task then dereferenced self.ui.document unguarded and
the unhandled error inside a UIManager task killed the whole app:

    main.lua:846: attempt to index field 'document' (a nil value)

    ...in function 'collectBookData'
    ...in function '_doUpdateProgress'
    ...in function 'action' (uimanager _checkTasks)

Observed as a hard crash on the auto-push (pages_before_update = 2)
right after opening an EPUB that needed a full re-render.

getBookhoardUUID and getContextText already nil-guarded their document
access; the task entry points never did. Guard them:

- _doUpdateProgress: bail before collectBookData — the single choke
  point for every push source (periodic, close, suspend, menu, the
  legacy bootstrap push), so one guard covers the whole class
- _doGetProgress: bail at entry, and re-validate first thing inside the
  nextTick closure (its body and applyServerAnnotations touch
  document.info long after the request was issued)
- getFileSHA256: return nil instead of indexing doc_settings/document
  (all callers already handle nil)

No sync-payload or endpoint changes; server behavior untouched.
2026-09-19 10:35:48 -04:00