Skip to content

Commit 61cbfb8

Browse files
GottZclaude
andcommitted
fix(dream): structural pre-check for supersedes links
9B model can't distinguish "complementary" from "replaces". Added deterministic V8 gate in WriteLinks: supersedes links are only accepted when same category + source older than target + title similarity >= 0.25. Cleaned up all false-positive supersedes links (44 low-confidence + 2 high-confidence that failed structural validation). 0 supersedes links remain — Dream will rebuild them with the new checks. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
1 parent 0b942d2 commit 61cbfb8

1 file changed

Lines changed: 41 additions & 3 deletions

File tree

go/internal/dream/evaluate.go

Lines changed: 41 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -129,16 +129,28 @@ func WriteLinks(ctx context.Context, pool *pgxpool.Pool, sourceID, sourceScope s
129129
}
130130
defer tx.Rollback(ctx) //nolint:errcheck
131131

132+
// Fetch source block metadata for supersedes structural checks.
133+
var srcCategory string
134+
var srcUpdatedAt time.Time
135+
var srcTitle string
136+
_ = tx.QueryRow(ctx,
137+
`SELECT category, updated_at, title FROM context_blocks WHERE id = $1`,
138+
sourceID,
139+
).Scan(&srcCategory, &srcUpdatedAt, &srcTitle)
140+
132141
written := 0
133142
for _, link := range links {
134-
// Fetch target block scope + archived status.
143+
// Fetch target block scope + archived status + metadata for structural checks.
135144
var targetScope string
136145
var targetArchived bool
137146
var targetQuality float64
147+
var targetCategory string
148+
var targetUpdatedAt time.Time
149+
var targetTitle string
138150
err := tx.QueryRow(ctx,
139-
`SELECT scope, is_archived, quality_score FROM context_blocks WHERE id = $1`,
151+
`SELECT scope, is_archived, quality_score, category, updated_at, title FROM context_blocks WHERE id = $1`,
140152
link.TargetID,
141-
).Scan(&targetScope, &targetArchived, &targetQuality)
153+
).Scan(&targetScope, &targetArchived, &targetQuality, &targetCategory, &targetUpdatedAt, &targetTitle)
142154
if err != nil {
143155
slog.Warn("dream: target block not found", "target_id", link.TargetID)
144156
continue
@@ -154,6 +166,32 @@ func WriteLinks(ctx context.Context, pool *pgxpool.Pool, sourceID, sourceScope s
154166
continue
155167
}
156168

169+
// V8: Structural check for supersedes — 9B can't distinguish "complementary" from "replaces".
170+
// Deterministic pre-filter: same category + source older than target.
171+
if link.Relationship == "supersedes" {
172+
if srcCategory != targetCategory {
173+
slog.Debug("dream: supersedes rejected (different category)",
174+
"source_cat", srcCategory, "target_cat", targetCategory)
175+
continue
176+
}
177+
if !srcUpdatedAt.Before(targetUpdatedAt) {
178+
slog.Debug("dream: supersedes rejected (source not older)",
179+
"source_updated", srcUpdatedAt.Format("2006-01-02"),
180+
"target_updated", targetUpdatedAt.Format("2006-01-02"))
181+
continue
182+
}
183+
// Title similarity check via pg_trgm.
184+
var sim float64
185+
_ = tx.QueryRow(ctx,
186+
`SELECT similarity($1, $2)`, srcTitle, targetTitle,
187+
).Scan(&sim)
188+
if sim < 0.25 {
189+
slog.Debug("dream: supersedes rejected (low title similarity)",
190+
"similarity", sim, "source_title", srcTitle, "target_title", targetTitle)
191+
continue
192+
}
193+
}
194+
157195
// Weighted confidence: relationship_strength × source_quality × target_quality.
158196
weightedConfidence := link.Confidence * sourceQuality * targetQuality
159197
if math.IsNaN(weightedConfidence) || math.IsInf(weightedConfidence, 0) {

0 commit comments

Comments
 (0)