Files
backnotprop__plannotator/packages/editor/sourceDocumentClient.test.ts
Michael Ramos 195328f7a6 Persist saved annotate file edits in drafts (#936)
* Persist saved annotate file edits in drafts

* Handle stale saved file edit context

* Test source edit conflict actions

* Return source metadata for single-file docs

* Fix saved file edit conflict races

* Handle deleted source files in annotate edits

* Tighten annotate missing-file recovery

* Reset edit state for missing file reopen

* Tighten source edit restore path handling

* Harden source edit recovery paths

* Harden source edit disk reconciliation

* Fix live file tree startup delay

* Document file tree watcher startup ordering

* Preserve source save through missing files and symlinks

* Harden missing source file recovery

* Tighten annotate source edit boundaries
2026-06-18 21:31:25 -07:00

106 lines
3.0 KiB
TypeScript

import { afterEach, describe, expect, test } from 'bun:test';
import { fetchSourceDocumentSnapshot, probeSourceSave } from './sourceDocumentClient';
const originalFetch = globalThis.fetch;
function mockFetch(response: Response | Error) {
globalThis.fetch = (async () => {
if (response instanceof Error) throw response;
return response;
}) as typeof fetch;
}
afterEach(() => {
globalThis.fetch = originalFetch;
});
describe('source document client', () => {
test('probes source-save metadata from /api/doc', async () => {
mockFetch(Response.json({
sourceSave: {
enabled: true,
kind: 'local-text-file',
scope: 'folder-file',
path: '/repo/docs/a.md',
basename: 'a.md',
language: 'markdown',
hash: 'sha256:after',
mtimeMs: 1000,
size: 6,
eol: 'lf',
},
}));
expect(await probeSourceSave('/repo/docs/a.md')).toEqual({
status: 'ok',
sourceSave: {
enabled: true,
kind: 'local-text-file',
scope: 'folder-file',
path: '/repo/docs/a.md',
basename: 'a.md',
language: 'markdown',
hash: 'sha256:after',
mtimeMs: 1000,
size: 6,
eol: 'lf',
},
});
});
test('distinguishes missing and unavailable source probes', async () => {
mockFetch(new Response('missing', { status: 404 }));
expect(await probeSourceSave('/repo/docs/missing.md')).toEqual({ status: 'missing' });
mockFetch(new Error('network'));
expect(await probeSourceSave('/repo/docs/a.md')).toEqual({ status: 'unavailable' });
});
test('fetches markdown source snapshots and rejects html documents', async () => {
mockFetch(Response.json({
markdown: 'after\n',
sourceSave: {
enabled: true,
kind: 'local-text-file',
scope: 'folder-file',
path: '/repo/docs/a.md',
basename: 'a.md',
language: 'markdown',
hash: 'sha256:after',
mtimeMs: 1000,
size: 6,
eol: 'lf',
},
}));
expect(await fetchSourceDocumentSnapshot('/repo/docs/a.md')).toEqual({
status: 'ok',
snapshot: {
markdown: 'after\n',
sourceSave: {
enabled: true,
kind: 'local-text-file',
scope: 'folder-file',
path: '/repo/docs/a.md',
basename: 'a.md',
language: 'markdown',
hash: 'sha256:after',
mtimeMs: 1000,
size: 6,
eol: 'lf',
},
},
});
mockFetch(Response.json({ markdown: '<p>after</p>', renderAs: 'html' }));
expect(await fetchSourceDocumentSnapshot('/repo/docs/a.html')).toEqual({ status: 'unavailable' });
});
test('distinguishes missing and unavailable source snapshots', async () => {
mockFetch(new Response('missing', { status: 404 }));
expect(await fetchSourceDocumentSnapshot('/repo/docs/missing.md')).toEqual({ status: 'missing' });
mockFetch(new Error('network'));
expect(await fetchSourceDocumentSnapshot('/repo/docs/a.md')).toEqual({ status: 'unavailable' });
});
});