19242ef73b
Every clarify turn said one sentence per gap, and a re-ask repeated it word for word. A question he already failed to answer is the worst one to ask again unchanged: the second wording is what tells him which part she missed. clarifytemplates.go holds three wordings per slot, picked by attempt rather than at random — short first, then naming the gap, then spelling it out with an example. Past the end she keeps the most explicit one instead of wrapping back to the short question he has already not answered. The intents with nothing identifiable to ask about (note, query, chat, system) kept the stub's single "не совсем поняла — можешь переформулировать?", which is the line he hears whenever she misses him completely. Four wordings now, picked by a hash of the utterance so one question asked twice reads the same and two different misses do not. Still no model call on this path: the resident model would wander, and this text has to be right every time. No schema_version either, unlike the nudge templates — these are Go constants, so no file can drift out of step with the code that reads it. The persona test already in clarify_test.go covers the new lines. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
64 lines
2.2 KiB
Go
64 lines
2.2 KiB
Go
package main
|
|
|
|
import (
|
|
"testing"
|
|
|
|
"github.com/kami/maven/internal/dialogue"
|
|
"github.com/kami/maven/internal/router"
|
|
)
|
|
|
|
// Every slot she can ask about has a wording for every attempt she is allowed,
|
|
// and no two attempts on one slot read the same. A deck with a repeated line is
|
|
// the defect this deck exists to fix (Vikunja #457).
|
|
func TestClarifyQuestionsVaryByAttempt(t *testing.T) {
|
|
for slot, variants := range clarifyQuestionVariants {
|
|
seen := map[string]bool{}
|
|
for _, v := range variants {
|
|
if v == "" {
|
|
t.Errorf("%s: empty wording in the deck", slot)
|
|
}
|
|
if seen[v] {
|
|
t.Errorf("%s: repeated wording %q", slot, v)
|
|
}
|
|
seen[v] = true
|
|
}
|
|
for attempt := 1; attempt <= len(variants); attempt++ {
|
|
got, ok := clarifyQuestionFor(slot, attempt)
|
|
if !ok || got != variants[attempt-1] {
|
|
t.Errorf("%s attempt %d = %q ok=%v, want %q", slot, attempt, got, ok, variants[attempt-1])
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
// Past the end she keeps the most explicit wording. Wrapping round would ask
|
|
// the short question he has already not answered twice.
|
|
func TestClarifyQuestionPastTheEndKeepsTheLastWording(t *testing.T) {
|
|
last := clarifyQuestionVariants[dialogue.SlotTime][len(clarifyQuestionVariants[dialogue.SlotTime])-1]
|
|
for _, attempt := range []int{0, 4, 9} {
|
|
if got, _ := clarifyQuestionFor(dialogue.SlotTime, attempt); attempt > 1 && got != last {
|
|
t.Errorf("attempt %d = %q, want the last wording %q", attempt, got, last)
|
|
}
|
|
}
|
|
if _, ok := clarifyQuestionFor("nonesuch", 1); ok {
|
|
t.Error("an unknown slot must have no question")
|
|
}
|
|
}
|
|
|
|
// The missed line is stable for one utterance and absent for a decision that is
|
|
// not a clarify.
|
|
func TestClarifyMissedLine(t *testing.T) {
|
|
d := router.Decision{Clarify: true, Utterance: "мгм"}
|
|
first := clarifyMissedLine(d)
|
|
if first == "" || first != clarifyMissedLine(d) {
|
|
t.Fatalf("the missed line must be stable for one utterance, got %q", first)
|
|
}
|
|
if got := clarifyMissedLine(router.Decision{Intent: router.IntentNote}); got != "" {
|
|
t.Errorf("a decision that is not a clarify got %q", got)
|
|
}
|
|
// The empty utterance still gets a line: she has to say something.
|
|
if got := clarifyMissedLine(router.Decision{Clarify: true}); got == "" {
|
|
t.Error("an empty utterance must still be answered out loud")
|
|
}
|
|
}
|