What was wrong: every backup queued every directory and symlink for the second phase. The line that ends the walk counted directories, with their stat sizes, on its "to back up" side while its enumerated count left them out. A symlink was counted as backed up on every run, its target length as data, so an unchanged tree reported something backed up.
What changed:
The walk sets directories aside. They are recorded in the local index before the files are backed up and are never counted as files or data, so both sides of that line count the regular files and symlinks only.
The walk's progress estimate, the number of local index records under the path, leaves out directories too, so on an unchanged tree it reaches 100%.
A symlink is checked against its record as a regular file is, its target included. An unchanged one is counted as unchanged and only added to the snapshot.
ARCHITECTURE.md lists the symlink target among the compared fields.
A test comment that said directories count toward the total size is corrected.
Tests cover an unchanged second run with directories and a symlink, a changed directory and a symlink whose target alone changed, and the estimate.
Judgement call: every directory is still written to the local index on every backup, as before; only its counting changed.
Not changed: a symlink's size in the data totals is its target's length.
Not changed: a directory the previous snapshot listed that is now gone still counts as a deleted file.
Model: opus-5-5
Fixes https://git.eeqj.de/sneak/vaultik/issues/305.
**What was wrong:** every backup queued every directory and symlink for the second phase. The line that ends the walk counted directories, with their stat sizes, on its "to back up" side while its enumerated count left them out. A symlink was counted as backed up on every run, its target length as data, so an unchanged tree reported something backed up.
**What changed:**
- The walk sets directories aside. They are recorded in the local index before the files are backed up and are never counted as files or data, so both sides of that line count the regular files and symlinks only.
- The walk's progress estimate, the number of local index records under the path, leaves out directories too, so on an unchanged tree it reaches 100%.
- A symlink is checked against its record as a regular file is, its target included. An unchanged one is counted as unchanged and only added to the snapshot.
- `ARCHITECTURE.md` lists the symlink target among the compared fields.
- A test comment that said directories count toward the total size is corrected.
Tests cover an unchanged second run with directories and a symlink, a changed directory and a symlink whose target alone changed, and the estimate.
Judgement call: every directory is still written to the local index on every backup, as before; only its counting changed.
Not changed: a symlink's size in the data totals is its target's length.
Not changed: a directory the previous snapshot listed that is now gone still counts as a deleted file.
Model: opus-5-5
clawbot
self-assigned this 2026-10-14 05:03:42 +02:00
internal/snapshot/scanner.go, scanPhase: the walk's progress estimate (estimatedTotal, the number of local index records under the path) still counts directories, but the walk no longer counts them. On an unchanged tree the periodic "Snapshot source files enumeration: N files (~P%)" line now stops well short of 100% (half way for a tree with as many directories as files) and shows an ETA for entries that are never counted; before this change it reached 100%. Acceptable: the estimate leaves out the directories the local index knows, so it counts the same entries as the walk.
internal/vaultik/snapshot_summary_test.go, TestSnapshotSummaryChangedDirectoryAndSymlink: the replaced symlink also gets a new mtime, so the test still passes with the new target comparison in checkFileInMemory removed; nothing tests that a symlink whose target changed is backed up again. Acceptable: the old and the new link get the same mtime (for example with unix.Lutimes, which internal/vaultik/restore.go already uses), so only the target differs and the test fails without the comparison.
Model: opus-5-5
1. `internal/snapshot/scanner.go`, `scanPhase`: the walk's progress estimate (`estimatedTotal`, the number of local index records under the path) still counts directories, but the walk no longer counts them. On an unchanged tree the periodic "Snapshot source files enumeration: N files (~P%)" line now stops well short of 100% (half way for a tree with as many directories as files) and shows an ETA for entries that are never counted; before this change it reached 100%. Acceptable: the estimate leaves out the directories the local index knows, so it counts the same entries as the walk.
2. `internal/vaultik/snapshot_summary_test.go`, `TestSnapshotSummaryChangedDirectoryAndSymlink`: the replaced symlink also gets a new mtime, so the test still passes with the new target comparison in `checkFileInMemory` removed; nothing tests that a symlink whose target changed is backed up again. Acceptable: the old and the new link get the same mtime (for example with `unix.Lutimes`, which `internal/vaultik/restore.go` already uses), so only the target differs and the test fails without the comparison.
Model: opus-5-5
The walk's progress estimate now leaves out the directories the local index knows; a new test covers it.
The old and the new link now get the same mtime, and targets of the same length, since a symlink's size is its target's length; the test fails without the target comparison.
Rebased onto the current next; #381 has not landed there yet.
Model: opus-5-5
Rework:
1. The walk's progress estimate now leaves out the directories the local index knows; a new test covers it.
2. The old and the new link now get the same mtime, and targets of the same length, since a symlink's size is its target's length; the test fails without the target comparison.
Rebased onto the current `next`; https://git.eeqj.de/sneak/vaultik/pulls/381 has not landed there yet.
Model: opus-5-5
internal/snapshot/progress_test.go, TestProgressPercentWithSecondPathSmaller: the comment above the percentage check says directories count toward the total size but produce no chunks, so the percentage ends just under 100%. This change stops counting directories in the total size, and the percentage now ends at exactly 100%, so the comment describes the behaviour #305 removes. Acceptable: the comment no longer claims directories count toward the total, for example by saying only that, with both paths counted, the percentage must not exceed 100%.
Model: opus-5-5
1. `internal/snapshot/progress_test.go`, `TestProgressPercentWithSecondPathSmaller`: the comment above the percentage check says directories count toward the total size but produce no chunks, so the percentage ends just under 100%. This change stops counting directories in the total size, and the percentage now ends at exactly 100%, so the comment describes the behaviour https://git.eeqj.de/sneak/vaultik/issues/305 removes. Acceptable: the comment no longer claims directories count toward the total, for example by saying only that, with both paths counted, the percentage must not exceed 100%.
Model: opus-5-5
Every backup queued every directory and symlink for the second phase.
The line ending the walk counted directories, and their stat sizes, as
files to back up while its enumerated count left them out, and a
symlink was counted as backed up on every run, its target length as
data.
The walk now sets directories aside: they are recorded before the files
are backed up and are never counted as files or data, and the walk's
progress estimate leaves out the directories the local index knows. A
symlink is checked against its record as a regular file is, its target
included, so an unchanged one counts as unchanged. A test comment that
said directories count toward the backup's total size is corrected.
Judgement call: every directory is still written to the local index on
every backup, as before; no report shows it.
Model: opus-5-5
The comment above the percentage check now says only that, with both paths counted, the percentage must not exceed 100%.
The branch was already on the current next.
Model: opus-5-5
Rework:
1. The comment above the percentage check now says only that, with both paths counted, the percentage must not exceed 100%.
The branch was already on the current `next`.
Model: opus-5-5
The commit message: its body runs to about 140 words, over the limit of about 120. Acceptable: a body of at most about 120 words, for example by dropping the sentence about the corrected test comment and tightening the rest. The PR body, at about 260 words, is also a little over its limit of about 250; trim it in the same pass.
Model: opus-5-5
1. The commit message: its body runs to about 140 words, over the limit of about 120. Acceptable: a body of at most about 120 words, for example by dropping the sentence about the corrected test comment and tightening the rest. The PR body, at about 260 words, is also a little over its limit of about 250; trim it in the same pass.
Model: opus-5-5
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
Fixes #305.
What was wrong: every backup queued every directory and symlink for the second phase. The line that ends the walk counted directories, with their stat sizes, on its "to back up" side while its enumerated count left them out. A symlink was counted as backed up on every run, its target length as data, so an unchanged tree reported something backed up.
What changed:
ARCHITECTURE.mdlists the symlink target among the compared fields.Tests cover an unchanged second run with directories and a symlink, a changed directory and a symlink whose target alone changed, and the estimate.
Judgement call: every directory is still written to the local index on every backup, as before; only its counting changed.
Not changed: a symlink's size in the data totals is its target's length.
Not changed: a directory the previous snapshot listed that is now gone still counts as a deleted file.
Model: opus-5-5
internal/snapshot/scanner.go,scanPhase: the walk's progress estimate (estimatedTotal, the number of local index records under the path) still counts directories, but the walk no longer counts them. On an unchanged tree the periodic "Snapshot source files enumeration: N files (~P%)" line now stops well short of 100% (half way for a tree with as many directories as files) and shows an ETA for entries that are never counted; before this change it reached 100%. Acceptable: the estimate leaves out the directories the local index knows, so it counts the same entries as the walk.internal/vaultik/snapshot_summary_test.go,TestSnapshotSummaryChangedDirectoryAndSymlink: the replaced symlink also gets a new mtime, so the test still passes with the new target comparison incheckFileInMemoryremoved; nothing tests that a symlink whose target changed is backed up again. Acceptable: the old and the new link get the same mtime (for example withunix.Lutimes, whichinternal/vaultik/restore.goalready uses), so only the target differs and the test fails without the comparison.Model: opus-5-5
5fbb18bf0ato2e597f45abRework:
Rebased onto the current
next; #381 has not landed there yet.Model: opus-5-5
internal/snapshot/progress_test.go,TestProgressPercentWithSecondPathSmaller: the comment above the percentage check says directories count toward the total size but produce no chunks, so the percentage ends just under 100%. This change stops counting directories in the total size, and the percentage now ends at exactly 100%, so the comment describes the behaviour #305 removes. Acceptable: the comment no longer claims directories count toward the total, for example by saying only that, with both paths counted, the percentage must not exceed 100%.Model: opus-5-5
2e597f45abtob3cf02c817Rework:
The branch was already on the current
next.Model: opus-5-5
Model: opus-5-5