F2 SLICE-1: artifact schema + CoauthorStore with round-trip tests (#4)

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
Ben Stull
2026-06-10 06:49:31 -07:00
parent 9c9d4928bd
commit 9d93ccca19
5 changed files with 271 additions and 0 deletions
+31
View File
@@ -0,0 +1,31 @@
/**
* CoauthorStore — load/save the per-document `.threads/` sidecar (spec §6.4).
* Git-native, serverless, plain pretty JSON (INV-2). vscode-free (Node fs only),
* so it is unit-testable; the FileSystemWatcher that triggers re-anchoring on
* external change is wired in the vscode layer (ThreadController, SLICE-4).
*/
import * as fs from "node:fs";
import * as path from "node:path";
import { serializeArtifact, type Artifact } from "./model";
export class CoauthorStore {
/** @param rootDir absolute workspace-folder root that owns the `.threads/` tree. */
constructor(private readonly rootDir: string) {}
/** `.threads/<repo-relative-docPath>.json` (spec §6.3). */
sidecarPath(docPath: string): string {
return path.join(this.rootDir, ".threads", `${docPath}.json`);
}
load(docPath: string): Artifact | null {
const p = this.sidecarPath(docPath);
if (!fs.existsSync(p)) return null;
return JSON.parse(fs.readFileSync(p, "utf8")) as Artifact;
}
save(docPath: string, artifact: Artifact): void {
const p = this.sidecarPath(docPath);
fs.mkdirSync(path.dirname(p), { recursive: true });
fs.writeFileSync(p, serializeArtifact(artifact), "utf8");
}
}