Unverified Commit 1021e76f authored by Cristian Maglie's avatar Cristian Maglie Committed by GitHub

Made `core search` results more similar to Arduino IDE 1.8.x search dialog (#1904)

* Factored function to get search terms

* Made 'core search' logic identical to Arduino IDE 1.8.x search dialog

* Drastically simplified search algorithm for libs

* Fixed SearchTermsFromQueryString function

* Moving SearchTermsFromQueryString into proper place
parent ce7b0620
......@@ -43,6 +43,16 @@ func removeDiatrics(s string) (string, error) {
return s, nil
}
// SearchTermsFromQueryString returns the terms inside the query string.
// All non alphanumeric characters (expect ':') are considered separators.
// All search terms are converted to lowercase.
func SearchTermsFromQueryString(query string) []string {
// Split on anything but 0-9, a-z or :
return strings.FieldsFunc(strings.ToLower(query), func(r rune) bool {
return !unicode.IsLetter(r) && !unicode.IsNumber(r) && r != ':'
})
}
// Match returns true if all substrings are contained in str.
// Both str and substrings are transforms to lower case and have their
// accents and other unicode diatrics removed.
......
......@@ -29,8 +29,6 @@ import (
// PlatformSearch FIXMEDOC
func PlatformSearch(req *rpc.PlatformSearchRequest) (*rpc.PlatformSearchResponse, error) {
searchArgs := strings.TrimSpace(req.SearchArgs)
allVersions := req.AllVersions
pme, release := commands.GetPackageManagerExplorer(req)
if pme == nil {
return nil, &arduino.InvalidInstanceError{}
......@@ -38,14 +36,14 @@ func PlatformSearch(req *rpc.PlatformSearchRequest) (*rpc.PlatformSearchResponse
defer release()
res := []*cores.PlatformRelease{}
if isUsb, _ := regexp.MatchString("[0-9a-f]{4}:[0-9a-f]{4}", searchArgs); isUsb {
vid, pid := searchArgs[:4], searchArgs[5:]
if isUsb, _ := regexp.MatchString("[0-9a-f]{4}:[0-9a-f]{4}", req.SearchArgs); isUsb {
vid, pid := req.SearchArgs[:4], req.SearchArgs[5:]
res = pme.FindPlatformReleaseProvidingBoardsWithVidPid(vid, pid)
} else {
searchArgs := utils.SearchTermsFromQueryString(req.SearchArgs)
allVersions := req.AllVersions
for _, targetPackage := range pme.GetPackages() {
for _, platform := range targetPackage.Platforms {
// discard invalid platforms
// Users can install platforms manually in the Sketchbook hardware folder,
// the core search command must operate only on platforms installed through
// the PlatformManager, thus we skip the manually installed ones.
......@@ -53,34 +51,32 @@ func PlatformSearch(req *rpc.PlatformSearchRequest) (*rpc.PlatformSearchResponse
continue
}
// discard invalid releases
platformRelease := platform.GetLatestRelease()
if platformRelease == nil {
// Discard platforms with no releases
latestRelease := platform.GetLatestRelease()
if latestRelease == nil {
continue
}
// Gather all strings that can be used for searching
toTest := []string{
platform.String(),
platform.Name,
platform.Architecture,
targetPackage.Name,
targetPackage.Maintainer,
targetPackage.WebsiteURL,
}
for _, board := range platformRelease.BoardsManifest {
toTest = append(toTest, board.Name)
toTest := platform.String() + " " +
platform.Name + " " +
platform.Architecture + " " +
targetPackage.Name + " " +
targetPackage.Maintainer + " " +
targetPackage.WebsiteURL
for _, board := range latestRelease.BoardsManifest {
toTest += board.Name + " "
}
// Search
if !utils.MatchAny(searchArgs, toTest) {
if !utils.Match(toTest, searchArgs) {
continue
}
if allVersions {
res = append(res, platform.GetAllReleases()...)
} else {
res = append(res, platformRelease)
res = append(res, latestRelease)
}
}
}
......
......@@ -17,11 +17,11 @@ package lib
import (
"context"
"strings"
"github.com/arduino/arduino-cli/arduino"
"github.com/arduino/arduino-cli/arduino/libraries/librariesindex"
"github.com/arduino/arduino-cli/arduino/libraries/librariesmanager"
"github.com/arduino/arduino-cli/arduino/utils"
"github.com/arduino/arduino-cli/commands"
rpc "github.com/arduino/arduino-cli/rpc/cc/arduino/cli/commands/v1"
semver "go.bug.st/relaxed-semver"
......@@ -38,42 +38,23 @@ func LibrarySearch(ctx context.Context, req *rpc.LibrarySearchRequest) (*rpc.Lib
func searchLibrary(req *rpc.LibrarySearchRequest, lm *librariesmanager.LibrariesManager) *rpc.LibrarySearchResponse {
res := []*rpc.SearchedLibrary{}
status := rpc.LibrarySearchStatus_LIBRARY_SEARCH_STATUS_SUCCESS
// Split on anything but 0-9, a-z or :
queryTerms := strings.FieldsFunc(strings.ToLower(req.GetQuery()), func(r rune) bool {
return !((r >= '0' && r <= '9') || (r >= 'a' && r <= 'z') || r == ':')
})
queryTerms := utils.SearchTermsFromQueryString(req.GetQuery())
for _, lib := range lm.Index.Libraries {
matchTerm := func(x string) bool {
if strings.Contains(strings.ToLower(lib.Name), x) ||
strings.Contains(strings.ToLower(lib.Latest.Paragraph), x) ||
strings.Contains(strings.ToLower(lib.Latest.Sentence), x) ||
strings.Contains(strings.ToLower(lib.Latest.Author), x) {
return true
}
for _, include := range lib.Latest.ProvidesIncludes {
if strings.Contains(strings.ToLower(include), x) {
return true
}
}
return false
}
match := func() bool {
for _, term := range queryTerms {
if !matchTerm(term) {
return false
}
}
return true
toTest := lib.Name + " " +
lib.Latest.Paragraph + " " +
lib.Latest.Sentence + " " +
lib.Latest.Author + " "
for _, include := range lib.Latest.ProvidesIncludes {
toTest += include + " "
}
if match() {
if utils.Match(toTest, queryTerms) {
res = append(res, indexLibraryToRPCSearchLibrary(lib))
}
}
return &rpc.LibrarySearchResponse{Libraries: res, Status: status}
return &rpc.LibrarySearchResponse{Libraries: res, Status: rpc.LibrarySearchStatus_LIBRARY_SEARCH_STATUS_SUCCESS}
}
// indexLibraryToRPCSearchLibrary converts a librariindex.Library to rpc.SearchLibrary
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment