package main import ( "strings" "testing" "git.novox.be/novox/mesh-sdk/go/asks" ) // adr0343 is the ask for ADR 0343 as the router now sends it to this channel (novox/hq issue 639): the knowledge // base's brief as its title and body, the rest in its note. On 2026-10-13 the same ask arrived as about thirty plain // lines — every one of its thirteen clauses on a line of its own — and the operator would not read it. var adr0343 = asks.Message{Handle: "h-343", To: "42", Title: "Your agents' memory follows you to every machine", Body: "What an agent learns in a project's memory is copied to every machine that runs the agent, so a session " + "anywhere starts with it. A file changed on two machines keeps both versions and warns you; secrets in memory files " + "are screened, though not perfectly.\n" + "• Only memory folders travel: links and files over 128 KiB stay where they are\n" + "• A conflict reaches you as a warning that needs you\n" + "• A deleted file is marked, and a newer change elsewhere outlives the deletion", Note: "Asked by mesh-knowledge at 16:05. Unanswered by tomorrow 15:55: the record stays proposed; nothing of it is in force.\n" + "Approve: the record is accepted and its clauses are in force. Decline: the record stays proposed; nothing of it is in force.\n" + "ADR 0343, proposed by fix-367@g14; the knowledge base's own review approved it. Fingerprint a59f 361b f60e cb5e d237 a837.\n" + "Read its 13 clauses with the knowledge base's get, number 343.", Buttons: []asks.Button{{Label: "Approve", Ticket: "t-approve"}, {Label: "Decline", Ticket: "t-decline"}}} // The ADR 0343 ask fits a phone's glance: a bold headline, the summary and its points, then the rest apart and // collapsed — at most twelve lines in all, and never a clause. func TestTheADR0343AskFitsAGlance(t *testing.T) { c, f, _, _ := newChannel(t, goodToken) subject, body := work(asks.Show, adr0343) if err := c.Take(subject, body); err != nil { t.Fatal(err) } sent := f.of("sendMessage") if len(sent) != 1 { t.Fatalf("sent %d", len(sent)) } html := sent[0].Body["text"].(string) t.Logf("as sent:\n%s", html) lines := strings.Split(html, "\n") if len(lines) > 12 { t.Errorf("the ask is %d lines, more than 12:\n%s", len(lines), html) } if lines[0] != "Your agents' memory follows you to every machine" && lines[0] != "Your agents' memory follows you to every machine" { t.Errorf("the headline is not first and bold: %q", lines[0]) } if !strings.HasPrefix(lines[1], "What an agent learns") || strings.Count(html, "\n• ") != 3 { t.Errorf("the summary and its three points do not follow the headline:\n%s", html) } if !strings.Contains(html, "\n\n
Asked by mesh-knowledge at 16:05.") || !strings.HasSuffix(html, "number 343.
") { t.Errorf("the note is not apart and collapsed:\n%s", html) } for _, lead := range []string{"Only the memory folders are carried", "How it is checked", "13 clause(s)", "**"} { if strings.Contains(html, lead) { t.Errorf("the ask carries %q", lead) } } if sent[0].Body["parse_mode"] != "HTML" { t.Errorf("not sent as HTML: %v", sent[0].Body["parse_mode"]) } } // A long note is cut before the body is, and the cut said; a body too long loses the note and is cut itself. func TestALongNoteIsCutBeforeTheBody(t *testing.T) { m := asks.Message{Title: "t", Body: "the summary", Note: strings.Repeat("n", 5000)} s := partsOf(m) if s.body != "the summary" || !strings.HasSuffix(s.note, cutNote) || len([]rune(s.plain())) != MaxLength { t.Errorf("body %q, note ends %q, %d characters", s.body, s.note[len(s.note)-20:], len([]rune(s.plain()))) } m.Body = strings.Repeat("b", 5000) s = partsOf(m) if s.note != "" || !strings.HasSuffix(s.body, cutNote) || len([]rune(s.plain())) != MaxLength { t.Errorf("note %d, %d characters", len(s.note), len([]rune(s.plain()))) } }