package storage import ( "strings" "unicode" ) // SearchWords splits what a user typed into a search box into the words // an index can match: runs of letters and digits, lower-cased, everything // else a separator. // // Both engines' query languages have operators — FTS5's quotes, AND, NEAR // and column filters, tsquery's & | ! and parentheses — and a search box is // not the place to expose them: a user searching for "C++ & Go" means the // words, not a malformed query. Reducing the term to words and building the // query from those is what makes any input safe to pass on. func SearchWords(term string) []string { fields := strings.FieldsFunc(term, func(r rune) bool { return !unicode.IsLetter(r) && !unicode.IsDigit(r) }) out := fields[:0] for _, f := range fields { out = append(out, strings.ToLower(f)) } return out }