mu-find: add --analyze option

For analyzing queries with the new query-parser.
This commit is contained in:
Dirk-Jan C. Binnema 2023-09-09 11:49:42 +03:00
parent a9bd6e69d3
commit f6122ecc9e
4 changed files with 43 additions and 25 deletions

View File

@ -119,7 +119,7 @@ entries are displayed.
** --summary-len=<number>
If > 0, use that number of lines of the message to provide a summary.
** --format=<plain|links|xquery|xml|sexp>
** --format=<plain|links|xml|sexp>
output results in the specified format:
@ -129,9 +129,7 @@ output results in the specified format:
information).
- *xml* formats the search results as XML.
- *sexp* formats the search results as an s-expression as used in Lisp programming
environments.
- *xquery* shows the Xapian query corresponding to your search terms. This is
meant for for debugging purposes.
environments
** --linksdir=<dir> and -c, --clearlinks
when using ~-format=links~, output the results as a maildir with symbolic links to
@ -215,6 +213,14 @@ not this may not really be the same message, if the message-id was copied.
The algorithm used for determining the threads is based on Jamie Zawinksi's
description: http://www.jwz.org/doc/threading.html
** -a,--analyze
instead of executing the query, analyze it by show the parse-tree s-expression
and a stringified version of the Xapian query. This can help users to determine
how ~mu~ interprets some query.
The output of this command are differ between versions, but should be helpful
nevertheless.
#+include: "muhome.inc" :minlevel 2
#+include: "common-options.inc" :minlevel 1

View File

@ -33,6 +33,7 @@
#include "mu-query-match-deciders.hh"
#include "mu-query.hh"
#include "mu-bookmarks.hh"
#include "mu-query-parser.hh"
#include "message/mu-message.hh"
#include "utils/mu-option.hh"
@ -61,12 +62,30 @@ using OutputFunc = std::function<Result<void>(const Option<Message>& msg, const
using Format = Options::Find::Format;
static Result<void>
print_internal(const Store& store,
const std::string& expr,
bool xapian,
bool warn)
analyze_query_expr(const Store& store, const std::string& expr, const Options& opts)
{
mu_println("{}", store.parse_query(expr, xapian));
auto print_item=[&](auto&&title, auto&&val) {
const auto blue{opts.nocolor ? "" : MU_COLOR_BLUE};
const auto green{opts.nocolor ? "" : MU_COLOR_GREEN};
const auto reset{opts.nocolor ? "" : MU_COLOR_DEFAULT};
mu_println("* {}{}{}:\n {}{}{}", blue, title, reset, green, val, reset);
};
print_item("query", expr);
const auto pq{parse_query(expr, false/*don't expand*/).to_string()};
const auto pqx{parse_query(expr, true/*do expand*/).to_string()};
print_item("parsed query", pq);
if (pq != pqx)
print_item("parsed query (expanded)", pqx);
auto xq{make_xapian_query(store, expr)};
if (!xq)
return Err(std::move(xq.error()));
print_item("Xapian query", xq->get_description());
return Ok();
}
@ -473,7 +492,7 @@ output_query_results(const QueryResults& qres, const Options& opts)
}
static Result<void>
process_query(const Store& store, const std::string& expr, const Options& opts)
process_store_query(const Store& store, const std::string& expr, const Options& opts)
{
auto qres{run_query(store, expr, opts)};
if (!qres)
@ -492,18 +511,14 @@ Mu::mu_cmd_find(const Store& store, const Options& opts)
if (!expr)
return Err(expr.error());
if (opts.find.format == Format::XQuery)
return print_internal(store, *expr, true, false);
else if (opts.find.format == Format::MQuery)
return print_internal(store, *expr, false, opts.verbose);
if (opts.find.analyze)
return analyze_query_expr(store, *expr, opts);
else
return process_query(store, *expr, opts);
return process_store_query(store, *expr, opts);
}
#ifdef BUILD_TESTS
/*
* Tests.

View File

@ -337,12 +337,6 @@ sub_find(CLI::App& sub, Options& opts)
{ Format::Json,
{"json", "JSON"}
},
{ Format::XQuery,
{"xquery", "Show Xapian query (for debugging)"}
},
{ Format::MQuery,
{"mquery", "Show mu query for (for debugging)"}
},
}};
sub.add_flag("--threads,-t", opts.find.threads,
@ -351,6 +345,8 @@ sub_find(CLI::App& sub, Options& opts)
"Show only one of messages with same message-id");
sub.add_flag("--include-related,-r", opts.find.include_related,
"Include related messages in results");
sub.add_flag("--analyze,-a", opts.find.analyze,
"Analyze the query");
const auto fhelp = options_help(FormatInfos, Format::Plain);
const auto fmap = options_map(FormatInfos);

View File

@ -143,11 +143,12 @@ struct Options {
bool reverse; /**< sort in revers order (z->a) */
bool threads; /**< show message threads */
bool clearlinks; /**< clear linksdir first */
std::string linksdir; /**< directory for links */
std::string linksdir; /**< directory for links */
OptSize summary_len; /**< max # of lines for summary */
std::string bookmark; /**< use bookmark */
bool analyze; /**< analyze query */
enum struct Format { Plain, Links, Xml, Json, Sexp, XQuery, MQuery, Exec };
enum struct Format { Plain, Links, Xml, Json, Sexp, Exec };
Format format; /**< Output format */
std::string exec; /**< cmd to execute on matches */
bool skip_dups; /**< show only first with msg id */