Switch to JaroWinkler distance and reweight package search scores (#2840)
fix(query): use JaroWinkler distance and reweight metric components Switch from Hamming to JaroWinkler distance for package name matching, as JaroWinkler handles variable-length strings and gives a prefix-match bonus better suited to package search. Reweight the score components from sim*0.50 + simDesc*0.20 + popularity*0.30 to sim*0.35 + simDesc*0.15 + popularity*0.50 to better surface popular packages when name similarity is moderate. Roll back the unreleased version target from 13.0.0 to 12.6.0 to align with the next minor release after v12.5.7. Fix scanner.Err() check in parseStdin to surface I/O errors that were previously silently dropped.
This commit is contained in:
7 files changed
+88
-14
No files matched your search
@@ -18,7 +18,7 @@ import (
|
||||
)
|
||||
|
||||
var (
|
||||
yayVersion = "13.0.0" // To be set by compiler.
|
||||
yayVersion = "12.6.0" // To be set by compiler.
|
||||
localePath = "/usr/share/locale" // To be set by compiler.
|
||||
)
|
||||
|
||||
|
||||
+1
-1
@@ -52,7 +52,7 @@ func (a *abstractResults) GetMetric(pkg *abstractResult) float64 {
|
||||
popularity = a.aurSortByMetric(pkg)
|
||||
}
|
||||
|
||||
sim = sim*0.5 + simDesc*0.2 + popularity*0.3
|
||||
sim = sim*0.35 + simDesc*0.15 + popularity*0.50
|
||||
|
||||
a.distanceCache[pkg.name] = sim
|
||||
|
||||
|
||||
@@ -181,7 +181,7 @@ func (s *SourceQueryBuilder) Execute(ctx context.Context, dbExecutor db.Executor
|
||||
|
||||
pkgS = RemoveInvalidTargets(s.logger, pkgS, s.targetMode)
|
||||
|
||||
metric := &metrics.Hamming{
|
||||
metric := &metrics.JaroWinkler{
|
||||
CaseSensitive: false,
|
||||
}
|
||||
|
||||
|
||||
@@ -567,13 +567,13 @@ func TestSourceQueryBuilderSortByFields(t *testing.T) {
|
||||
desc: "sort-by-metric topdown",
|
||||
sortBy: "",
|
||||
bottomUp: false,
|
||||
wantNames: []string{"yay", "yay-git", "ruby-yard"},
|
||||
wantNames: []string{"yay", "ruby-yard", "yay-git"},
|
||||
},
|
||||
{
|
||||
desc: "sort-by-metric bottomup",
|
||||
sortBy: "",
|
||||
bottomUp: true,
|
||||
wantNames: []string{"ruby-yard", "yay-git", "yay"},
|
||||
wantNames: []string{"yay-git", "ruby-yard", "yay"},
|
||||
},
|
||||
}
|
||||
|
||||
@@ -599,6 +599,76 @@ func TestSourceQueryBuilderSortByFields(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestSourceQueryBuilderChromeRanking(t *testing.T) {
|
||||
t.Parallel()
|
||||
|
||||
mockDB := &mock.DBExecutor{
|
||||
ReposFn: func() []string {
|
||||
return []string{"extra"}
|
||||
},
|
||||
SyncPackagesFn: func(pkgs ...string) []mock.IPackage {
|
||||
return nil
|
||||
},
|
||||
LocalPackageFn: func(string) mock.IPackage {
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
||||
mockAUR := &mockaur.MockAUR{
|
||||
GetFn: func(ctx context.Context, query *aur.Query) ([]aur.Pkg, error) {
|
||||
return []aur.Pkg{
|
||||
{
|
||||
Description: "The popular web browser by Google (Stable Channel)",
|
||||
Name: "google-chrome",
|
||||
NumVotes: 2351,
|
||||
Popularity: 13.24,
|
||||
PackageBase: "google-chrome",
|
||||
Version: "149.0.7827.53-1",
|
||||
},
|
||||
{
|
||||
Description: "Extract Android APKs for running in Chrome OS OR Chrome in OS X, Linux and Windows",
|
||||
Name: "chromeos-apk-git",
|
||||
NumVotes: 37,
|
||||
Popularity: 0.00,
|
||||
PackageBase: "chromeos-apk-git",
|
||||
Version: "20201218.r129.f13a94d-1",
|
||||
},
|
||||
{
|
||||
Description: "External extension updater for Chromium based browsers",
|
||||
Name: "chromexup",
|
||||
NumVotes: 5,
|
||||
Popularity: 0.00,
|
||||
PackageBase: "chromexup",
|
||||
Version: "0.5.4-5",
|
||||
},
|
||||
{
|
||||
Description: "Standalone server that implements the W3C WebDriver standard (for goog",
|
||||
Name: "chromedriver",
|
||||
NumVotes: 52,
|
||||
Popularity: 0.50,
|
||||
PackageBase: "chromedriver",
|
||||
Version: "149.0.7827.54-1",
|
||||
},
|
||||
}, nil
|
||||
},
|
||||
}
|
||||
|
||||
w := &strings.Builder{}
|
||||
queryBuilder := NewSourceQueryBuilder(mockAUR,
|
||||
text.NewLogger(w, io.Discard, strings.NewReader(""), false, "test"),
|
||||
"", parser.ModeAny, "", false,
|
||||
false, false)
|
||||
|
||||
queryBuilder.Execute(context.Background(), mockDB, []string{"chrome"})
|
||||
|
||||
gotNames := make([]string, len(queryBuilder.results))
|
||||
for i, result := range queryBuilder.results {
|
||||
gotNames[i] = result.name
|
||||
}
|
||||
|
||||
assert.Equal(t, []string{"google-chrome", "chromedriver", "chromeos-apk-git", "chromexup"}, gotNames)
|
||||
}
|
||||
|
||||
func newYayQueryBuilderMocks() (*mock.DBExecutor, *mockaur.MockAUR) {
|
||||
mockDB := &mock.DBExecutor{
|
||||
ReposFn: func() []string {
|
||||
|
||||
@@ -56,7 +56,7 @@ func (migration *configSortByMigration) Do(config *Configuration) bool {
|
||||
}
|
||||
|
||||
func (migration *configSortByMigration) TargetVersion() string {
|
||||
return "13.0.0"
|
||||
return "12.6.0"
|
||||
}
|
||||
|
||||
func DefaultMigrations() []configMigration {
|
||||
|
||||
@@ -188,37 +188,37 @@ func TestSortByMigration(t *testing.T) {
|
||||
{
|
||||
desc: "to upgrade",
|
||||
testConfig: &Configuration{
|
||||
Version: "12.9.0",
|
||||
Version: "12.5.7",
|
||||
SortBy: "name",
|
||||
},
|
||||
newVersion: "13.0.0",
|
||||
newVersion: "12.6.0",
|
||||
wantSave: true,
|
||||
},
|
||||
{
|
||||
desc: "to upgrade-git",
|
||||
testConfig: &Configuration{
|
||||
Version: "12.9.0.r7.g6f60892",
|
||||
Version: "12.3.0.r7.g6f60892",
|
||||
SortBy: "votes",
|
||||
},
|
||||
newVersion: "13.0.0",
|
||||
newVersion: "12.6.0",
|
||||
wantSave: true,
|
||||
},
|
||||
{
|
||||
desc: "to not upgrade",
|
||||
testConfig: &Configuration{
|
||||
Version: "12.9.0",
|
||||
Version: "12.2.0",
|
||||
SortBy: "",
|
||||
},
|
||||
newVersion: "13.0.0",
|
||||
newVersion: "12.6.0",
|
||||
wantSave: false,
|
||||
},
|
||||
{
|
||||
desc: "to not upgrade - target version",
|
||||
testConfig: &Configuration{
|
||||
Version: "13.0.0",
|
||||
Version: "12.6.0",
|
||||
SortBy: "name",
|
||||
},
|
||||
newVersion: "13.0.0",
|
||||
newVersion: "12.6.0",
|
||||
wantSave: false,
|
||||
},
|
||||
{
|
||||
|
||||
@@ -613,6 +613,10 @@ func (a *Arguments) parseStdin() error {
|
||||
a.AddTarget(scanner.Text())
|
||||
}
|
||||
|
||||
if err := scanner.Err(); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return os.Stdin.Close()
|
||||
}
|
||||
|
||||
|
||||
Reference in new issue
Block a user