From b12aada52d682c45aa1e66e13dc448dc894aee79 Mon Sep 17 00:00:00 2001 From: "Danilo M." Date: Thu, 1 Oct 2026 10:31:51 +0200 Subject: fix: double a quote in a search term, as notmuch expects SearchTerm::quote() escaped an embedded double quote with a backslash. notmuch has no backslash escape inside a quoted term: it doubles the quote, and a backslash-escaped one ENDS the term. Selected text holding a quote therefore let the rest of the selection reach the query as syntax. Measured on a throwaway index: under a `tag:nomatch and` scope, the backslash form of `x " or tag:inbox or id:"` matched every message, while the doubled form matched none. quote() now doubles the quote and leaves a backslash alone, since notmuch reads it literally. Truncation still runs first, so a cut cannot split a doubled pair. Co-Authored-By: Claude Opus 5.5 --- AGENTS.md | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) (limited to 'AGENTS.md') diff --git a/AGENTS.md b/AGENTS.md index 0697b20..8c4ebd7 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -472,9 +472,11 @@ labelled Sent that shows the whole Maildir. (`src/searchterm.h`), and that is what stops five surfaces growing five quoting rules.** It holds no widget, so the grammar is tested without a painter or a web engine. Two of its rules are load-bearing rather than cosmetic. `quote()` -escapes backslashes BEFORE quotes, since the other order escapes the -backslashes it just added; it truncates before escaping, so a cut cannot land -mid-escape. And `extend()` parenthesises BOTH sides, because the query bar can +DOUBLES an embedded quote, because notmuch has no backslash escape: a +backslash-escaped quote ends the term, and a selection holding +`x \" or tag:inbox or id:"` walked out of a `tag:nomatch and` scope and matched +every message, measured, where the doubled form matched none. It truncates +before doubling, so a cut cannot land mid-pair. And `extend()` parenthesises BOTH sides, because the query bar can hold a hand-written disjunction and `a or b AND c` binds as `a or (b AND c)`, which widens a search the user asked to narrow, reporting nothing. This is the same trap the `post-new` hook handles when it scopes a rule with `tag:new`. -- cgit v1.2.3