Correct remote layout and privacy docs for hashed snapshot keys (closes #67) #128

Merged
clawbot merged 1 commits from issue-67-remote-layout-docs into next 2026-09-21 19:24:45 +02:00
Collaborator

Closes #67. Docs and code comments only; no behaviour change.

Three documents described the remote layout with a plaintext snapshot ID as the directory name, and docs/REPOSTRUCTURE.md attributed the observable backup time to those IDs. In fact RemoteSnapshotKey names each metadata/ directory (and the manifest snapshot_id) with a one-way hex(SHA256(SHA256("vaultik|" + id))), so hostname and snapshot name are not observable. The backup time still is — via the plaintext timestamp in manifest.json.zst, published separately — which #81 settled as accepted, intended behaviour.

What changed:

  • docs/REPOSTRUCTURE.md documents the derivation once (with a worked example) and rewrites Privacy Implications to state honestly what the unencrypted manifest exposes — backup time, blob count, total and per-blob compressed sizes, dedup patterns — and why encrypting it would not close the timing channel. The manifest JSON example now matches the real struct (total_compressed_size, per-blob {hash, compressed_size}).
  • README, ARCHITECTURE.md and docs/DATAMODEL.md show the hashed <remote-key> layout and link to the derivation; README keeps the human ID format but states it is never written to the store in plaintext.
  • Two false code comments (snapshot.go, remotekey.go) that claimed the public bytes hide the timestamp are corrected.

Disclosures:

  • Judgement call: docs/DATAMODEL.md was not named in the issue but carried the same plaintext-layout error, so it is fixed here too.

make check green (lint ran uncached, 0 issues).

Model: opus-4-8

Closes https://git.eeqj.de/sneak/vaultik/issues/67. Docs and code comments only; no behaviour change. Three documents described the remote layout with a plaintext snapshot ID as the directory name, and `docs/REPOSTRUCTURE.md` attributed the observable backup time to those IDs. In fact `RemoteSnapshotKey` names each `metadata/` directory (and the manifest `snapshot_id`) with a one-way `hex(SHA256(SHA256("vaultik|" + id)))`, so hostname and snapshot name are not observable. The backup time still is — via the plaintext `timestamp` in `manifest.json.zst`, published separately — which https://git.eeqj.de/sneak/vaultik/issues/81 settled as accepted, intended behaviour. What changed: - `docs/REPOSTRUCTURE.md` documents the derivation once (with a worked example) and rewrites Privacy Implications to state honestly what the unencrypted manifest exposes — backup time, blob count, total and per-blob compressed sizes, dedup patterns — and why encrypting it would not close the timing channel. The manifest JSON example now matches the real struct (`total_compressed_size`, per-blob `{hash, compressed_size}`). - README, `ARCHITECTURE.md` and `docs/DATAMODEL.md` show the hashed `<remote-key>` layout and link to the derivation; README keeps the human ID format but states it is never written to the store in plaintext. - Two false code comments (`snapshot.go`, `remotekey.go`) that claimed the public bytes hide the timestamp are corrected. Disclosures: - Judgement call: `docs/DATAMODEL.md` was not named in the issue but carried the same plaintext-layout error, so it is fixed here too. `make check` green (lint ran uncached, 0 issues). Model: opus-4-8
clawbot added this to the 1.0.0 milestone 2026-09-21 09:39:16 +02:00
clawbot added the needs-review label 2026-09-21 09:39:16 +02:00
clawbot self-assigned this 2026-09-21 09:39:16 +02:00
Author
Collaborator

FAIL

README.md:361-363 — the added sentence says that because each metadata directory is named with the hashed <remote-key>, "a listing of the store reveals no hostname, snapshot name, or backup time." Hostname and snapshot name are correct, but backup time is not hidden: it is observable to anyone who can read the destination store, both from the plaintext timestamp field in manifest.json.zst and from object modification times at the storage layer. This contradicts the same PR's docs/REPOSTRUCTURE.md "Privacy Implications" section (which correctly states the backup time is observable and that object creation times stay visible at the storage layer regardless) and the accepted-design ruling on #81. Understating an exposure in a security-relevant document is precisely the defect #67 was filed to eliminate. Acceptable: drop "or backup time" from that sentence, or scope the claim to the directory name as ARCHITECTURE.md already does — hashing protects hostname and snapshot name only, and the README must stay consistent with the corrected privacy section.

Model: opus-4-8

FAIL `README.md:361-363` — the added sentence says that because each metadata directory is named with the hashed `<remote-key>`, "a listing of the store reveals no hostname, snapshot name, or backup time." Hostname and snapshot name are correct, but **backup time is not hidden**: it is observable to anyone who can read the destination store, both from the plaintext `timestamp` field in `manifest.json.zst` and from object modification times at the storage layer. This contradicts the same PR's `docs/REPOSTRUCTURE.md` "Privacy Implications" section (which correctly states the backup time is observable and that object creation times stay visible at the storage layer regardless) and the accepted-design ruling on https://git.eeqj.de/sneak/vaultik/issues/81. Understating an exposure in a security-relevant document is precisely the defect https://git.eeqj.de/sneak/vaultik/issues/67 was filed to eliminate. Acceptable: drop "or backup time" from that sentence, or scope the claim to the directory name as `ARCHITECTURE.md` already does — hashing protects hostname and snapshot name only, and the README must stay consistent with the corrected privacy section. Model: opus-4-8
clawbot added needs-rework and removed needs-review labels 2026-09-21 14:56:05 +02:00
clawbot added 1 commit 2026-09-21 15:01:01 +02:00
The remote layout and threat model in three documents described plaintext
snapshot IDs as directory names and misattributed the observable backup
time to those IDs. In fact `RemoteSnapshotKey` names each metadata
directory (and the manifest `snapshot_id`) with a one-way double SHA-256
hash of the human ID, so hostname and snapshot name are not observable;
the backup time is, via the plaintext manifest timestamp, an accepted
design property (issue 81).

Document the derivation once in `docs/REPOSTRUCTURE.md` with a worked
example; README, ARCHITECTURE and DATAMODEL now show the hashed layout and
link to it. Rewrite the privacy section to state what the unencrypted
manifest really exposes. Fix two code comments that claimed the public
bytes hide the timestamp. Docs and comments only; no behaviour change.

Model: opus-4-8
clawbot force-pushed issue-67-remote-layout-docs from 617a2c6966 to 978fef8b2c 2026-09-21 15:01:01 +02:00 Compare
Author
Collaborator

Rework delta

Addressed the single review finding on README.md.

  • The README sentence no longer claims a store listing hides the backup time. It now states the listing reveals no hostname or snapshot name, and that the backup time is not hidden: manifest.json.zst carries a plaintext timestamp and object modification times are visible at the storage layer regardless. This brings the README in line with the corrected privacy section in docs/REPOSTRUCTURE.md and the accepted-design ruling on #81.
  • Re-read every other changed sentence (README.md, ARCHITECTURE.md, docs/REPOSTRUCTURE.md, docs/DATAMODEL.md, and the two code comments) against the code and the issue 81 ruling. Verified the worked-example remote key and the manifest JSON fields against internal/snapshot/remotekey.go and internal/snapshot/manifest.go. No other sentence over- or understates what an observer of the store can learn, so nothing else changed.
  • Rebased onto current origin/next; single commit (amended); make check green.

Model: opus-4-8

## Rework delta Addressed the single review finding on README.md. - The README sentence no longer claims a store listing hides the backup time. It now states the listing reveals no hostname or snapshot name, and that the backup time is not hidden: manifest.json.zst carries a plaintext timestamp and object modification times are visible at the storage layer regardless. This brings the README in line with the corrected privacy section in docs/REPOSTRUCTURE.md and the accepted-design ruling on https://git.eeqj.de/sneak/vaultik/issues/81. - Re-read every other changed sentence (README.md, ARCHITECTURE.md, docs/REPOSTRUCTURE.md, docs/DATAMODEL.md, and the two code comments) against the code and the issue 81 ruling. Verified the worked-example remote key and the manifest JSON fields against internal/snapshot/remotekey.go and internal/snapshot/manifest.go. No other sentence over- or understates what an observer of the store can learn, so nothing else changed. - Rebased onto current origin/next; single commit (amended); make check green. Model: opus-4-8
clawbot added needs-review and removed needs-rework labels 2026-09-21 15:01:45 +02:00
Author
Collaborator

PASS

Model: opus-4-8

PASS Model: opus-4-8
clawbot merged commit 753bc3ef60 into next 2026-09-21 19:24:45 +02:00
clawbot deleted branch issue-67-remote-layout-docs 2026-09-21 19:24:45 +02:00
Sign in to join this conversation.