Review: a path is read as a path in the whole words, and Details say what the desk shows (issue 383)
mesh/merge-gate pass: builds build-agent, mesh-controller, route-proxy → ace, g14, novox, shanks; no bus step; every machine composes with the change as it…
mesh/repo-check pass: its merge-check.sh passed
mesh/delivery-group group fix/383-a-proposal-reads-whole-on-the-phone ready: every member ready, and composed together they pass
mesh/delivery superseded: a newer head of the same pull request

The review of 2026-10-10: a mixed-case path with a digit ("/mnt/Photos_2024/Jochen") read as a
random string and was withheld from the whole words, the symptom again (outward.Secret now judges
a run with a slash piece by piece, as the messenger's CheckSecret does); and the Details line on
masking read, on the phone, as if something there were masked.
This commit is contained in:
jochen
2026-10-10 15:46:55 +02:00
parent 7a92224886
commit 68557b412f
4 changed files with 23 additions and 6 deletions
+1 -1
View File
@@ -178,7 +178,7 @@ func (p settingsProposal) ask(id string, machines []string) (asks.Ask, map[strin
var d strings.Builder
fmt.Fprintf(&d, "Fingerprint %s.\n", fingerprint(p.Digest))
if !shownWhole {
d.WriteString("Parts shown as ‹address›, ‹path› or ‹withheld› may not leave the mesh where the sender is not proven.\n")
d.WriteString("On a channel that does not prove who answers, these values are shown as ‹address›, ‹path› or ‹withheld›.\n")
}
fmt.Fprintf(&d, "Read it whole, with this fingerprint: settings proposals %s at the controller's terminal, or "+
"mesh-controller.settings with proposal %s through the mesh MCP server.\n", id, id)
+3 -3
View File
@@ -133,7 +133,7 @@ func TestAProposalAsksAtTheLevelApproveWithTheExactChange(t *testing.T) {
}
for _, line := range []string{
"Fingerprint " + fingerprint(layerDigest(mountsSources)) + ".",
"Parts shown as ‹address›, ‹path› or ‹withheld› may not leave the mesh where the sender is not proven.",
"On a channel that does not prove who answers, these values are shown as ‹address›, ‹path› or ‹withheld›.",
"Read it whole, with this fingerprint: settings proposals " + kept(r).ID + " at the controller's terminal",
"Approved, the layer is set at once and the machine takes it at its next push.",
} {
@@ -141,7 +141,7 @@ func TestAProposalAsksAtTheLevelApproveWithTheExactChange(t *testing.T) {
t.Errorf("Details lack %q:\n%s", line, q.Details)
}
}
for _, howTo := range []string{"ingerprint", "settings proposals", "mesh-controller.settings", "may not leave", "Approved,"} {
for _, howTo := range []string{"ingerprint", "settings proposals", "mesh-controller.settings", "does not prove", "Approved,"} {
if strings.Contains(q.Explanation, howTo) || strings.Contains(q.Whole, howTo) {
t.Errorf("the message carries the how-to %q", howTo)
}
@@ -261,7 +261,7 @@ func TestAProposalShowsItsValuesWholeOnlyWhereTheSenderIsProvenAndNeverASecret(t
t.Fatal(err)
}
if q2 := r2.askSent(t); q2.Whole != "" || !strings.HasPrefix(q2.Explanation, "+ font-size: 13\n+ width: 500\nProposed by ") ||
strings.Contains(q2.Details, "may not leave") {
strings.Contains(q2.Details, "does not prove who answers") {
t.Errorf("%+v", q2)
}
}
+16 -2
View File
@@ -105,13 +105,27 @@ func Check(text string, machines ...string) (Refusal, bool) {
// Secret says whether a text carries a secret's shape, the one class that leaves the mesh nowhere — the
// messenger's CheckSecret, one for one. It is what an ask's whole words (asks.Ask.Whole, novox/hq issue 383)
// are held to: on a channel that proves who answers, a path or an address is what the operator approves and
// is shown; a secret never is.
// is shown; a secret never is. A path is read as one: a run with a slash in it is judged piece by piece
// between the slashes, so "/mnt/Photos_2024/Jochen" is a path and not a random string (the review of
// 2026-10-10); the named shapes hold whatever the run holds.
func Secret(text string, machines ...string) (Refusal, bool) {
text = withoutMachines(text, machines)
if refusal, ok := secretShape(text); !ok {
return refusal, false
}
return randomRun(text)
return randomRunOutsidePaths(text)
}
// randomRunOutsidePaths is randomRun with each run that holds a slash judged by its pieces between the slashes.
func randomRunOutsidePaths(text string) (Refusal, bool) {
for _, run := range reRun.FindAllString(text, -1) {
for _, piece := range strings.Split(run, "/") {
if len(piece) >= 20 && looksRandom(piece) {
return Refusal{"secret", "a long random-looking string"}, false
}
}
}
return Refusal{}, true
}
// secretShape is the secret shapes a pattern names.
+3
View File
@@ -107,6 +107,9 @@ func TestSecretRefusesOnlyASecretsShape(t *testing.T) {
for _, text := range []string{
"recalbox=smb://nas.lan/recalbox@/mnt/recalbox:ro",
"library=/mnt/library",
"photos=/mnt/Photos_2024/Jochen",
"games=smb://nas.lan/Recalbox_Games2024",
"/srv/media/Series_Archive/Season01",
"10.77.0.9:53",
"jochen@example.com",
"C:\\Users\\jo",