summaryrefslogtreecommitdiffstats
path: root/common/datastorequery.cpp
diff options
context:
space:
mode:
authorChristian Mollekopf <chrigi_1@fastmail.fm>2016-10-18 12:44:12 +0200
committerChristian Mollekopf <chrigi_1@fastmail.fm>2016-10-21 09:18:49 +0200
commit71a0167e0216f84588b492c84e92667847fbe5a5 (patch)
tree016718fe0ab13359e9738b9ddbf2450b05bb4603 /common/datastorequery.cpp
parent2a9c738b813133d398683596df6d41d355e3cb3b (diff)
downloadsink-71a0167e0216f84588b492c84e92667847fbe5a5.tar.gz
sink-71a0167e0216f84588b492c84e92667847fbe5a5.zip
Use the ApplicationDomainType in the queries as well.
We have to access properties, so we need the mapper anyways, and the ApplicationDomainType type shouldn't be a large overhead anyways.
Diffstat (limited to 'common/datastorequery.cpp')
-rw-r--r--common/datastorequery.cpp94
1 files changed, 42 insertions, 52 deletions
diff --git a/common/datastorequery.cpp b/common/datastorequery.cpp
index 8897c29..f56ac91 100644
--- a/common/datastorequery.cpp
+++ b/common/datastorequery.cpp
@@ -19,8 +19,6 @@
19#include "datastorequery.h" 19#include "datastorequery.h"
20 20
21#include "log.h" 21#include "log.h"
22#include "entitybuffer.h"
23#include "entity_generated.h"
24#include "applicationdomaintype.h" 22#include "applicationdomaintype.h"
25 23
26#include "folder.h" 24#include "folder.h"
@@ -68,8 +66,8 @@ class Source : public FilterBase {
68 if (mIt == mIds.constEnd()) { 66 if (mIt == mIds.constEnd()) {
69 return false; 67 return false;
70 } 68 }
71 readEntity(*mIt, [callback](const QByteArray &uid, const Sink::EntityBuffer &entityBuffer) { 69 readEntity(*mIt, [callback](const Sink::ApplicationDomain::ApplicationDomainType &entity, Sink::Operation operation) {
72 callback({uid, entityBuffer, entityBuffer.operation()}); 70 callback({entity, operation});
73 }); 71 });
74 mIt++; 72 mIt++;
75 return mIt != mIds.constEnd(); 73 return mIt != mIds.constEnd();
@@ -110,23 +108,23 @@ public:
110 bool next(const std::function<void(const ResultSet::Result &result)> &callback) Q_DECL_OVERRIDE { 108 bool next(const std::function<void(const ResultSet::Result &result)> &callback) Q_DECL_OVERRIDE {
111 bool foundValue = false; 109 bool foundValue = false;
112 while(!foundValue && mSource->next([this, callback, &foundValue](const ResultSet::Result &result) { 110 while(!foundValue && mSource->next([this, callback, &foundValue](const ResultSet::Result &result) {
113 SinkTrace() << "Filter: " << result.uid << result.operation; 111 SinkTrace() << "Filter: " << result.entity.identifier() << result.operation;
114 112
115 //Always accept removals. They can't match the filter since the data is gone. 113 //Always accept removals. They can't match the filter since the data is gone.
116 if (result.operation == Sink::Operation_Removal) { 114 if (result.operation == Sink::Operation_Removal) {
117 SinkTrace() << "Removal: " << result.uid << result.operation; 115 SinkTrace() << "Removal: " << result.entity.identifier() << result.operation;
118 callback(result); 116 callback(result);
119 foundValue = true; 117 foundValue = true;
120 } else if (matchesFilter(result.uid, result.buffer)) { 118 } else if (matchesFilter(result.entity)) {
121 SinkTrace() << "Accepted: " << result.uid << result.operation; 119 SinkTrace() << "Accepted: " << result.entity.identifier() << result.operation;
122 callback(result); 120 callback(result);
123 foundValue = true; 121 foundValue = true;
124 //TODO if something did not match the filter so far but does now, turn into an add operation. 122 //TODO if something did not match the filter so far but does now, turn into an add operation.
125 } else { 123 } else {
126 SinkTrace() << "Rejected: " << result.uid << result.operation; 124 SinkTrace() << "Rejected: " << result.entity.identifier() << result.operation;
127 //TODO emit a removal if we had the uid in the result set and this is a modification. 125 //TODO emit a removal if we had the uid in the result set and this is a modification.
128 //We don't know if this results in a removal from the dataset, so we emit a removal notification anyways 126 //We don't know if this results in a removal from the dataset, so we emit a removal notification anyways
129 callback({result.uid, result.buffer, Sink::Operation_Removal, result.aggregateValues}); 127 callback({result.entity, Sink::Operation_Removal, result.aggregateValues});
130 } 128 }
131 return false; 129 return false;
132 })) 130 }))
@@ -134,9 +132,9 @@ public:
134 return foundValue; 132 return foundValue;
135 } 133 }
136 134
137 bool matchesFilter(const QByteArray &uid, const Sink::EntityBuffer &entityBuffer) { 135 bool matchesFilter(const ApplicationDomain::ApplicationDomainType &entity) {
138 for (const auto &filterProperty : propertyFilter.keys()) { 136 for (const auto &filterProperty : propertyFilter.keys()) {
139 const auto property = getProperty(entityBuffer.entity(), filterProperty); 137 const auto property = entity.getProperty(filterProperty);
140 const auto comparator = propertyFilter.value(filterProperty); 138 const auto comparator = propertyFilter.value(filterProperty);
141 if (!comparator.matches(property)) { 139 if (!comparator.matches(property)) {
142 SinkTrace() << "Filtering entity due to property mismatch on filter: " << filterProperty << property << ":" << comparator.value; 140 SinkTrace() << "Filtering entity due to property mismatch on filter: " << filterProperty << property << ":" << comparator.value;
@@ -224,7 +222,7 @@ public:
224 bool next(const std::function<void(const ResultSet::Result &)> &callback) Q_DECL_OVERRIDE { 222 bool next(const std::function<void(const ResultSet::Result &)> &callback) Q_DECL_OVERRIDE {
225 bool foundValue = false; 223 bool foundValue = false;
226 while(!foundValue && mSource->next([this, callback, &foundValue](const ResultSet::Result &result) { 224 while(!foundValue && mSource->next([this, callback, &foundValue](const ResultSet::Result &result) {
227 auto reductionValue = getProperty(result.buffer.entity(), mReductionProperty); 225 auto reductionValue = result.entity.getProperty(mReductionProperty);
228 if (!mReducedValues.contains(getByteArray(reductionValue))) { 226 if (!mReducedValues.contains(getByteArray(reductionValue))) {
229 //Only reduce every value once. 227 //Only reduce every value once.
230 mReducedValues.insert(getByteArray(reductionValue)); 228 mReducedValues.insert(getByteArray(reductionValue));
@@ -234,18 +232,18 @@ public:
234 232
235 QVariantList list; 233 QVariantList list;
236 for (const auto r : results) { 234 for (const auto r : results) {
237 readEntity(r, [&, this](const QByteArray &uid, const Sink::EntityBuffer &entityBuffer) { 235 readEntity(r, [&, this](const Sink::ApplicationDomain::ApplicationDomainType &entity, Sink::Operation operation) {
238 for (auto &aggregator : mAggregators) { 236 for (auto &aggregator : mAggregators) {
239 if (!aggregator.property.isEmpty()) { 237 if (!aggregator.property.isEmpty()) {
240 aggregator.process(getProperty(entityBuffer.entity(), aggregator.property)); 238 aggregator.process(entity.getProperty(aggregator.property));
241 } else { 239 } else {
242 aggregator.process(); 240 aggregator.process();
243 } 241 }
244 } 242 }
245 auto selectionValue = getProperty(entityBuffer.entity(), mSelectionProperty); 243 auto selectionValue = entity.getProperty(mSelectionProperty);
246 if (!selectionResultValue.isValid() || compare(selectionValue, selectionResultValue, mSelectionComparator)) { 244 if (!selectionResultValue.isValid() || compare(selectionValue, selectionResultValue, mSelectionComparator)) {
247 selectionResultValue = selectionValue; 245 selectionResultValue = selectionValue;
248 selectionResult = uid; 246 selectionResult = entity.identifier();
249 } 247 }
250 }); 248 });
251 } 249 }
@@ -255,8 +253,8 @@ public:
255 aggregateValues.insert(aggregator.resultProperty, aggregator.result()); 253 aggregateValues.insert(aggregator.resultProperty, aggregator.result());
256 } 254 }
257 255
258 readEntity(selectionResult, [&, this](const QByteArray &uid, const Sink::EntityBuffer &entityBuffer) { 256 readEntity(selectionResult, [&, this](const Sink::ApplicationDomain::ApplicationDomainType &entity, Sink::Operation operation) {
259 callback({uid, entityBuffer, Sink::Operation_Creation, aggregateValues}); 257 callback({entity, Sink::Operation_Creation, aggregateValues});
260 foundValue = true; 258 foundValue = true;
261 }); 259 });
262 } 260 }
@@ -285,11 +283,11 @@ public:
285 bool next(const std::function<void(const ResultSet::Result &result)> &callback) Q_DECL_OVERRIDE { 283 bool next(const std::function<void(const ResultSet::Result &result)> &callback) Q_DECL_OVERRIDE {
286 bool foundValue = false; 284 bool foundValue = false;
287 while(!foundValue && mSource->next([this, callback, &foundValue](const ResultSet::Result &result) { 285 while(!foundValue && mSource->next([this, callback, &foundValue](const ResultSet::Result &result) {
288 auto bloomValue = getProperty(result.buffer.entity(), mBloomProperty); 286 auto bloomValue = result.entity.getProperty(mBloomProperty);
289 auto results = indexLookup(mBloomProperty, bloomValue); 287 auto results = indexLookup(mBloomProperty, bloomValue);
290 for (const auto r : results) { 288 for (const auto r : results) {
291 readEntity(r, [&, this](const QByteArray &uid, const Sink::EntityBuffer &entityBuffer) { 289 readEntity(r, [&, this](const Sink::ApplicationDomain::ApplicationDomainType &entity, Sink::Operation operation) {
292 callback({uid, entityBuffer, Sink::Operation_Creation}); 290 callback({entity, Sink::Operation_Creation});
293 foundValue = true; 291 foundValue = true;
294 }); 292 });
295 } 293 }
@@ -300,23 +298,15 @@ public:
300 } 298 }
301}; 299};
302 300
303DataStoreQuery::DataStoreQuery(const Sink::Query &query, const QByteArray &type, EntityStore::Ptr store, std::function<QVariant(const Sink::Entity &entity, const QByteArray &property)> getProperty) 301DataStoreQuery::DataStoreQuery(const Sink::Query &query, const QByteArray &type, EntityStore::Ptr store)
304 : mQuery(query), mType(type), mGetProperty(getProperty), mStore(store) 302 : mQuery(query), mType(type), mStore(store)
305{ 303{
306 setupQuery(); 304 setupQuery();
307} 305}
308 306
309void DataStoreQuery::readEntity(const QByteArray &key, const BufferCallback &resultCallback) 307void DataStoreQuery::readEntity(const QByteArray &key, const BufferCallback &resultCallback)
310{ 308{
311 mStore->readLatest(mType, key, [=](const QByteArray &key, const Sink::EntityBuffer &buffer) { 309 mStore->readLatest(mType, key, resultCallback);
312 resultCallback(DataStore::uidFromKey(key), buffer);
313 return false;
314 });
315}
316
317QVariant DataStoreQuery::getProperty(const Sink::Entity &entity, const QByteArray &property)
318{
319 return mGetProperty(entity, property);
320} 310}
321 311
322QVector<QByteArray> DataStoreQuery::indexLookup(const QByteArray &property, const QVariant &value) 312QVector<QByteArray> DataStoreQuery::indexLookup(const QByteArray &property, const QVariant &value)
@@ -404,28 +394,28 @@ QVector<QByteArray> DataStoreQuery::indexLookup(const QByteArray &property, cons
404/* } */ 394/* } */
405/* } */ 395/* } */
406 396
407template <typename ... Args> 397/* template <typename ... Args> */
408QSharedPointer<DataStoreQuery> prepareQuery(const QByteArray &type, Args && ... args) 398/* QSharedPointer<DataStoreQuery> prepareQuery(const QByteArray &type, Args && ... args) */
409{ 399/* { */
410 if (type == ApplicationDomain::getTypeName<ApplicationDomain::Folder>()) { 400/* if (type == ApplicationDomain::getTypeName<ApplicationDomain::Folder>()) { */
411 return ApplicationDomain::TypeImplementation<ApplicationDomain::Folder>::prepareQuery(std::forward<Args>(args)...); 401/* return ApplicationDomain::TypeImplementation<ApplicationDomain::Folder>::prepareQuery(std::forward<Args>(args)...); */
412 } else if (type == ApplicationDomain::getTypeName<ApplicationDomain::Mail>()) { 402/* } else if (type == ApplicationDomain::getTypeName<ApplicationDomain::Mail>()) { */
413 return ApplicationDomain::TypeImplementation<ApplicationDomain::Mail>::prepareQuery(std::forward<Args>(args)...); 403/* return ApplicationDomain::TypeImplementation<ApplicationDomain::Mail>::prepareQuery(std::forward<Args>(args)...); */
414 } else if (type == ApplicationDomain::getTypeName<ApplicationDomain::Event>()) { 404/* } else if (type == ApplicationDomain::getTypeName<ApplicationDomain::Event>()) { */
415 return ApplicationDomain::TypeImplementation<ApplicationDomain::Event>::prepareQuery(std::forward<Args>(args)...); 405/* return ApplicationDomain::TypeImplementation<ApplicationDomain::Event>::prepareQuery(std::forward<Args>(args)...); */
416 } 406/* } */
417 Q_ASSERT(false); 407/* Q_ASSERT(false); */
418 return QSharedPointer<DataStoreQuery>(); 408/* return QSharedPointer<DataStoreQuery>(); */
419} 409/* } */
420 410
421QByteArrayList DataStoreQuery::executeSubquery(const Query &subquery) 411QByteArrayList DataStoreQuery::executeSubquery(const Query &subquery)
422{ 412{
423 Q_ASSERT(!subquery.type.isEmpty()); 413 Q_ASSERT(!subquery.type.isEmpty());
424 auto sub = prepareQuery(subquery.type, subquery, mStore); 414 auto sub = DataStoreQuery(subquery, subquery.type, mStore);
425 auto result = sub->execute(); 415 auto result = sub.execute();
426 QByteArrayList ids; 416 QByteArrayList ids;
427 while (result.next([&ids](const ResultSet::Result &result) { 417 while (result.next([&ids](const ResultSet::Result &result) {
428 ids << result.uid; 418 ids << result.entity.identifier();
429 })) 419 }))
430 {} 420 {}
431 return ids; 421 return ids;
@@ -518,7 +508,7 @@ ResultSet DataStoreQuery::update(qint64 baseRevision)
518 mSource->add(incrementalResultSet); 508 mSource->add(incrementalResultSet);
519 ResultSet::ValueGenerator generator = [this](const ResultSet::Callback &callback) -> bool { 509 ResultSet::ValueGenerator generator = [this](const ResultSet::Callback &callback) -> bool {
520 if (mCollector->next([this, callback](const ResultSet::Result &result) { 510 if (mCollector->next([this, callback](const ResultSet::Result &result) {
521 SinkTrace() << "Got incremental result: " << result.uid << result.operation; 511 SinkTrace() << "Got incremental result: " << result.entity.identifier() << result.operation;
522 callback(result); 512 callback(result);
523 })) 513 }))
524 { 514 {
@@ -537,8 +527,8 @@ ResultSet DataStoreQuery::execute()
537 ResultSet::ValueGenerator generator = [this](const ResultSet::Callback &callback) -> bool { 527 ResultSet::ValueGenerator generator = [this](const ResultSet::Callback &callback) -> bool {
538 if (mCollector->next([this, callback](const ResultSet::Result &result) { 528 if (mCollector->next([this, callback](const ResultSet::Result &result) {
539 if (result.operation != Sink::Operation_Removal) { 529 if (result.operation != Sink::Operation_Removal) {
540 SinkTrace() << "Got initial result: " << result.uid << result.operation; 530 SinkTrace() << "Got initial result: " << result.entity.identifier() << result.operation;
541 callback(ResultSet::Result{result.uid, result.buffer, Sink::Operation_Creation, result.aggregateValues}); 531 callback(ResultSet::Result{result.entity, Sink::Operation_Creation, result.aggregateValues});
542 } 532 }
543 })) 533 }))
544 { 534 {