Support for partial queries in catalog search

The search text in the catalog query is interpreted as partial by
default, but partial query mode can be disabled in C++. The latter
possibility is not exposed via the /catalog/search kiwix-serve endpoint,
though.
This commit is contained in:
Veloman Yunkan 2021-03-10 16:18:43 +04:00 committed by Matthieu Gautier
parent 47c67a4202
commit 09233bf4f3
3 changed files with 11 additions and 4 deletions

View File

@ -59,6 +59,7 @@ class Filter {
std::string _creator; std::string _creator;
size_t _maxSize; size_t _maxSize;
std::string _query; std::string _query;
bool _queryIsPartial;
std::string _name; std::string _name;
public: public:
@ -103,11 +104,12 @@ class Filter {
Filter& publisher(std::string publisher); Filter& publisher(std::string publisher);
Filter& creator(std::string creator); Filter& creator(std::string creator);
Filter& maxSize(size_t size); Filter& maxSize(size_t size);
Filter& query(std::string query); Filter& query(std::string query, bool partial=true);
Filter& name(std::string name); Filter& name(std::string name);
bool hasQuery() const; bool hasQuery() const;
const std::string& getQuery() const { return _query; } const std::string& getQuery() const { return _query; }
bool queryIsPartial() const { return _queryIsPartial; }
bool accept(const Book& book) const; bool accept(const Book& book) const;
bool acceptByQueryOnly(const Book& book) const; bool acceptByQueryOnly(const Book& book) const;

View File

@ -296,6 +296,9 @@ Library::BookIdCollection Library::getBooksByTitleOrDescription(const Filter& fi
queryParser.set_default_op(Xapian::Query::OP_AND); queryParser.set_default_op(Xapian::Query::OP_AND);
queryParser.add_prefix("title", "S"); queryParser.add_prefix("title", "S");
queryParser.add_prefix("description", "XD"); queryParser.add_prefix("description", "XD");
const auto partialQueryFlag = filter.queryIsPartial()
? Xapian::QueryParser::FLAG_PARTIAL
: 0;
// Language assumed for the query is not known for sure so stemming // Language assumed for the query is not known for sure so stemming
// is not applied // is not applied
//queryParser.set_stemmer(Xapian::Stem(iso639_3ToXapian.at(???))); //queryParser.set_stemmer(Xapian::Stem(iso639_3ToXapian.at(???)));
@ -303,7 +306,8 @@ Library::BookIdCollection Library::getBooksByTitleOrDescription(const Filter& fi
const auto flags = Xapian::QueryParser::FLAG_PHRASE const auto flags = Xapian::QueryParser::FLAG_PHRASE
| Xapian::QueryParser::FLAG_BOOLEAN | Xapian::QueryParser::FLAG_BOOLEAN
| Xapian::QueryParser::FLAG_LOVEHATE | Xapian::QueryParser::FLAG_LOVEHATE
| Xapian::QueryParser::FLAG_WILDCARD; | Xapian::QueryParser::FLAG_WILDCARD
| partialQueryFlag;
const auto query = queryParser.parse_query(filter.getQuery(), flags); const auto query = queryParser.parse_query(filter.getQuery(), flags);
Xapian::Enquire enquire(m_bookDB); Xapian::Enquire enquire(m_bookDB);
enquire.set_query(query); enquire.set_query(query);
@ -561,9 +565,10 @@ Filter& Filter::maxSize(size_t maxSize)
return *this; return *this;
} }
Filter& Filter::query(std::string query) Filter& Filter::query(std::string query, bool partial)
{ {
_query = query; _query = query;
_queryIsPartial = partial;
activeFilters |= QUERY; activeFilters |= QUERY;
return *this; return *this;
} }

View File

@ -263,7 +263,7 @@ TEST_F(LibraryTest, filterCheck)
bookIds = lib.filter(kiwix::Filter().query("folklore")); bookIds = lib.filter(kiwix::Filter().query("folklore"));
EXPECT_EQ(bookIds.size(), 1U); EXPECT_EQ(bookIds.size(), 1U);
bookIds = lib.filter(kiwix::Filter().query("Wiki*")); bookIds = lib.filter(kiwix::Filter().query("Wiki"));
EXPECT_EQ(bookIds.size(), 4U); EXPECT_EQ(bookIds.size(), 4U);
bookIds = lib.filter(kiwix::Filter().query("Wiki").creator("Wiki")); bookIds = lib.filter(kiwix::Filter().query("Wiki").creator("Wiki"));