Skip to content

A sealed move deletes a note's version history without asking — the one path where the user never asked for encryption #91

Description

@cloudmanic

harbor notes update <id> --notebook <encrypt-by-default-notebook> seals the note, which hard-deletes every earlier version of it server-side — with no confirmation and no --yes to bypass.

Found while reviewing #82 (PR #90).

Why this one is different

#82 gated notes encrypt and notes decrypt, which is right: those are commands the user ran in order to change encryption, so a confirmation is the natural place to say what it costs.

The sealed move is the opposite. The user ran a command to move a note. Encryption is a side effect of the destination notebook's default_encrypt flag, and the history deletion is a side effect of that. Nothing in "move this note to that notebook" suggests the note's version history is about to be destroyed, and the command does not ask.

What exists today

  • cmd/notes.gonotes update --help carries the history-loss caveat, so it is documented beforehand.
  • cmd/notes_move.go:246printHistoryCaveat() prints it on stderr afterwards.

Both were added by PR #90. So the user is told, twice — but only in help text they may not have read and in a message that arrives after the versions are already gone. There is no point at which they can say no.

What to decide

Whether a move that seals should confirm. Arguments both ways:

  • For: it destroys data irreversibly, and it is the one path where the user never asked for encryption at all. Every other irreversible command in the CLI confirms (trash empty, notes delete --permanent, notes encrypt, notes decrypt, account deletion).
  • Against: moving notes is routine and a prompt on every move into an encrypting notebook would become noise people learn to dismiss — which is the exact failure mode notes encrypt silently deletes a note's version history, then says it's still readable #82's confirmation was designed around. It is also already warned in both directions.

A middle option: confirm only when the note actually has history to lose (the client would need to look), or gate it behind the existing --yes only when the move will seal.

Related

  • cmd/confirm_test.goirreversibleClientCalls now lists c.ConvertNoteToEncrypted(, but that guard only scans literal RunE block text. notesUpdateCmd reaches the call one frame away through writeNoteUpdate, so the structural check does not flag this path. Worth widening if this is gated.

Acceptance criteria

  • A decision recorded on this issue about whether the sealed move confirms
  • If it should: it confirms before writing, with --yes for scripts, and refuses unattended runs
  • If it should not: the reasoning is written down here, and the "no prompt" behaviour gets a test pinning it deliberately rather than by omission
  • irreversibleClientCalls' guard either catches this path or documents why it cannot

Metadata

Metadata

Assignees

Labels

encryptionEnd-to-end encryption: keys, locking, sealing, and what encryption does and does not cover

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions