const { test } = require('node:test'); const assert = require('node:assert/strict'); const fs = require('node:fs'); const vm = require('node:vm'); const factory = vm.runInNewContext(fs.readFileSync('src/content/modal.js', 'utf8') + '\ncreateContentModal'); function setup(check) { const hint = { hidden: true }, modal = { hidden: false }, timers = new Map(); let next = 0; const app = factory({ MODAL_ID: 'modal', getShortcutBookmarkStatus: check, environment: { window: {}, document: { getElementById: id => id === 'modal' ? modal : hint }, setTimeout(fn, delay) { const id = ++next; timers.set(id, { fn, delay }); return id; }, clearTimeout(id) { timers.delete(id); } } }); return { app, hint, modal, timers }; } test('unbookmarked shortcut shows for 20 seconds and can show on reopening', async () => { const h = setup(async () => ({ ok: true, bookmarked: false })); await h.app.refreshBookmarkHint(); assert.equal(h.hint.hidden, false); const timer = [...h.timers.values()][0]; assert.equal(timer.delay, 20000); timer.fn(); assert.equal(h.hint.hidden, true); await h.app.refreshBookmarkHint(); assert.equal(h.hint.hidden, false); h.app.hideBookmarkHint(); assert.equal(h.timers.size, 0); }); test('existing bookmark and failed checks never display the hint', async () => { for (const check of [async () => ({ ok: true, bookmarked: true }), async () => ({ ok: false }), async () => { throw Error('unavailable'); }]) { const h = setup(check); await h.app.refreshBookmarkHint(); assert.equal(h.hint.hidden, true); assert.equal(h.timers.size, 0); } }); test('closing or saving while the check is pending prevents late hints', async () => { let resolve; const h = setup(() => new Promise(done => { resolve = done; })); const pending = h.app.refreshBookmarkHint(); h.app.hideBookmarkHint(); resolve({ ok: true, bookmarked: false }); await pending; assert.equal(h.hint.hidden, true); assert.equal(h.timers.size, 0); });