feat(persona): give a face a cursor, so its masked values can be read - #288
Merged
Conversation
Opening a face showed its claims masked with no way to read one, and told the holder to go and find the value among their attributes instead. That is a real answer to a question nobody asked: someone is looking at *this* face precisely because they want to know what *this* face shows, and sending them to another tab to reconstruct it by eye is the pane declining to answer. The old refusal was reasoned, and the reasoning is what changed. It was not "a face must not be revealed" — it was "a face has no cursor over its claims, so the only reveal this view could offer is the blanket one the mask exists to avoid". That is a statement about the pane, not about the data. Give the detail view a cursor and the objection is gone, because "the selected claim" becomes a thing a holder can name. So the face detail now works exactly like the attributes tab, on the same terms: - `↑`/`↓` move a cursor over the claims. - `s` lifts the mask on the selected one, and puts it back on a second press. - The grant is one claim, and only while it is also the selected row — the render checks the pairing as well as the handler clearing it, so a grant that outlived its row cannot open a claim nobody chose. - Moving the cursor, closing the face, or leaving the tab each ends it. Opening a face starts at the top with nothing revealed, rather than inheriting an index that now names a different claim in a different face. A masked row also says it is masked, for the reason the attributes tab already does: `••••••••` and "(no value)" are the same shape on a row, and a holder who reads the first as the second concludes the face shows nothing. The "s to show" tail follows the cursor rather than sitting on every masked row, so the key is offered where it would work. There is deliberately no `v` here. On the attributes tab `v` is a *network* question — a listing fetched without values does not hold them — but a face detail is resolved in full when it is opened, so every value is already in hand and the mask is the only thing between it and the screen. A `v` would be a display flag pretending to be an escalation. `ResolvedClaim::revealed_value` is the new counterpart to `display_value`, and stays a separate method rather than a `reveal: bool` for the reason its pool sibling gives: reading a masked value in the clear should be something a call site had to name. Its doc records why the counterpart used to be absent and what changed, so the next reader meets the argument rather than a gap. Tests: the reveal opens only the selected claim; a grant that no longer names the selected row opens nothing; the key toggles; a reveal past the end or with no face open does nothing; every exit puts the mask back; opening a face starts closed and at the top; and at the core level a masked claim reads back whole only when asked for, while a stale one still says it is stale under a reveal. The test that encoded the old decision is updated rather than deleted, and says what changed. Gate: fmt, clippy -D warnings, rustdoc -D warnings, cargo test --workspace, and --no-default-features. Signed-off-by: Glenn Gore <glenn.g@affinidi.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Reported from the seat: "in Faces, we have some of these as able to be shown, yet showing as masked", and "be good to have a key (v) to press to show values easily".
Opening a face showed its claims masked with no way to read one, and told the holder to go and find the value among their attributes instead:
That is a real answer to a question nobody asked. Someone is looking at this face precisely because they want to know what this face shows; sending them to another tab to reconstruct it by eye is the pane declining to answer.
Why the old refusal no longer holds
It was reasoned, and the reasoning is what changed. It was never "a face must not be revealed" — it was:
That is a statement about the pane, not about the data. Give the detail view a cursor and the objection is gone, because "the selected claim" becomes a thing a holder can name.
What it does now
The face detail works exactly like the attributes tab, on the same terms:
↑/↓move a cursor over the claimsslifts the mask on the selected one; a second press puts it backA masked row also says it is masked, for the reason the attributes tab already does:
••••••••and(no value)are the same shape on a row, and a holder who reads the first as the second concludes the face shows nothing. The— s to showtail follows the cursor, so the key is only offered where it would work.On the
vkeyvalready exists — on Your attributes, where the header readsvalues shown — v to hide. It is deliberately not added here, and that is not an omission:vis a network question. A listing fetched without values does not hold them, which is what makes it an opt-in rather than a blindfold.A
vhere would be a display flag pretending to be an escalation.sis the honest key for what this view can actually offer.Types
ResolvedClaim::revealed_valueis the new counterpart todisplay_value. It stays a separate method rather than areveal: bool, for the reason its pool sibling gives: reading a masked value in the clear should be something a call site had to name. Its doc records why the counterpart used to be absent and what changed, so the next reader meets the argument rather than a gap.Tests
The reveal opens only the selected claim; a grant that no longer names the selected row opens nothing; the key toggles; a reveal past the end or with no face open does nothing; every exit puts the mask back; opening a face starts closed and at the top. At the core level: a masked claim reads back whole only when asked for, and a stale one still says it is stale under a reveal.
The test that encoded the old decision (
a_face_masks_its_values_and_says_where_to_read_one) is updated rather than deleted, and its doc says what changed and why.Gate
cargo fmt --all;cargo clippy --workspace --all-targets -- -D warnings;RUSTDOCFLAGS="-D warnings" cargo doc;cargo test --workspace;--no-default-featureschecks.Does not address the other two findings from the same session — the
(no value)rows (which #286 should already have fixed by sendingincludeSensitive; needs confirming against a live VTA) andwears: nothing, which is still waiting on a decision about which context a membership's face belongs to.