diff --git a/secrets b/secrets index 600a25e..2328fdc 100755 --- a/secrets +++ b/secrets @@ -529,7 +529,11 @@ STORE_FORMAT_FILE_NAME=".secrets-format" _store_format() { local f="$SECRETS_DIR/$STORE_FORMAT_FILE_NAME" v if [ -f "$f" ]; then - v=$(head -1 "$f" 2>/dev/null | tr -dc '0-9') + # Strict exact match (modulo line endings): only a marker of exactly "2" + # reads as v2. Anything else (empty, "20", "v2", garbage) ⇒ v1 — the safe + # default, since misreading v2-as-v1 only triggers a harmless re-migrate + # while v1-as-v2 would mislocate blobs. + v=$(head -1 "$f" 2>/dev/null | tr -d '\r\n') [ "$v" = "2" ] && { echo 2; return; } fi echo 1 @@ -2233,7 +2237,9 @@ $untwinned cd into each project and run 'secrets migrate', then re-run 'secrets # Stamp the marker FIRST, then drop v1 blobs. If finalize crashes between # the two, the store reads as v2 and the (verified) v2 twins serve every - # upgraded client; leftover v1 blobs are harmless orphans a re-run cleans. + # upgraded client; any leftover v1 blobs are harmless orphans (referenced by + # no v2 suffix lookup) that `secrets verify` will flag and the operator can + # remove. A re-run of --finalize early-returns (store is already v2). printf '2\n' > "$SECRETS_DIR/$STORE_FORMAT_FILE_NAME" while IFS= read -r f; do [ -f "$f" ] || continue