image search test

This commit is contained in:
2026-09-16 11:52:35 +05:30
parent 42ea007fe7
commit 28af3e05f2
5 changed files with 181 additions and 6 deletions

View File

@@ -480,15 +480,33 @@ func scoreCachedHits(cached []repositories.CatalogueHit) []scoredHit {
return hits
}
// sortHits ranks by blended score, then by the model's own similarity, and
// only then by name. Name alone used to break every tie, which quietly made
// punctuation decide relevance: "Parle Monaco Classic" sorts above "Parle-G
// Original …" because a space precedes a hyphen in ASCII, so equal-scoring
// crackers beat the biscuit that was actually scanned.
func sortHits(hits []scoredHit) {
sort.SliceStable(hits, func(i, j int) bool {
if hits[i].score != hits[j].score {
return hits[i].score > hits[j].score
}
di, dj := vectorRank(hits[i].Distance), vectorRank(hits[j].Distance)
if di != dj {
return di < dj
}
return hits[i].ProductName < hits[j].ProductName
})
}
// vectorRank orders by cosine distance, nearest first, with a row the model
// never saw (-1, text-only) sorting behind every row it did.
func vectorRank(d float64) float64 {
if d < 0 {
return math.MaxFloat64
}
return d
}
func (s *scanService) modelName() string {
if s.embedder == nil {
return "none"
@@ -516,8 +534,20 @@ func textScore(h repositories.CatalogueHit, label string, tokens []string) float
name := strings.ToLower(h.ProductName)
hay := name + " " + strings.ToLower(h.Title)
label = strings.ToLower(strings.TrimSpace(label))
if label != "" && strings.Contains(name, label) {
return 0.95
// The substring test compares separator-folded forms, so the brand's own
// punctuation does not decide the match: "Parle G", "Parle-G" and
// "ParleG" all have to reach "Parle-G Original Glucose Biscuits".
if label != "" {
foldedName, foldedLabel := utils.FoldSeparators(name), utils.FoldSeparators(label)
if foldedLabel != "" && strings.Contains(foldedName, foldedLabel) {
return 0.95
}
// Separators dropped rather than folded. Only for a label long enough
// that a run of letters means something — "lay" inside "malayalam" is
// not a match anyone wants.
if tight := utils.TightenLabel(label); len(tight) >= 4 && strings.Contains(utils.TightenLabel(name), tight) {
return 0.95
}
}
if len(tokens) == 0 {
return 0