app/src/embed.test.ts intermittently fails CI with an unhandled rejection after the jsdom environment is torn down:
ReferenceError: localStorage is not defined
❯ migrateLegacyDevice src/lib/identity.ts:204:18
❯ loadStoredDevice src/lib/identity.ts:227:26
❯ loadIdentity src/lib/identity.ts:452:27
❯ src/App.tsx:350:30
This error originated in "src/embed.test.ts" test file ... caught after test environment was torn down.
Example failing run: https://github.com/sssubscript/write/actions/runs/37154350731 (first attempt failed; the rerun passed with no code change). main has also had intermittent CI failures.
Cause
The embed tests mount App, which starts async identity loading (loadIdentity → IndexedDB → localStorage) in an effect. The tests only await a single setTimeout(0) tick, so that work can still be running when Vitest tears down jsdom, and the next localStorage access throws.
Acceptance criteria
- The embed tests no longer leave identity loading running past teardown, for example by waiting for it to settle before unmounting or by stubbing
loadIdentity in these tests.
- Alternatively, or additionally, the identity loading effect in
App ignores or cancels work after unmount.
pnpm run test passes reliably with no unhandled rejections, repeated (e.g. 20 consecutive runs of embed.test.ts).
Addresses #2 and #4
app/src/embed.test.tsintermittently fails CI with an unhandled rejection after the jsdom environment is torn down:Example failing run: https://github.com/sssubscript/write/actions/runs/37154350731 (first attempt failed; the rerun passed with no code change).
mainhas also had intermittent CI failures.Cause
The embed tests mount
App, which starts async identity loading (loadIdentity→ IndexedDB →localStorage) in an effect. The tests onlyawaita singlesetTimeout(0)tick, so that work can still be running when Vitest tears down jsdom, and the nextlocalStorageaccess throws.Acceptance criteria
loadIdentityin these tests.Appignores or cancels work after unmount.pnpm run testpasses reliably with no unhandled rejections, repeated (e.g. 20 consecutive runs ofembed.test.ts).Addresses #2 and #4