* Feature request: search for last N modified mails
@ 2016-12-02 14:01 Ico
2016-12-03 13:22 ` cesar mena
` (2 more replies)
0 siblings, 3 replies; 6+ messages in thread
From: Ico @ 2016-12-02 14:01 UTC (permalink / raw)
To: notmuch
My normal mail workflow is to keep todo's in my inbox; these can be a few days
or weeks old if I'm lazy. Every now and then I find myself accidentally
removing things from the inbox, and I have a very hard time finding things
back. As discussed on #notmuch IRC today: I'd like to request a feature for
searching for the last N modified mails, as notmuch already has this info in
the database.
bremner suggested this could be implemented using with a query like
lastmod:-10
14:39 < Zevv> basically, I'd like to be able to search for the last 10 modified
mails. Where 'modified' would probably mean changing tags
14:41 < bremner> Zevv: you can get the current value from notmuch count --lastmod '*'
14:41 < bremner> then basically every tag change increments it
14:42 < bremner> so I guess subtract 10 and search?
14:44 < Zevv> Hm that would make it hard to use it as a simple query for in alot
14:45 < bremner> yes.
14:45 < bremner> I never thought about it before, but it would be possible to
impliment lastmod:-10
14:47 < Zevv> that would be extremely handy
--
:wq
^X^Cy^K^X^C^C^C^C
^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: Feature request: search for last N modified mails
2016-12-02 14:01 Feature request: search for last N modified mails Ico
@ 2016-12-03 13:22 ` cesar mena
2022-08-08 11:50 ` [PATCH] WIP: provide relative lastmod sexp queries David Bremner
2022-09-03 11:51 ` Feature request: search for last N modified mails David Bremner
2 siblings, 0 replies; 6+ messages in thread
From: cesar mena @ 2016-12-03 13:22 UTC (permalink / raw)
To: Ico, notmuch
hello,
Ico <ico@pruts.nl> writes:
> My normal mail workflow is to keep todo's in my inbox; these can be a few days
> or weeks old if I'm lazy. Every now and then I find myself accidentally
> removing things from the inbox, and I have a very hard time finding things
> back. As discussed on #notmuch IRC today: I'd like to request a feature for
> searching for the last N modified mails, as notmuch already has this info in
> the database.
>
> bremner suggested this could be implemented using with a query like
>
> lastmod:-10
until such time you can consider using a 'done' tag that's muted.
-cm
^ permalink raw reply [flat|nested] 6+ messages in thread
* [PATCH] WIP: provide relative lastmod sexp queries
2016-12-02 14:01 Feature request: search for last N modified mails Ico
2016-12-03 13:22 ` cesar mena
@ 2022-08-08 11:50 ` David Bremner
2022-08-09 11:25 ` [PATCH 2/3] WIP/lib: factor out lastmod range handling from sexp parser David Bremner
2022-09-03 11:51 ` Feature request: search for last N modified mails David Bremner
2 siblings, 1 reply; 6+ messages in thread
From: David Bremner @ 2022-08-08 11:50 UTC (permalink / raw)
To: Ico, notmuch
---
I haven't looked carefully at how much work it would be to add to the
infix parser yet. I suspect it means adding a new RangeProcessor class
modelled on ParseTimeRangeProcessor. Maybe some of the logic from
_parse_sexp_range could be shared with the other parser.
lib/parse-sexp.cc | 6 ++++++
test/T570-revision-tracking.sh | 8 ++++++++
2 files changed, 14 insertions(+)
diff --git a/lib/parse-sexp.cc b/lib/parse-sexp.cc
index 0f14d8b7..e9ef4268 100644
--- a/lib/parse-sexp.cc
+++ b/lib/parse-sexp.cc
@@ -575,6 +575,9 @@ _sexp_parse_range (notmuch_database_t *notmuch, const _sexp_prefix_t *prefix,
return NOTMUCH_STATUS_BAD_QUERY_SYNTAX;
}
+ if (from_idx < 0)
+ from_idx += notmuch_database_get_revision (notmuch, NULL);
+
try {
if (EMPTY_STRING (to))
to_idx = LONG_MAX;
@@ -585,6 +588,9 @@ _sexp_parse_range (notmuch_database_t *notmuch, const _sexp_prefix_t *prefix,
return NOTMUCH_STATUS_BAD_QUERY_SYNTAX;
}
+ if (to_idx < 0)
+ to_idx += notmuch_database_get_revision (notmuch, NULL);
+
output = Xapian::Query (Xapian::Query::OP_VALUE_RANGE, NOTMUCH_VALUE_LAST_MOD,
Xapian::sortable_serialise (from_idx),
Xapian::sortable_serialise (to_idx));
diff --git a/test/T570-revision-tracking.sh b/test/T570-revision-tracking.sh
index e1cc684d..aaa45468 100755
--- a/test/T570-revision-tracking.sh
+++ b/test/T570-revision-tracking.sh
@@ -95,4 +95,12 @@ subtotal=$(notmuch count lastmod:..$lastmod)
result=$(($subtotal == $total-1))
test_expect_equal 1 "$result"
+if [ $NOTMUCH_HAVE_SFSEXP -eq 1 ]; then
+ test_begin_subtest 'exclude one message using negative lastmod (sexp)'
+ total=$(notmuch count '*')
+ notmuch tag +${RANDOM} id:4EFC743A.3060609@april.org
+ count=$(notmuch count --query=sexp '(lastmod -1 *)')
+ test_expect_equal 1 "$count"
+fi
+
test_done
--
2.35.2
^ permalink raw reply related [flat|nested] 6+ messages in thread
* [PATCH 2/3] WIP/lib: factor out lastmod range handling from sexp parser.
2022-08-08 11:50 ` [PATCH] WIP: provide relative lastmod sexp queries David Bremner
@ 2022-08-09 11:25 ` David Bremner
2022-08-09 11:25 ` [PATCH 3/3] WIP/lib: use common lastmod logic in infix parser David Bremner
0 siblings, 1 reply; 6+ messages in thread
From: David Bremner @ 2022-08-09 11:25 UTC (permalink / raw)
To: David Bremner, Ico, notmuch
This will permit the re-use of the same logic in the infix query
parser. The location of the shared code in the infix side is just a
convention at this point.
---
lib/Makefile.local | 3 +-
lib/database-private.h | 6 ++++
lib/lastmod-fp.cc | 68 ++++++++++++++++++++++++++++++++++++++++++
lib/parse-sexp.cc | 37 ++++-------------------
4 files changed, 82 insertions(+), 32 deletions(-)
create mode 100644 lib/lastmod-fp.cc
diff --git a/lib/Makefile.local b/lib/Makefile.local
index 6d67a2a4..4e766305 100644
--- a/lib/Makefile.local
+++ b/lib/Makefile.local
@@ -65,7 +65,8 @@ libnotmuch_cxx_srcs = \
$(dir)/open.cc \
$(dir)/init.cc \
$(dir)/parse-sexp.cc \
- $(dir)/sexp-fp.cc
+ $(dir)/sexp-fp.cc \
+ $(dir)/lastmod-fp.cc
libnotmuch_modules := $(libnotmuch_c_srcs:.c=.o) $(libnotmuch_cxx_srcs:.cc=.o)
diff --git a/lib/database-private.h b/lib/database-private.h
index 419b9fe6..b9be4e22 100644
--- a/lib/database-private.h
+++ b/lib/database-private.h
@@ -381,5 +381,11 @@ _notmuch_sexp_string_to_xapian_query (notmuch_database_t *notmuch, const char *q
notmuch_status_t
_notmuch_date_strings_to_query (Xapian::valueno slot, const std::string &from, const std::string &to,
Xapian::Query &output, std::string &msg);
+
+/* lastmod-fp.h */
+notmuch_status_t
+_notmuch_lastmod_strings_to_query (notmuch_database_t *notmuch,
+ const std::string &from, const std::string &to,
+ Xapian::Query &output, std::string &msg);
#endif
#endif
diff --git a/lib/lastmod-fp.cc b/lib/lastmod-fp.cc
new file mode 100644
index 00000000..5fdaf281
--- /dev/null
+++ b/lib/lastmod-fp.cc
@@ -0,0 +1,68 @@
+/* lastmod-fp.cc - lastmod range query glue
+ *
+ * This file is part of notmuch.
+ *
+ * Copyright © 2022 David Bremner
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see https://www.gnu.org/licenses/ .
+ *
+ * Author: David Bremner <david@tethera.net>
+ */
+
+#include "database-private.h"
+
+notmuch_status_t
+_notmuch_lastmod_strings_to_query (notmuch_database_t *notmuch,
+ const std::string &from, const std::string &to,
+ Xapian::Query &output, std::string &msg)
+{
+ long from_idx = 0L, to_idx = LONG_MAX;
+ long current;
+ std::string str;
+
+ /* revision should not change, but for the avoidance of doubt,
+ * grab for both ends of range, if needed*/
+ current = notmuch_database_get_revision (notmuch, NULL);
+
+ try {
+ if (from.empty ())
+ from_idx = 0L;
+ else
+ from_idx = std::stol (from);
+ } catch (std::logic_error &e) {
+ msg = "bad 'from' revision: '" + from + "'";
+ return NOTMUCH_STATUS_BAD_QUERY_SYNTAX;
+ }
+
+ if (from_idx < 0)
+ from_idx += current;
+
+ try {
+ if (EMPTY_STRING (to))
+ to_idx = LONG_MAX;
+ else
+ to_idx = std::stol (to);
+ } catch (std::logic_error &e) {
+ msg = "bad 'to' revision: '" + to + "'";
+ return NOTMUCH_STATUS_BAD_QUERY_SYNTAX;
+ }
+
+ if (to_idx < 0)
+ to_idx += current;
+
+ output = Xapian::Query (Xapian::Query::OP_VALUE_RANGE, NOTMUCH_VALUE_LAST_MOD,
+ Xapian::sortable_serialise (from_idx),
+ Xapian::sortable_serialise (to_idx));
+ return NOTMUCH_STATUS_SUCCESS;
+}
diff --git a/lib/parse-sexp.cc b/lib/parse-sexp.cc
index e9ef4268..9cadbc13 100644
--- a/lib/parse-sexp.cc
+++ b/lib/parse-sexp.cc
@@ -563,38 +563,13 @@ _sexp_parse_range (notmuch_database_t *notmuch, const _sexp_prefix_t *prefix,
}
if (strcmp (prefix->name, "lastmod") == 0) {
- long from_idx, to_idx;
-
- try {
- if (EMPTY_STRING (from))
- from_idx = 0L;
- else
- from_idx = std::stol (from);
- } catch (std::logic_error &e) {
- _notmuch_database_log (notmuch, "bad 'from' revision: '%s'\n", from);
- return NOTMUCH_STATUS_BAD_QUERY_SYNTAX;
- }
-
- if (from_idx < 0)
- from_idx += notmuch_database_get_revision (notmuch, NULL);
-
- try {
- if (EMPTY_STRING (to))
- to_idx = LONG_MAX;
- else
- to_idx = std::stol (to);
- } catch (std::logic_error &e) {
- _notmuch_database_log (notmuch, "bad 'to' revision: '%s'\n", to);
- return NOTMUCH_STATUS_BAD_QUERY_SYNTAX;
+ notmuch_status_t status;
+ status = _notmuch_lastmod_strings_to_query (notmuch, from, to, output, msg);
+ if (status) {
+ if (! msg.empty ())
+ _notmuch_database_log (notmuch, "%s\n", msg.c_str ());
}
-
- if (to_idx < 0)
- to_idx += notmuch_database_get_revision (notmuch, NULL);
-
- output = Xapian::Query (Xapian::Query::OP_VALUE_RANGE, NOTMUCH_VALUE_LAST_MOD,
- Xapian::sortable_serialise (from_idx),
- Xapian::sortable_serialise (to_idx));
- return NOTMUCH_STATUS_SUCCESS;
+ return status;
}
_notmuch_database_log (notmuch, "unimplimented range prefix: '%s'\n", prefix->name);
--
2.35.2
\r
^ permalink raw reply related [flat|nested] 6+ messages in thread
* [PATCH 3/3] WIP/lib: use common lastmod logic in infix parser
2022-08-09 11:25 ` [PATCH 2/3] WIP/lib: factor out lastmod range handling from sexp parser David Bremner
@ 2022-08-09 11:25 ` David Bremner
0 siblings, 0 replies; 6+ messages in thread
From: David Bremner @ 2022-08-09 11:25 UTC (permalink / raw)
To: David Bremner, Ico, notmuch
This allows the support of negative lastmod revisions to be
interpreted as relative to the most recent revision.
---
lib/lastmod-fp.cc | 15 +++++++++++++
lib/lastmod-fp.h | 39 ++++++++++++++++++++++++++++++++++
lib/open.cc | 4 ++--
test/T570-revision-tracking.sh | 6 ++++++
4 files changed, 62 insertions(+), 2 deletions(-)
create mode 100644 lib/lastmod-fp.h
diff --git a/lib/lastmod-fp.cc b/lib/lastmod-fp.cc
index 5fdaf281..f85efd28 100644
--- a/lib/lastmod-fp.cc
+++ b/lib/lastmod-fp.cc
@@ -21,6 +21,7 @@
*/
#include "database-private.h"
+#include "lastmod-fp.h"
notmuch_status_t
_notmuch_lastmod_strings_to_query (notmuch_database_t *notmuch,
@@ -66,3 +67,17 @@ _notmuch_lastmod_strings_to_query (notmuch_database_t *notmuch,
Xapian::sortable_serialise (to_idx));
return NOTMUCH_STATUS_SUCCESS;
}
+
+Xapian::Query
+LastModRangeProcessor::operator() (const std::string &begin, const std::string &end)
+{
+
+ Xapian::Query output;
+ std::string msg;
+
+ if (_notmuch_lastmod_strings_to_query (notmuch, begin, end, output, msg))
+ throw Xapian::QueryParserError (msg);
+
+ return output;
+}
+
diff --git a/lib/lastmod-fp.h b/lib/lastmod-fp.h
new file mode 100644
index 00000000..448241f8
--- /dev/null
+++ b/lib/lastmod-fp.h
@@ -0,0 +1,39 @@
+/* lastmod-fp.h - database revision query glue
+ *
+ * This file is part of notmuch.
+ *
+ * Copyright © 2022 David Bremner
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see https://www.gnu.org/licenses/ .
+ *
+ * Author: David Bremner <david@tethera.net>
+ */
+
+#ifndef NOTMUCH_LASTMOD_FP_H
+#define NOTMUCH_LASTMOD_FP_H
+
+#include <xapian.h>
+
+class LastModRangeProcessor : public Xapian::RangeProcessor {
+protected:
+ notmuch_database_t *notmuch;
+
+public:
+ LastModRangeProcessor (notmuch_database_t *notmuch_, const std::string prefix_)
+ : Xapian::RangeProcessor(NOTMUCH_VALUE_LAST_MOD, prefix_, 0), notmuch(notmuch_) { }
+
+ Xapian::Query operator() (const std::string &begin, const std::string &end);
+};
+
+#endif /* NOTMUCH_LASTMOD_FP_H */
diff --git a/lib/open.cc b/lib/open.cc
index 30cfcf9e..02ed7285 100644
--- a/lib/open.cc
+++ b/lib/open.cc
@@ -3,6 +3,7 @@
#include "database-private.h"
#include "parse-time-vrp.h"
+#include "lastmod-fp.h"
#include "path-util.h"
#if HAVE_XAPIAN_DB_RETRY_LOCK
@@ -431,8 +432,7 @@ _finish_open (notmuch_database_t *notmuch,
notmuch->value_range_processor = new Xapian::NumberRangeProcessor (NOTMUCH_VALUE_TIMESTAMP);
notmuch->date_range_processor = new ParseTimeRangeProcessor (NOTMUCH_VALUE_TIMESTAMP,
"date:");
- notmuch->last_mod_range_processor = new Xapian::NumberRangeProcessor (NOTMUCH_VALUE_LAST_MOD,
- "lastmod:");
+ notmuch->last_mod_range_processor = new LastModRangeProcessor (notmuch, "lastmod:");
notmuch->query_parser->set_default_op (Xapian::Query::OP_AND);
notmuch->query_parser->set_database (*notmuch->xapian_db);
notmuch->stemmer = new Xapian::Stem ("english");
diff --git a/test/T570-revision-tracking.sh b/test/T570-revision-tracking.sh
index aaa45468..067935b2 100755
--- a/test/T570-revision-tracking.sh
+++ b/test/T570-revision-tracking.sh
@@ -103,4 +103,10 @@ if [ $NOTMUCH_HAVE_SFSEXP -eq 1 ]; then
test_expect_equal 1 "$count"
fi
+test_begin_subtest 'exclude one message using negative lastmod'
+total=$(notmuch count '*')
+notmuch tag +${RANDOM} id:4EFC743A.3060609@april.org
+count=$(notmuch count lastmod:-1..)
+test_expect_equal 1 "$count"
+
test_done
--
2.35.2
\r
^ permalink raw reply related [flat|nested] 6+ messages in thread
* Re: Feature request: search for last N modified mails
2016-12-02 14:01 Feature request: search for last N modified mails Ico
2016-12-03 13:22 ` cesar mena
2022-08-08 11:50 ` [PATCH] WIP: provide relative lastmod sexp queries David Bremner
@ 2022-09-03 11:51 ` David Bremner
2 siblings, 0 replies; 6+ messages in thread
From: David Bremner @ 2022-09-03 11:51 UTC (permalink / raw)
To: Ico, notmuch
Ico <ico@pruts.nl> writes:
> My normal mail workflow is to keep todo's in my inbox; these can be a few days
> or weeks old if I'm lazy. Every now and then I find myself accidentally
> removing things from the inbox, and I have a very hard time finding things
> back. As discussed on #notmuch IRC today: I'd like to request a feature for
> searching for the last N modified mails, as notmuch already has this info in
> the database.
>
> bremner suggested this could be implemented using with a query like
>
> lastmod:-10
>
>
>
> 14:39 < Zevv> basically, I'd like to be able to search for the last 10 modified
> mails. Where 'modified' would probably mean changing tags
> 14:41 < bremner> Zevv: you can get the current value from notmuch count --lastmod '*'
> 14:41 < bremner> then basically every tag change increments it
> 14:42 < bremner> so I guess subtract 10 and search?
> 14:44 < Zevv> Hm that would make it hard to use it as a simple query for in alot
> 14:45 < bremner> yes.
> 14:45 < bremner> I never thought about it before, but it would be possible to
> impliment lastmod:-10
> 14:47 < Zevv> that would be extremely handy
The syntax lastmod:-10.. (or '(lastmod -10 *)' is now supported in git
master.
^ permalink raw reply [flat|nested] 6+ messages in thread
end of thread, other threads:[~2022-09-03 11:51 UTC | newest]
Thread overview: 6+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2016-12-02 14:01 Feature request: search for last N modified mails Ico
2016-12-03 13:22 ` cesar mena
2022-08-08 11:50 ` [PATCH] WIP: provide relative lastmod sexp queries David Bremner
2022-08-09 11:25 ` [PATCH 2/3] WIP/lib: factor out lastmod range handling from sexp parser David Bremner
2022-08-09 11:25 ` [PATCH 3/3] WIP/lib: use common lastmod logic in infix parser David Bremner
2022-09-03 11:51 ` Feature request: search for last N modified mails David Bremner
Code repositories for project(s) associated with this public inbox
https://yhetil.org/notmuch.git/
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).