Skip to content

Commit

Permalink
xapian_wrap.cpp: support phrase search for email addresses
Browse files Browse the repository at this point in the history
Quotes signify phrase search in free text queries but were
not supported in email queries since we supported querying
for sub-parts of an email address. This reintroduces phrase
search for email queries.
  • Loading branch information
rsto committed Jan 10, 2025
1 parent fb218d0 commit 7d207b2
Show file tree
Hide file tree
Showing 2 changed files with 27 additions and 2 deletions.
15 changes: 15 additions & 0 deletions cassandane/tiny-tests/JMAPEmail/email_query_emailaddress
Original file line number Diff line number Diff line change
Expand Up @@ -180,6 +180,21 @@ EOF
}, {
to => decode('utf-8', 'Dømi <*@*dømi.fo>'),
wantIds => [$ids[4]],
}, {
to => '[email protected]',
wantIds => [$ids[0]],
}, {
to => 'Jon Doe <[email protected]>',
wantIds => [$ids[0]],
}, {
to => '"[email protected]"',
wantIds => [$ids[0]],
}, {
to => '"Jon Doe <[email protected]>"',
wantIds => [$ids[0]],
}, {
to => '"foo*@*example.com"',
wantIds => [],
});

foreach (@tests) {
Expand Down
14 changes: 12 additions & 2 deletions imap/xapian_wrap.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1632,6 +1632,7 @@ static Xapian::Query *query_new_email(const xapian_db_t *db,
const char *searchstr)
{
std::string prefix(get_term_prefix(partnum));
bool is_phrase_query = false;

unsigned queryflags =
Xapian::QueryParser::FLAG_PHRASE | Xapian::QueryParser::FLAG_WILDCARD;
Expand All @@ -1641,6 +1642,14 @@ static Xapian::Query *query_new_email(const xapian_db_t *db,
db->parser->set_stemming_strategy(Xapian::QueryParser::STEM_NONE);

std::string str = Xapian::Unicode::tolower(searchstr);
// Remove enclosing phrase search quotes, if any.
if (str.size() >= 2 && str.front() == '"' && str.back() == '"') {
str.erase(str.end() - 1);
str.erase(str.begin());
if (str.empty()) return NULL;
is_phrase_query = true;
}

size_t atsign_pos = str.find('@');

if (atsign_pos == std::string::npos || atsign_pos == str.length() - 1) {
Expand All @@ -1660,7 +1669,8 @@ static Xapian::Query *query_new_email(const xapian_db_t *db,
email.append(str, 0, atsign_pos);
}

if (!email.empty() && email[email.length() - 1] == '*') {
if (!is_phrase_query &&
!email.empty() && email[email.length() - 1] == '*') {
wildcard_localpart = true;
email.erase(email.length() - 1, 1);
}
Expand All @@ -1682,7 +1692,7 @@ static Xapian::Query *query_new_email(const xapian_db_t *db,
bool subdomain_only = false;
std::string domain(str, atsign_pos + 1);

if (domain.length() && domain[0] == '*') {
if (!is_phrase_query && domain.length() && domain[0] == '*') {
wildcard_domain = true;
domain.erase(0, 1);
if (domain.length() && domain[0] == '.') {
Expand Down

0 comments on commit 7d207b2

Please sign in to comment.