Commit Graph

3 Commits

Author SHA1 Message Date
vvzvlad
2f7c0649bb feat(sync): FS->Docmost push #3 — move/rename apply (§5 path-as-truth)
Complete the push action coverage (create/update/delete/move/rename/noop).

- push.ts classifyRenameMoves (pure): the file PATH is the source of truth for
  tree position (§5) — new parent resolved from the enclosing folder's <dir>.md
  page, not the stale meta.parentPageId. Emit move iff parent changed, rename iff
  meta.title changed; a pure path-only rename is a NOOP (no Docmost call — the
  path is local, identity is pageId)
- applyPushActions: move (move_page, reparent) THEN rename (rename_page); noop
  records and calls nothing; per-page isolation + refs-only-on-success preserved
- resolveParentPageId reads <dir>.md meta via readFile (current) /
  git.showFileAtRef(last-pushed) (prev), matching buildVaultLayout
- review fixes: prefetch wrapped in per-page try/catch so a tree-read throw
  isolates one page (§12), not the batch; failures.kind attributes the op that
  actually threw (rename-after-move -> "rename")
- tests (+13): classifier (move/rename/both/noop/to-root), apply (calls/no-calls,
  ordering, isolation); 724 -> 737 green (x2 stable); corpus STABLE

Deferred (final increment): live main() daemon, FS-watcher/debounce (§7.1),
git-remote push (§7.2), pull-side bodyHash/updatedAt consumption, fractional-index
position, escalate-on-divergent-docmost.
2026-06-20 18:52:54 +03:00
vvzvlad
2d13e5ca15 feat(sync): FS->Docmost push #2 — loop-close (§6.3/§10) + fix flaky property timeout
- git.ts: fastForwardBranch(branch, toCommit) — advances ONLY on a true
  fast-forward (merge-base --is-ancestor), refuses a non-ff without clobbering
  divergent docmost history
- push.ts: after a CLEAN push (failures===0) advance both refs/docmost/last-pushed
  AND fast-forward the docmost mirror, so the next pull sees no diff for pushed
  pages (loop-guard, git-native); a partial push advances NEITHER (§12)
- push.ts: per-page error isolation (one bad page doesn't block the batch,
  failures recorded); create requires a non-empty spaceId else skipped (§8 spirit)
- loop-guard.ts: bodyHash() (sha256) + per-page pushed:[{pageId,updatedAt?,bodyHash}]
  record for the §10 self-write suppression (pull-side consumption deferred)
- test: markdown-roundtrip property tests get a 30s per-test timeout (deterministic
  inputs via fixed seed; the only flakiness was wall-clock under parallel load,
  which intermittently failed CI/docker)
- 709 -> 724 green (3x stable); build clean; corpus STABLE

Deferred (next/final increment): move/rename apply, pull-side loop-guard consumption,
FS-watcher/debounce (§7.1), git-remote push (§7.2), runnable live main(),
escalate-on-divergent-docmost.
2026-06-20 17:10:09 +03:00
vvzvlad
9c6283aa8e feat(sync): FS->Docmost push #1 — diff/ref primitives + pure planner + apply (fakes)
First slice of the push direction (SPEC §6), mirroring pull: VaultGit primitives +
pure planner + thin injectable apply, exercised via fakes (no live destructive run).

- git.ts: diffNameStatus (--name-status -M -z, NUL-parsed, rename-aware),
  revParse/readRef/updateRef (refs/docmost/last-pushed), showFileAtRef (recover a
  deleted file's pre-image pageId)
- push.ts computePushActions (pure): A/M/D/R -> create/update/delete/renamesMoves;
  delete only when pageId is recovered from the pre-image, else skipped (§8 guard —
  no spurious Docmost delete)
- push.ts applyPushActions (fakes): update via importPageMarkdown (collab/Yjs path,
  §2 — never a raw jsonb overwrite); create via createPage then write the assigned
  pageId back into the file meta (body preserved); delete via deletePage (soft, §8);
  renamesMoves deferred; advances last-pushed
- tests (+26): diffNameStatus A/M/D/rename, ref round-trip, showFileAtRef; pure
  classification incl. §8 no-pageid skip; apply with fakes (collab-path update,
  pageid write-back, soft-delete, deferred moves)
- 683 -> 709 green; build clean; corpus STABLE

Deferred (next increment): move/rename apply, loop-guard (§10), watcher/debounce,
remote push, live main wiring, empty-spaceId create guard, per-page error isolation.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-17 02:32:15 +03:00