feat(legacymove): also clear raw/ leftovers from before inbox zero (#209)

PlanRaw: an original that was archived but never removed (it has a .processed
marker AND a byte-identical copy under raw/processed/) is deleted with its
marker; a marker without a note is deleted; an unmarked note, a note without an
identical archive copy, and AutoTunnel's tunnel-candidates-* review queue are
never touched. The archive key flattens the whole path so raw/x.md and
wiki/sources/x.md cannot overwrite each other. Live dry run: 84 entries, 16
move, 53 delete (24 junk + 29 raw leftovers), 15 left.
Mutation-checked.

Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com>
This commit is contained in:
2026-10-20 21:02:41 +02:00
co-authored by Claude Sonnet 5.5
parent e14577d814
commit 2b16f2cc2f
3 changed files with 205 additions and 8 deletions
@@ -171,3 +171,101 @@ func TestApply_TheArchiveIsOutsideRawSoTheWatcherNeverIngestsIt(t *testing.T) {
assert.False(t, strings.Contains(res.ArchiveDir, "/raw"), res.ArchiveDir)
assert.True(t, strings.HasPrefix(res.ArchiveDir, "archive/"), res.ArchiveDir)
}
// --- raw/ leftovers from before inbox zero ---
func rawFile(t *testing.T, dir, rel, body string) { page(t, dir, rel, body) }
func TestPlanRaw_AnArchivedOriginalAndItsMarkerAreDeleted(t *testing.T) {
dir := t.TempDir()
rawFile(t, dir, "raw/clip.md", "the clip text")
rawFile(t, dir, "raw/clip.md.processed", "2026-10-19")
rawFile(t, dir, "raw/processed/2026-10-19/clip.md", "the clip text")
items, err := legacymove.PlanRaw(dir)
require.NoError(t, err)
m := byFrom(items)
assert.Equal(t, legacymove.Delete, m["raw/clip.md"].Action)
assert.Equal(t, legacymove.Delete, m["raw/clip.md.processed"].Action)
}
func TestPlanRaw_AnOriginalWhoseArchiveCopyDiffersIsLeftAlone(t *testing.T) {
dir := t.TempDir()
rawFile(t, dir, "raw/clip.md", "the clip text, edited since")
rawFile(t, dir, "raw/clip.md.processed", "2026-10-19")
rawFile(t, dir, "raw/processed/2026-10-19/clip.md", "the clip text")
items, err := legacymove.PlanRaw(dir)
require.NoError(t, err)
m := byFrom(items)
assert.Equal(t, legacymove.Skip, m["raw/clip.md"].Action, "no identical archive copy: not ours to delete")
assert.Contains(t, m["raw/clip.md"].Reason, "no identical copy")
_, hasMarker := m["raw/clip.md.processed"]
assert.False(t, hasMarker, "the marker of a note we keep is kept")
}
func TestPlanRaw_ACopyUnderATimestampedNameCounts(t *testing.T) {
dir := t.TempDir()
rawFile(t, dir, "raw/clip.md", "same text")
rawFile(t, dir, "raw/clip.md.processed", "d")
rawFile(t, dir, "raw/processed/2026-10-19/clip-180200.md", "same text")
rawFile(t, dir, "raw/processed/2026-10-19/clip-2.md", "other text")
items, err := legacymove.PlanRaw(dir)
require.NoError(t, err)
assert.Equal(t, legacymove.Delete, byFrom(items)["raw/clip.md"].Action)
}
func TestPlanRaw_AnOrphanMarkerIsDeleted(t *testing.T) {
dir := t.TempDir()
rawFile(t, dir, "raw/gone.md.processed", "2026-06-16")
items, err := legacymove.PlanRaw(dir)
require.NoError(t, err)
assert.Equal(t, legacymove.Delete, byFrom(items)["raw/gone.md.processed"].Action)
}
func TestPlanRaw_TheAutoTunnelReviewQueueAndANoteWithoutAMarkerAreNotTouched(t *testing.T) {
dir := t.TempDir()
rawFile(t, dir, "raw/tunnel-candidates-2026-06-14.md", "AutoTunnel's own queue")
rawFile(t, dir, "raw/tunnel-candidates-2026-06-14.md.processed", "x")
rawFile(t, dir, "raw/fresh.md", "an unprocessed clip")
rawFile(t, dir, "raw/processed/2026-10-19/fresh.md", "an unprocessed clip") // same bytes, but no marker: still in the inbox
items, err := legacymove.PlanRaw(dir)
require.NoError(t, err)
m := byFrom(items)
for _, f := range []string{"raw/tunnel-candidates-2026-06-14.md", "raw/tunnel-candidates-2026-06-14.md.processed", "raw/fresh.md"} {
_, listed := m[f]
assert.False(t, listed, "%s is not a leftover", f)
}
}
func TestApplyAndRollback_HandleRawLeftoversAndNeverCollideWithSourcesOfTheSameName(t *testing.T) {
dir := t.TempDir()
rawFile(t, dir, "raw/same.md", "raw text")
rawFile(t, dir, "raw/same.md.processed", "d")
rawFile(t, dir, "raw/processed/2026-10-19/same.md", "raw text")
page(t, dir, "wiki/sources/same.md", src("video")) // a wiki source with the same basename
rawItems, err := legacymove.PlanRaw(dir)
require.NoError(t, err)
srcItems, err := legacymove.Plan(dir, "web-clip")
require.NoError(t, err)
res, err := legacymove.Apply(dir, append(rawItems, srcItems...), time.Date(2026, 10, 20, 0, 0, 0, 0, time.UTC))
require.NoError(t, err)
for _, gone := range []string{"raw/same.md", "raw/same.md.processed", "wiki/sources/same.md"} {
_, statErr := os.Stat(filepath.Join(dir, gone))
assert.ErrorIs(t, statErr, os.ErrNotExist, gone)
}
_, statErr := os.Stat(filepath.Join(dir, "raw/processed/2026-10-19/same.md"))
assert.NoError(t, statErr, "the archive copy in raw/processed is never touched")
require.NoError(t, legacymove.Rollback(dir, res.ArchiveDir))
got, err := os.ReadFile(filepath.Join(dir, "raw/same.md"))
require.NoError(t, err)
assert.Equal(t, "raw text", string(got), "the raw note and the wiki source of one name did not overwrite each other in the archive")
got, err = os.ReadFile(filepath.Join(dir, "wiki/sources/same.md"))
require.NoError(t, err)
assert.Equal(t, src("video"), string(got))
}