From f6c3f2af238bea9bc38818beb30b990b34ebb072 Mon Sep 17 00:00:00 2001 From: Mathias Date: Fri, 2 Oct 2026 16:40:10 +0200 Subject: [PATCH] test(reconcile): the skipped reason carries a kind, not the model's text (red; review F3) Co-Authored-By: Claude Sonnet 5.5 --- internal/reconcile/reconcile_reason_test.go | 33 +++++++++++++++++++++ 1 file changed, 33 insertions(+) create mode 100644 internal/reconcile/reconcile_reason_test.go diff --git a/internal/reconcile/reconcile_reason_test.go b/internal/reconcile/reconcile_reason_test.go new file mode 100644 index 0000000..d8ab642 --- /dev/null +++ b/internal/reconcile/reconcile_reason_test.go @@ -0,0 +1,33 @@ +package reconcile_test + +import ( + "context" + "errors" + "testing" + + "github.com/stretchr/testify/assert" + "github.com/stretchr/testify/require" + + "git.d-ma.be/mathias/tapir/internal/domain" + "git.d-ma.be/mathias/tapir/internal/reconcile" +) + +// The reason a reconciliation was skipped is stored and shown on a page about a private +// recording, so it carries a kind, never the model's error text, which can echo the +// prompt (adversarial review F3). + +func TestReconcile_TheBreakerReasonCarriesAKindNotTheModelsText(t *testing.T) { + adj := &scripted{fn: func(int, reconcile.Request) (reconcile.Verdict, error) { + return reconcile.VerdictBase, errors.New("gateway echoed the prompt: zebrakaka secret words") + }} + small := opts + small.BreakAfter = 2 + + out, err := reconcile.Reconcile(context.Background(), tr(progBase), tr(progAlt), adj, small) + + require.NoError(t, err) + require.Equal(t, domain.ReconcileSkipped, out.Reconciliation.Status) + assert.NotContains(t, out.Reconciliation.Reason, "zebrakaka", "provider text must not be stored or shown") + assert.Contains(t, out.Reconciliation.Reason, "2 times in a row", "the reason still says what happened") + assert.Contains(t, out.Reconciliation.Reason, "error", "and carries a kind") +}