Akonadi Search

collectionquery.cpp
1 /*
2  * This file is part of the KDE Akonadi Search Project
3  * SPDX-FileCopyrightText: 2014 Christian Mollekopf <[email protected]>
4  *
5  * SPDX-License-Identifier: LGPL-2.1-only OR LGPL-3.0-only OR LicenseRef-KDE-Accepted-LGPL
6  *
7  */
8 
9 #include <xapian.h>
10 
11 #include "akonadi_search_pim_debug.h"
12 #include "collectionquery.h"
13 #include "resultiterator_p.h"
14 #include <QFile>
15 #include <QList>
16 
17 #include <QStandardPaths>
18 
19 using namespace Akonadi::Search::PIM;
20 
21 class Akonadi::Search::PIM::CollectionQueryPrivate
22 {
23 public:
24  QStringList ns;
26  QString nameString;
27  QString identifierString;
28  QString pathString;
29  QString databaseDir;
30  int limit;
31 };
32 
33 CollectionQuery::CollectionQuery()
34  : Query()
35  , d(new CollectionQueryPrivate)
36 {
37  d->databaseDir = defaultLocation(QStringLiteral("collections"));
38  d->limit = 0;
39 }
40 
41 CollectionQuery::~CollectionQuery() = default;
42 
43 void CollectionQuery::setDatabaseDir(const QString &dir)
44 {
45  d->databaseDir = dir;
46 }
47 
48 void CollectionQuery::nameMatches(const QString &match)
49 {
50  d->nameString = match;
51 }
52 
53 void CollectionQuery::identifierMatches(const QString &match)
54 {
55  d->identifierString = match;
56 }
57 
58 void CollectionQuery::pathMatches(const QString &match)
59 {
60  d->pathString = match;
61 }
62 
63 void CollectionQuery::setNamespace(const QStringList &ns)
64 {
65  d->ns = ns;
66 }
67 
68 void CollectionQuery::setMimetype(const QStringList &mt)
69 {
70  d->mimeType = mt;
71 }
72 
73 void CollectionQuery::setLimit(int limit)
74 {
75  d->limit = limit;
76 }
77 
78 ResultIterator CollectionQuery::exec()
79 {
80  Xapian::Database db;
81  try {
82  db = Xapian::Database(QFile::encodeName(d->databaseDir).toStdString());
83  } catch (const Xapian::DatabaseError &e) {
84  qCWarning(AKONADI_SEARCH_PIM_LOG) << "Failed to open Xapian database:" << d->databaseDir << "; error:" << QString::fromStdString(e.get_error_string());
85  return {};
86  }
87 
88  QList<Xapian::Query> queries;
89 
90  if (!d->nameString.isEmpty()) {
91  // qDebug() << "searching by name";
92  Xapian::QueryParser parser;
93  parser.set_database(db);
94  parser.add_prefix("", "N");
95  parser.set_default_op(Xapian::Query::OP_AND);
96  queries << parser.parse_query(d->nameString.toStdString(), Xapian::QueryParser::FLAG_PARTIAL);
97  }
98 
99  if (!d->identifierString.isEmpty()) {
100  Xapian::QueryParser parser;
101  parser.set_database(db);
102  parser.add_prefix("", "I");
103  parser.set_default_op(Xapian::Query::OP_AND);
104  queries << parser.parse_query(d->identifierString.toStdString(), Xapian::QueryParser::FLAG_PARTIAL);
105  }
106 
107  if (!d->pathString.isEmpty()) {
108  Xapian::QueryParser parser;
109  parser.set_database(db);
110  parser.add_prefix("", "P");
111  parser.set_default_op(Xapian::Query::OP_AND);
112  queries << parser.parse_query(d->pathString.toStdString(), Xapian::QueryParser::FLAG_PARTIAL | Xapian::QueryParser::FLAG_PHRASE);
113  }
114 
115  if (!d->ns.isEmpty()) {
116  QList<Xapian::Query> queryList;
117  queryList.reserve(d->ns.count());
118  for (const QString &n : std::as_const(d->ns)) {
119  const QByteArray term = "NS" + n.toUtf8();
120  queryList << Xapian::Query(term.constData());
121  }
122  queries << Xapian::Query(Xapian::Query::OP_OR, queryList.begin(), queryList.end());
123  }
124 
125  if (!d->mimeType.isEmpty()) {
126  QList<Xapian::Query> queryList;
127  queryList.reserve(d->mimeType.count());
128  for (const QString &n : std::as_const(d->mimeType)) {
129  const QByteArray term = "M" + n.toUtf8();
130  queryList << Xapian::Query(term.constData());
131  }
132  queries << Xapian::Query(Xapian::Query::OP_OR, queryList.begin(), queryList.end());
133  }
134 
135  Xapian::Query query = Xapian::Query(Xapian::Query::OP_AND, queries.begin(), queries.end());
136 
137  if (d->limit == 0) {
138  d->limit = 1000000;
139  }
140 
141  Xapian::Enquire enquire(db);
142  enquire.set_query(query);
143 
144  Xapian::MSet mset = enquire.get_mset(0, d->limit);
145 
146  ResultIterator iter;
147  iter.d->init(mset);
148  return iter;
149 }
QByteArray encodeName(const QString &fileName)
KCALUTILS_EXPORT QString mimeType()
void reserve(int alloc)
std::string toStdString() const const
QString fromStdString(const std::string &str)
Query base class.
Definition: lib/query.h:23
PIM specific search API.
const char * constData() const const
QList::iterator begin()
QList::iterator end()
This file is part of the KDE documentation.
Documentation copyright © 1996-2023 The KDE developers.
Generated on Wed Nov 29 2023 04:08:49 by doxygen 1.8.17 written by Dimitri van Heesch, © 1997-2006

KDE's Doxygen guidelines are available online.