File indexing completed on 2024-11-24 04:44:33
0001 /* This file is part of the KDE project 0002 SPDX-FileCopyrightText: 2010 Klarälvdalens Datakonsult AB, a KDAB Group company <info@kdab.net> 0003 SPDX-FileContributor: Kevin Krammer <krake@kdab.com> 0004 0005 SPDX-License-Identifier: LGPL-2.0-or-later 0006 */ 0007 0008 #include "abstractlocalstore.h" 0009 0010 #include "collectioncreatejob.h" 0011 #include "collectiondeletejob.h" 0012 #include "collectionfetchjob.h" 0013 #include "collectionmodifyjob.h" 0014 #include "collectionmovejob.h" 0015 #include "itemcreatejob.h" 0016 #include "itemdeletejob.h" 0017 #include "itemfetchjob.h" 0018 #include "itemmodifyjob.h" 0019 #include "itemmovejob.h" 0020 #include "sessionimpls_p.h" 0021 #include "storecompactjob.h" 0022 0023 #include <KRandom> 0024 #include <QRandomGenerator> 0025 0026 #include <QTest> 0027 0028 using namespace Akonadi; 0029 using namespace Akonadi::FileStore; 0030 0031 class TestStore : public AbstractLocalStore 0032 { 0033 Q_OBJECT 0034 0035 public: 0036 TestStore() 0037 : mLastCheckedJob(nullptr) 0038 , mLastProcessedJob(nullptr) 0039 , mErrorCode(0) 0040 { 0041 } 0042 0043 public: 0044 mutable Akonadi::FileStore::Job *mLastCheckedJob = nullptr; 0045 Akonadi::FileStore::Job *mLastProcessedJob = nullptr; 0046 0047 Collection mTopLevelCollection; 0048 0049 int mErrorCode; 0050 QString mErrorText; 0051 0052 protected: 0053 void processJob(Akonadi::FileStore::Job *job) override; 0054 0055 protected: 0056 void setTopLevelCollection(const Collection &collection) override 0057 { 0058 mTopLevelCollection = collection; 0059 0060 Collection modifiedCollection = collection; 0061 modifiedCollection.setContentMimeTypes(QStringList() << Collection::mimeType()); 0062 0063 AbstractLocalStore::setTopLevelCollection(modifiedCollection); 0064 } 0065 0066 void checkCollectionCreate(Akonadi::FileStore::CollectionCreateJob *job, int &errorCode, QString &errorText) const override 0067 { 0068 mLastCheckedJob = job; 0069 errorCode = mErrorCode; 0070 errorText = mErrorText; 0071 } 0072 0073 void checkCollectionDelete(Akonadi::FileStore::CollectionDeleteJob *job, int &errorCode, QString &errorText) const override 0074 { 0075 mLastCheckedJob = job; 0076 errorCode = mErrorCode; 0077 errorText = mErrorText; 0078 } 0079 0080 void checkCollectionFetch(Akonadi::FileStore::CollectionFetchJob *job, int &errorCode, QString &errorText) const override 0081 { 0082 mLastCheckedJob = job; 0083 errorCode = mErrorCode; 0084 errorText = mErrorText; 0085 } 0086 0087 void checkCollectionModify(Akonadi::FileStore::CollectionModifyJob *job, int &errorCode, QString &errorText) const override 0088 { 0089 mLastCheckedJob = job; 0090 errorCode = mErrorCode; 0091 errorText = mErrorText; 0092 } 0093 0094 void checkCollectionMove(Akonadi::FileStore::CollectionMoveJob *job, int &errorCode, QString &errorText) const override 0095 { 0096 mLastCheckedJob = job; 0097 errorCode = mErrorCode; 0098 errorText = mErrorText; 0099 } 0100 0101 void checkItemCreate(Akonadi::FileStore::ItemCreateJob *job, int &errorCode, QString &errorText) const override 0102 { 0103 mLastCheckedJob = job; 0104 errorCode = mErrorCode; 0105 errorText = mErrorText; 0106 } 0107 0108 void checkItemDelete(Akonadi::FileStore::ItemDeleteJob *job, int &errorCode, QString &errorText) const override 0109 { 0110 mLastCheckedJob = job; 0111 errorCode = mErrorCode; 0112 errorText = mErrorText; 0113 } 0114 0115 void checkItemFetch(Akonadi::FileStore::ItemFetchJob *job, int &errorCode, QString &errorText) const override 0116 { 0117 mLastCheckedJob = job; 0118 errorCode = mErrorCode; 0119 errorText = mErrorText; 0120 } 0121 0122 void checkItemModify(Akonadi::FileStore::ItemModifyJob *job, int &errorCode, QString &errorText) const override 0123 { 0124 mLastCheckedJob = job; 0125 errorCode = mErrorCode; 0126 errorText = mErrorText; 0127 } 0128 0129 void checkItemMove(Akonadi::FileStore::ItemMoveJob *job, int &errorCode, QString &errorText) const override 0130 { 0131 mLastCheckedJob = job; 0132 errorCode = mErrorCode; 0133 errorText = mErrorText; 0134 } 0135 0136 void checkStoreCompact(Akonadi::FileStore::StoreCompactJob *job, int &errorCode, QString &errorText) const override 0137 { 0138 mLastCheckedJob = job; 0139 errorCode = mErrorCode; 0140 errorText = mErrorText; 0141 } 0142 }; 0143 0144 void TestStore::processJob(Akonadi::FileStore::Job *job) 0145 { 0146 mLastProcessedJob = job; 0147 0148 QCOMPARE(currentJob(), job); 0149 QVERIFY(job->error() == 0); 0150 0151 if (mErrorCode != 0) { 0152 notifyError(mErrorCode, mErrorText); 0153 } 0154 } 0155 0156 class AbstractLocalStoreTest : public QObject 0157 { 0158 Q_OBJECT 0159 0160 public: 0161 AbstractLocalStoreTest() 0162 : QObject() 0163 , mStore(nullptr) 0164 { 0165 } 0166 0167 ~AbstractLocalStoreTest() override 0168 { 0169 delete mStore; 0170 } 0171 0172 private: 0173 TestStore *mStore = nullptr; 0174 0175 private Q_SLOTS: 0176 void init(); 0177 void testSetPath(); 0178 void testCreateCollection(); 0179 void testDeleteCollection(); 0180 void testFetchCollection(); 0181 void testModifyCollection(); 0182 void testMoveCollection(); 0183 void testFetchItems(); 0184 void testFetchItem(); 0185 void testCreateItem(); 0186 void testDeleteItem(); 0187 void testModifyItem(); 0188 void testMoveItem(); 0189 void testCompactStore(); 0190 }; 0191 0192 void AbstractLocalStoreTest::init() 0193 { 0194 delete mStore; 0195 mStore = new TestStore; 0196 } 0197 0198 void AbstractLocalStoreTest::testSetPath() 0199 { 0200 const QString file = KRandom::randomString(10); 0201 const QString path = QLatin1StringView("/tmp/test/") + file; 0202 0203 // check that setTopLevelCollection() has been called 0204 mStore->setPath(path); 0205 QCOMPARE(mStore->mTopLevelCollection.remoteId(), path); 0206 0207 // check that the modified collection is the one returned by topLevelCollection() 0208 QVERIFY(mStore->mTopLevelCollection.contentMimeTypes().isEmpty()); 0209 QCOMPARE(mStore->topLevelCollection().remoteId(), path); 0210 QCOMPARE(mStore->topLevelCollection().contentMimeTypes(), QStringList() << Collection::mimeType()); 0211 QCOMPARE(mStore->topLevelCollection().name(), file); 0212 0213 // check that calling with the same path again, does not call the template method 0214 mStore->mTopLevelCollection = Collection(); 0215 mStore->setPath(path); 0216 QVERIFY(mStore->mTopLevelCollection.remoteId().isEmpty()); 0217 QCOMPARE(mStore->topLevelCollection().remoteId(), path); 0218 QCOMPARE(mStore->topLevelCollection().contentMimeTypes(), QStringList() << Collection::mimeType()); 0219 QCOMPARE(mStore->topLevelCollection().name(), file); 0220 0221 // check that calling with a different path works like the first call 0222 const QString file2 = KRandom::randomString(10); 0223 const QString path2 = QLatin1StringView("/tmp/test2/") + file2; 0224 0225 mStore->setPath(path2); 0226 QCOMPARE(mStore->mTopLevelCollection.remoteId(), path2); 0227 QCOMPARE(mStore->topLevelCollection().remoteId(), path2); 0228 QCOMPARE(mStore->topLevelCollection().contentMimeTypes(), QStringList() << Collection::mimeType()); 0229 QCOMPARE(mStore->topLevelCollection().name(), file2); 0230 } 0231 0232 void AbstractLocalStoreTest::testCreateCollection() 0233 { 0234 Akonadi::FileStore::CollectionCreateJob *job = nullptr; 0235 0236 // test without setPath() 0237 job = mStore->createCollection(Collection(), Collection()); 0238 QVERIFY(job != nullptr); 0239 QCOMPARE(mStore->mLastCheckedJob, job); 0240 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidStoreState); 0241 QVERIFY(!job->errorText().isEmpty()); 0242 0243 QVERIFY(!job->exec()); 0244 QVERIFY(mStore->mLastProcessedJob == nullptr); 0245 0246 // test with path but with invalid collections 0247 mStore->setPath(QStringLiteral("/tmp/test")); 0248 job = mStore->createCollection(Collection(), Collection()); 0249 QVERIFY(job != nullptr); 0250 QCOMPARE(mStore->mLastCheckedJob, job); 0251 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0252 QVERIFY(!job->errorText().isEmpty()); 0253 0254 QVERIFY(!job->exec()); 0255 QVERIFY(mStore->mLastProcessedJob == nullptr); 0256 0257 // test with potentially valid collection (has remoteId), but invalid target parent 0258 Collection collection; 0259 collection.setRemoteId(QStringLiteral("/tmp/test/foo")); 0260 job = mStore->createCollection(collection, Collection()); 0261 QVERIFY(job != nullptr); 0262 QCOMPARE(mStore->mLastCheckedJob, job); 0263 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0264 QVERIFY(!job->errorText().isEmpty()); 0265 0266 QVERIFY(!job->exec()); 0267 QVERIFY(mStore->mLastProcessedJob == nullptr); 0268 0269 // test with potentially valid collections 0270 Collection targetParent; 0271 targetParent.setRemoteId(QStringLiteral("/tmp/test2")); 0272 job = mStore->createCollection(collection, targetParent); 0273 QVERIFY(job != nullptr); 0274 QCOMPARE(mStore->mLastCheckedJob, job); 0275 QCOMPARE(job->error(), 0); 0276 QVERIFY(job->errorText().isEmpty()); 0277 0278 QVERIFY(job->exec()); 0279 QCOMPARE(mStore->mLastProcessedJob, job); 0280 mStore->mLastProcessedJob = nullptr; 0281 0282 // test template check method 0283 mStore->mErrorCode = QRandomGenerator::global()->generate() + 1; 0284 mStore->mErrorText = KRandom::randomString(10); 0285 0286 job = mStore->createCollection(collection, targetParent); 0287 QVERIFY(job != nullptr); 0288 QCOMPARE(mStore->mLastCheckedJob, job); 0289 QCOMPARE(job->error(), mStore->mErrorCode); 0290 QCOMPARE(job->errorText(), mStore->mErrorText); 0291 0292 QVERIFY(!job->exec()); 0293 QVERIFY(mStore->mLastProcessedJob == nullptr); 0294 mStore->mErrorCode = 0; 0295 mStore->mErrorText = QString(); 0296 } 0297 0298 void AbstractLocalStoreTest::testDeleteCollection() 0299 { 0300 Akonadi::FileStore::CollectionDeleteJob *job = nullptr; 0301 0302 // test without setPath() 0303 job = mStore->deleteCollection(Collection()); 0304 QVERIFY(job != nullptr); 0305 QCOMPARE(mStore->mLastCheckedJob, job); 0306 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidStoreState); 0307 QVERIFY(!job->errorText().isEmpty()); 0308 0309 QVERIFY(!job->exec()); 0310 QVERIFY(mStore->mLastProcessedJob == nullptr); 0311 0312 // test with path but with invalid collection 0313 mStore->setPath(QStringLiteral("/tmp/test")); 0314 job = mStore->deleteCollection(Collection()); 0315 QVERIFY(job != nullptr); 0316 QCOMPARE(mStore->mLastCheckedJob, job); 0317 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0318 QVERIFY(!job->errorText().isEmpty()); 0319 0320 QVERIFY(!job->exec()); 0321 QVERIFY(mStore->mLastProcessedJob == nullptr); 0322 0323 // test with ivalid collection (has remoteId, but no parent collection remoteId) 0324 Collection collection; 0325 collection.setRemoteId(QStringLiteral("/tmp/test/foo")); 0326 job = mStore->deleteCollection(collection); 0327 QVERIFY(job != nullptr); 0328 QCOMPARE(mStore->mLastCheckedJob, job); 0329 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0330 QVERIFY(!job->errorText().isEmpty()); 0331 0332 QVERIFY(!job->exec()); 0333 QVERIFY(mStore->mLastProcessedJob == nullptr); 0334 0335 // test with potentially valid collection (has remoteId and parent collection remoteId) 0336 Collection parentCollection; 0337 parentCollection.setRemoteId(QStringLiteral("/tmp/test")); 0338 collection.setParentCollection(parentCollection); 0339 job = mStore->deleteCollection(collection); 0340 QVERIFY(job != nullptr); 0341 QCOMPARE(mStore->mLastCheckedJob, job); 0342 QCOMPARE(job->error(), 0); 0343 QVERIFY(job->errorText().isEmpty()); 0344 0345 QVERIFY(job->exec()); 0346 QCOMPARE(mStore->mLastProcessedJob, job); 0347 mStore->mLastProcessedJob = nullptr; 0348 0349 // test template check method 0350 mStore->mErrorCode = QRandomGenerator::global()->generate() + 1; 0351 mStore->mErrorText = KRandom::randomString(10); 0352 0353 job = mStore->deleteCollection(collection); 0354 QVERIFY(job != nullptr); 0355 QCOMPARE(mStore->mLastCheckedJob, job); 0356 QCOMPARE(job->error(), mStore->mErrorCode); 0357 QCOMPARE(job->errorText(), mStore->mErrorText); 0358 0359 QVERIFY(!job->exec()); 0360 QVERIFY(mStore->mLastProcessedJob == nullptr); 0361 mStore->mErrorCode = 0; 0362 mStore->mErrorText = QString(); 0363 } 0364 0365 void AbstractLocalStoreTest::testFetchCollection() 0366 { 0367 Akonadi::FileStore::CollectionFetchJob *job = nullptr; 0368 0369 // test without setPath() 0370 job = mStore->fetchCollections(Collection()); 0371 QVERIFY(job != nullptr); 0372 QCOMPARE(mStore->mLastCheckedJob, job); 0373 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidStoreState); 0374 QVERIFY(!job->errorText().isEmpty()); 0375 0376 QVERIFY(!job->exec()); 0377 QVERIFY(mStore->mLastProcessedJob == nullptr); 0378 0379 // test with path but with invalid collection 0380 mStore->setPath(QStringLiteral("/tmp/test")); 0381 job = mStore->fetchCollections(Collection()); 0382 QVERIFY(job != nullptr); 0383 QCOMPARE(mStore->mLastCheckedJob, job); 0384 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0385 QVERIFY(!job->errorText().isEmpty()); 0386 0387 QVERIFY(!job->exec()); 0388 QVERIFY(mStore->mLastProcessedJob == nullptr); 0389 0390 // test with potentially valid collection (has remoteId) 0391 Collection collection; 0392 collection.setRemoteId(QStringLiteral("/tmp/test/foo")); 0393 job = mStore->fetchCollections(collection); 0394 QVERIFY(job != nullptr); 0395 QCOMPARE(mStore->mLastCheckedJob, job); 0396 QCOMPARE(job->error(), 0); 0397 QVERIFY(job->errorText().isEmpty()); 0398 0399 QVERIFY(job->exec()); 0400 QCOMPARE(mStore->mLastProcessedJob, job); 0401 mStore->mLastProcessedJob = nullptr; 0402 0403 // test template check method 0404 mStore->mErrorCode = QRandomGenerator::global()->generate() + 1; 0405 mStore->mErrorText = KRandom::randomString(10); 0406 0407 job = mStore->fetchCollections(collection); 0408 QVERIFY(job != nullptr); 0409 QCOMPARE(mStore->mLastCheckedJob, job); 0410 QCOMPARE(job->error(), mStore->mErrorCode); 0411 QCOMPARE(job->errorText(), mStore->mErrorText); 0412 0413 QVERIFY(!job->exec()); 0414 QVERIFY(mStore->mLastProcessedJob == nullptr); 0415 mStore->mErrorCode = 0; 0416 mStore->mErrorText = QString(); 0417 0418 // test fetch of top level collection only 0419 collection.setRemoteId(mStore->topLevelCollection().remoteId()); 0420 job = mStore->fetchCollections(collection, Akonadi::FileStore::CollectionFetchJob::Base); 0421 QVERIFY(job != nullptr); 0422 QCOMPARE(mStore->mLastCheckedJob, job); 0423 QCOMPARE(job->error(), 0); 0424 QVERIFY(job->errorText().isEmpty()); 0425 0426 QVERIFY(job->exec()); 0427 QVERIFY(mStore->mLastProcessedJob == nullptr); // job not handed to subclass because it is full processed in base class 0428 QCOMPARE(job->collections().count(), 1); 0429 QCOMPARE(job->collections()[0], mStore->topLevelCollection()); 0430 } 0431 0432 void AbstractLocalStoreTest::testModifyCollection() 0433 { 0434 Akonadi::FileStore::CollectionModifyJob *job = nullptr; 0435 0436 // test without setPath() 0437 job = mStore->modifyCollection(Collection()); 0438 QVERIFY(job != nullptr); 0439 QCOMPARE(mStore->mLastCheckedJob, job); 0440 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidStoreState); 0441 QVERIFY(!job->errorText().isEmpty()); 0442 0443 QVERIFY(!job->exec()); 0444 QVERIFY(mStore->mLastProcessedJob == nullptr); 0445 0446 // test with path but with invalid item 0447 mStore->setPath(QStringLiteral("/tmp/test")); 0448 job = mStore->modifyCollection(Collection()); 0449 QVERIFY(job != nullptr); 0450 QCOMPARE(mStore->mLastCheckedJob, job); 0451 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0452 QVERIFY(!job->errorText().isEmpty()); 0453 0454 QVERIFY(!job->exec()); 0455 QVERIFY(mStore->mLastProcessedJob == nullptr); 0456 0457 // test with potentially valid collection (has remoteId, but no parent remoteId) 0458 Collection collection; 0459 collection.setRemoteId(QStringLiteral("/tmp/test/foo")); 0460 job = mStore->modifyCollection(collection); 0461 QVERIFY(job != nullptr); 0462 QCOMPARE(mStore->mLastCheckedJob, job); 0463 QCOMPARE(job->error(), 0); 0464 QVERIFY(job->errorText().isEmpty()); 0465 0466 QVERIFY(job->exec()); 0467 QCOMPARE(mStore->mLastProcessedJob, job); 0468 mStore->mLastProcessedJob = nullptr; 0469 0470 // test with potentially valid collection (has remoteId and parent remoteId) 0471 Collection parentCollection; 0472 parentCollection.setRemoteId(QStringLiteral("/tmp/test")); 0473 collection.setParentCollection(parentCollection); 0474 job = mStore->modifyCollection(collection); 0475 QVERIFY(job != nullptr); 0476 QCOMPARE(mStore->mLastCheckedJob, job); 0477 QCOMPARE(job->error(), 0); 0478 QVERIFY(job->errorText().isEmpty()); 0479 0480 QVERIFY(job->exec()); 0481 QCOMPARE(mStore->mLastProcessedJob, job); 0482 mStore->mLastProcessedJob = nullptr; 0483 0484 // test template check method 0485 mStore->mErrorCode = QRandomGenerator::global()->generate() + 1; 0486 mStore->mErrorText = KRandom::randomString(10); 0487 0488 job = mStore->modifyCollection(collection); 0489 QVERIFY(job != nullptr); 0490 QCOMPARE(mStore->mLastCheckedJob, job); 0491 QCOMPARE(job->error(), mStore->mErrorCode); 0492 QCOMPARE(job->errorText(), mStore->mErrorText); 0493 0494 QVERIFY(!job->exec()); 0495 QVERIFY(mStore->mLastProcessedJob == nullptr); 0496 } 0497 0498 void AbstractLocalStoreTest::testMoveCollection() 0499 { 0500 Akonadi::FileStore::CollectionMoveJob *job = nullptr; 0501 0502 // test without setPath() 0503 job = mStore->moveCollection(Collection(), Collection()); 0504 QVERIFY(job != nullptr); 0505 QCOMPARE(mStore->mLastCheckedJob, job); 0506 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidStoreState); 0507 QVERIFY(!job->errorText().isEmpty()); 0508 0509 QVERIFY(!job->exec()); 0510 QVERIFY(mStore->mLastProcessedJob == nullptr); 0511 0512 // test with path but with invalid collections 0513 mStore->setPath(QStringLiteral("/tmp/test")); 0514 job = mStore->moveCollection(Collection(), Collection()); 0515 QVERIFY(job != nullptr); 0516 QCOMPARE(mStore->mLastCheckedJob, job); 0517 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0518 QVERIFY(!job->errorText().isEmpty()); 0519 0520 QVERIFY(!job->exec()); 0521 QVERIFY(mStore->mLastProcessedJob == nullptr); 0522 0523 // test with potentially valid collection (has remoteId and parent remoteId), but invalid target parent 0524 Collection collection; 0525 collection.setRemoteId(QStringLiteral("/tmp/test/foo")); 0526 Collection parentCollection; 0527 parentCollection.setRemoteId(QStringLiteral("/tmp/test")); 0528 collection.setParentCollection(parentCollection); 0529 job = mStore->moveCollection(collection, Collection()); 0530 QVERIFY(job != nullptr); 0531 QCOMPARE(mStore->mLastCheckedJob, job); 0532 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0533 QVERIFY(!job->errorText().isEmpty()); 0534 0535 QVERIFY(!job->exec()); 0536 QVERIFY(mStore->mLastProcessedJob == nullptr); 0537 0538 // test with invalid parent collection, but with potentially valid collection and target parent 0539 collection.setParentCollection(Collection()); 0540 job = mStore->moveCollection(collection, parentCollection); 0541 QVERIFY(job != nullptr); 0542 QCOMPARE(mStore->mLastCheckedJob, job); 0543 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0544 QVERIFY(!job->errorText().isEmpty()); 0545 0546 QVERIFY(!job->exec()); 0547 QVERIFY(mStore->mLastProcessedJob == nullptr); 0548 0549 // test with potentially valid collections 0550 Collection targetParent; 0551 targetParent.setRemoteId(QStringLiteral("/tmp/test2")); 0552 collection.setParentCollection(parentCollection); 0553 job = mStore->moveCollection(collection, targetParent); 0554 QVERIFY(job != nullptr); 0555 QCOMPARE(mStore->mLastCheckedJob, job); 0556 QCOMPARE(job->error(), 0); 0557 QVERIFY(job->errorText().isEmpty()); 0558 0559 QVERIFY(job->exec()); 0560 QCOMPARE(mStore->mLastProcessedJob, job); 0561 mStore->mLastProcessedJob = nullptr; 0562 0563 // test template check method 0564 mStore->mErrorCode = QRandomGenerator::global()->generate() + 1; 0565 mStore->mErrorText = KRandom::randomString(10); 0566 0567 job = mStore->moveCollection(collection, targetParent); 0568 QVERIFY(job != nullptr); 0569 QCOMPARE(mStore->mLastCheckedJob, job); 0570 QCOMPARE(job->error(), mStore->mErrorCode); 0571 QCOMPARE(job->errorText(), mStore->mErrorText); 0572 0573 QVERIFY(!job->exec()); 0574 QVERIFY(mStore->mLastProcessedJob == nullptr); 0575 } 0576 0577 void AbstractLocalStoreTest::testFetchItems() 0578 { 0579 Akonadi::FileStore::ItemFetchJob *job = nullptr; 0580 0581 // test without setPath() 0582 job = mStore->fetchItems(Collection()); 0583 QVERIFY(job != nullptr); 0584 QCOMPARE(mStore->mLastCheckedJob, job); 0585 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidStoreState); 0586 QVERIFY(!job->errorText().isEmpty()); 0587 0588 QVERIFY(!job->exec()); 0589 QVERIFY(mStore->mLastProcessedJob == nullptr); 0590 0591 // test with path but with invalid collection 0592 mStore->setPath(QStringLiteral("/tmp/test")); 0593 job = mStore->fetchItems(Collection()); 0594 QVERIFY(job != nullptr); 0595 QCOMPARE(mStore->mLastCheckedJob, job); 0596 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0597 QVERIFY(!job->errorText().isEmpty()); 0598 0599 QVERIFY(!job->exec()); 0600 QVERIFY(mStore->mLastProcessedJob == nullptr); 0601 0602 // test with potentially valid collection (has remoteId) 0603 Collection collection; 0604 collection.setRemoteId(QStringLiteral("/tmp/test/foo")); 0605 job = mStore->fetchItems(collection); 0606 QVERIFY(job != nullptr); 0607 QCOMPARE(mStore->mLastCheckedJob, job); 0608 QCOMPARE(job->error(), 0); 0609 QVERIFY(job->errorText().isEmpty()); 0610 0611 QVERIFY(job->exec()); 0612 QCOMPARE(mStore->mLastProcessedJob, job); 0613 mStore->mLastProcessedJob = nullptr; 0614 0615 // test template check method 0616 mStore->mErrorCode = QRandomGenerator::global()->generate() + 1; 0617 mStore->mErrorText = KRandom::randomString(10); 0618 0619 job = mStore->fetchItems(collection); 0620 QVERIFY(job != nullptr); 0621 QCOMPARE(mStore->mLastCheckedJob, job); 0622 QCOMPARE(job->error(), mStore->mErrorCode); 0623 QCOMPARE(job->errorText(), mStore->mErrorText); 0624 0625 QVERIFY(!job->exec()); 0626 QVERIFY(mStore->mLastProcessedJob == nullptr); 0627 mStore->mErrorCode = 0; 0628 mStore->mErrorText = QString(); 0629 } 0630 0631 void AbstractLocalStoreTest::testFetchItem() 0632 { 0633 Akonadi::FileStore::ItemFetchJob *job = nullptr; 0634 0635 // test without setPath() 0636 job = mStore->fetchItem(Item()); 0637 QVERIFY(job != nullptr); 0638 QCOMPARE(mStore->mLastCheckedJob, job); 0639 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidStoreState); 0640 QVERIFY(!job->errorText().isEmpty()); 0641 0642 QVERIFY(!job->exec()); 0643 QVERIFY(mStore->mLastProcessedJob == nullptr); 0644 0645 // test with path but with invalid item 0646 mStore->setPath(QStringLiteral("/tmp/test")); 0647 job = mStore->fetchItem(Item()); 0648 QVERIFY(job != nullptr); 0649 QCOMPARE(mStore->mLastCheckedJob, job); 0650 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0651 QVERIFY(!job->errorText().isEmpty()); 0652 0653 QVERIFY(!job->exec()); 0654 QVERIFY(mStore->mLastProcessedJob == nullptr); 0655 0656 // test with potentially valid item (has remoteId) 0657 Item item; 0658 item.setRemoteId(QStringLiteral("/tmp/test/foo")); 0659 job = mStore->fetchItem(item); 0660 QVERIFY(job != nullptr); 0661 QCOMPARE(mStore->mLastCheckedJob, job); 0662 QCOMPARE(job->error(), 0); 0663 QVERIFY(job->errorText().isEmpty()); 0664 0665 QVERIFY(job->exec()); 0666 QCOMPARE(mStore->mLastProcessedJob, job); 0667 mStore->mLastProcessedJob = nullptr; 0668 0669 // test template check method 0670 mStore->mErrorCode = QRandomGenerator::global()->generate() + 1; 0671 mStore->mErrorText = KRandom::randomString(10); 0672 0673 job = mStore->fetchItem(item); 0674 QVERIFY(job != nullptr); 0675 QCOMPARE(mStore->mLastCheckedJob, job); 0676 QCOMPARE(job->error(), mStore->mErrorCode); 0677 QCOMPARE(job->errorText(), mStore->mErrorText); 0678 0679 QVERIFY(!job->exec()); 0680 QVERIFY(mStore->mLastProcessedJob == nullptr); 0681 mStore->mErrorCode = 0; 0682 mStore->mErrorText = QString(); 0683 } 0684 0685 void AbstractLocalStoreTest::testCreateItem() 0686 { 0687 Akonadi::FileStore::ItemCreateJob *job = nullptr; 0688 0689 // test without setPath() 0690 job = mStore->createItem(Item(), Collection()); 0691 QVERIFY(job != nullptr); 0692 QCOMPARE(mStore->mLastCheckedJob, job); 0693 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidStoreState); 0694 QVERIFY(!job->errorText().isEmpty()); 0695 0696 QVERIFY(!job->exec()); 0697 QVERIFY(mStore->mLastProcessedJob == nullptr); 0698 0699 // test with path but with invalid collection 0700 mStore->setPath(QStringLiteral("/tmp/test")); 0701 job = mStore->createItem(Item(), Collection()); 0702 QVERIFY(job != nullptr); 0703 QCOMPARE(mStore->mLastCheckedJob, job); 0704 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0705 QVERIFY(!job->errorText().isEmpty()); 0706 0707 QVERIFY(!job->exec()); 0708 QVERIFY(mStore->mLastProcessedJob == nullptr); 0709 0710 // test with potentially valid collection (has remoteId) 0711 Collection collection; 0712 collection.setRemoteId(QStringLiteral("/tmp/test/foo")); 0713 job = mStore->createItem(Item(), collection); 0714 QVERIFY(job != nullptr); 0715 QCOMPARE(mStore->mLastCheckedJob, job); 0716 QCOMPARE(job->error(), 0); 0717 QVERIFY(job->errorText().isEmpty()); 0718 0719 QVERIFY(job->exec()); 0720 QCOMPARE(mStore->mLastProcessedJob, job); 0721 mStore->mLastProcessedJob = nullptr; 0722 0723 // test template check method 0724 mStore->mErrorCode = QRandomGenerator::global()->generate() + 1; 0725 mStore->mErrorText = KRandom::randomString(10); 0726 0727 job = mStore->createItem(Item(), collection); 0728 QVERIFY(job != nullptr); 0729 QCOMPARE(mStore->mLastCheckedJob, job); 0730 QCOMPARE(job->error(), mStore->mErrorCode); 0731 QCOMPARE(job->errorText(), mStore->mErrorText); 0732 0733 QVERIFY(!job->exec()); 0734 QVERIFY(mStore->mLastProcessedJob == nullptr); 0735 mStore->mErrorCode = 0; 0736 mStore->mErrorText = QString(); 0737 } 0738 0739 void AbstractLocalStoreTest::testDeleteItem() 0740 { 0741 Akonadi::FileStore::ItemDeleteJob *job = nullptr; 0742 0743 // test without setPath() 0744 job = mStore->deleteItem(Item()); 0745 QVERIFY(job != nullptr); 0746 QCOMPARE(mStore->mLastCheckedJob, job); 0747 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidStoreState); 0748 QVERIFY(!job->errorText().isEmpty()); 0749 0750 QVERIFY(!job->exec()); 0751 QVERIFY(mStore->mLastProcessedJob == nullptr); 0752 0753 // test with path but with invalid item 0754 mStore->setPath(QStringLiteral("/tmp/test")); 0755 job = mStore->deleteItem(Item()); 0756 QVERIFY(job != nullptr); 0757 QCOMPARE(mStore->mLastCheckedJob, job); 0758 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0759 QVERIFY(!job->errorText().isEmpty()); 0760 0761 QVERIFY(!job->exec()); 0762 QVERIFY(mStore->mLastProcessedJob == nullptr); 0763 0764 // test with potentially valid item (has remoteId) 0765 Item item; 0766 item.setRemoteId(QStringLiteral("/tmp/test/foo")); 0767 job = mStore->deleteItem(item); 0768 QVERIFY(job != nullptr); 0769 QCOMPARE(mStore->mLastCheckedJob, job); 0770 QCOMPARE(job->error(), 0); 0771 QVERIFY(job->errorText().isEmpty()); 0772 0773 QVERIFY(job->exec()); 0774 QCOMPARE(mStore->mLastProcessedJob, job); 0775 mStore->mLastProcessedJob = nullptr; 0776 0777 // test template check method 0778 mStore->mErrorCode = QRandomGenerator::global()->generate() + 1; 0779 mStore->mErrorText = KRandom::randomString(10); 0780 0781 job = mStore->deleteItem(item); 0782 QVERIFY(job != nullptr); 0783 QCOMPARE(mStore->mLastCheckedJob, job); 0784 QCOMPARE(job->error(), mStore->mErrorCode); 0785 QCOMPARE(job->errorText(), mStore->mErrorText); 0786 0787 QVERIFY(!job->exec()); 0788 QVERIFY(mStore->mLastProcessedJob == nullptr); 0789 mStore->mErrorCode = 0; 0790 mStore->mErrorText = QString(); 0791 } 0792 0793 void AbstractLocalStoreTest::testModifyItem() 0794 { 0795 Akonadi::FileStore::ItemModifyJob *job = nullptr; 0796 0797 // test without setPath() 0798 job = mStore->modifyItem(Item()); 0799 QVERIFY(job != nullptr); 0800 QCOMPARE(mStore->mLastCheckedJob, job); 0801 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidStoreState); 0802 QVERIFY(!job->errorText().isEmpty()); 0803 0804 QVERIFY(!job->exec()); 0805 QVERIFY(mStore->mLastProcessedJob == nullptr); 0806 0807 // test with path but with invalid item 0808 mStore->setPath(QStringLiteral("/tmp/test")); 0809 job = mStore->modifyItem(Item()); 0810 QVERIFY(job != nullptr); 0811 QCOMPARE(mStore->mLastCheckedJob, job); 0812 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0813 QVERIFY(!job->errorText().isEmpty()); 0814 0815 QVERIFY(!job->exec()); 0816 QVERIFY(mStore->mLastProcessedJob == nullptr); 0817 0818 // test with potentially valid item (has remoteId) 0819 Item item; 0820 item.setRemoteId(QStringLiteral("/tmp/test/foo")); 0821 job = mStore->modifyItem(item); 0822 QVERIFY(job != nullptr); 0823 QCOMPARE(mStore->mLastCheckedJob, job); 0824 QCOMPARE(job->error(), 0); 0825 QVERIFY(job->errorText().isEmpty()); 0826 0827 QVERIFY(job->exec()); 0828 QCOMPARE(mStore->mLastProcessedJob, job); 0829 mStore->mLastProcessedJob = nullptr; 0830 0831 // test template check method 0832 mStore->mErrorCode = QRandomGenerator::global()->generate() + 1; 0833 mStore->mErrorText = KRandom::randomString(10); 0834 0835 job = mStore->modifyItem(item); 0836 QVERIFY(job != nullptr); 0837 QCOMPARE(mStore->mLastCheckedJob, job); 0838 QCOMPARE(job->error(), mStore->mErrorCode); 0839 QCOMPARE(job->errorText(), mStore->mErrorText); 0840 0841 QVERIFY(!job->exec()); 0842 QVERIFY(mStore->mLastProcessedJob == nullptr); 0843 } 0844 0845 void AbstractLocalStoreTest::testMoveItem() 0846 { 0847 Akonadi::FileStore::ItemMoveJob *job = nullptr; 0848 0849 // test without setPath() 0850 job = mStore->moveItem(Item(), Collection()); 0851 QVERIFY(job != nullptr); 0852 QCOMPARE(mStore->mLastCheckedJob, job); 0853 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidStoreState); 0854 QVERIFY(!job->errorText().isEmpty()); 0855 0856 QVERIFY(!job->exec()); 0857 QVERIFY(mStore->mLastProcessedJob == nullptr); 0858 0859 // test with path but with invalid item and collection 0860 mStore->setPath(QStringLiteral("/tmp/test")); 0861 job = mStore->moveItem(Item(), Collection()); 0862 QVERIFY(job != nullptr); 0863 QCOMPARE(mStore->mLastCheckedJob, job); 0864 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0865 QVERIFY(!job->errorText().isEmpty()); 0866 0867 QVERIFY(!job->exec()); 0868 QVERIFY(mStore->mLastProcessedJob == nullptr); 0869 0870 // test with potentially valid item (has remoteId and parent remoteId), but invalid target parent 0871 Item item; 0872 item.setRemoteId(QStringLiteral("/tmp/test/foo")); 0873 Collection parentCollection; 0874 parentCollection.setRemoteId(QStringLiteral("/tmp/test")); 0875 item.setParentCollection(parentCollection); 0876 job = mStore->moveItem(item, Collection()); 0877 QVERIFY(job != nullptr); 0878 QCOMPARE(mStore->mLastCheckedJob, job); 0879 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0880 QVERIFY(!job->errorText().isEmpty()); 0881 0882 QVERIFY(!job->exec()); 0883 QVERIFY(mStore->mLastProcessedJob == nullptr); 0884 0885 // test with invalid parent collection, but with potentially valid item and target parent 0886 item.setParentCollection(Collection()); 0887 job = mStore->moveItem(item, parentCollection); 0888 QVERIFY(job != nullptr); 0889 QCOMPARE(mStore->mLastCheckedJob, job); 0890 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidJobContext); 0891 QVERIFY(!job->errorText().isEmpty()); 0892 0893 QVERIFY(!job->exec()); 0894 QVERIFY(mStore->mLastProcessedJob == nullptr); 0895 0896 // test with potentially valid item and collections 0897 Collection targetParent; 0898 targetParent.setRemoteId(QStringLiteral("/tmp/test2")); 0899 item.setParentCollection(parentCollection); 0900 job = mStore->moveItem(item, targetParent); 0901 QVERIFY(job != nullptr); 0902 QCOMPARE(mStore->mLastCheckedJob, job); 0903 QCOMPARE(job->error(), 0); 0904 QVERIFY(job->errorText().isEmpty()); 0905 0906 QVERIFY(job->exec()); 0907 QCOMPARE(mStore->mLastProcessedJob, job); 0908 mStore->mLastProcessedJob = nullptr; 0909 0910 // test template check method 0911 mStore->mErrorCode = QRandomGenerator::global()->generate() + 1; 0912 mStore->mErrorText = KRandom::randomString(10); 0913 0914 job = mStore->moveItem(item, targetParent); 0915 QVERIFY(job != nullptr); 0916 QCOMPARE(mStore->mLastCheckedJob, job); 0917 QCOMPARE(job->error(), mStore->mErrorCode); 0918 QCOMPARE(job->errorText(), mStore->mErrorText); 0919 0920 QVERIFY(!job->exec()); 0921 QVERIFY(mStore->mLastProcessedJob == nullptr); 0922 } 0923 0924 void AbstractLocalStoreTest::testCompactStore() 0925 { 0926 Akonadi::FileStore::StoreCompactJob *job = nullptr; 0927 0928 // test without setPath() 0929 job = mStore->compactStore(); 0930 QVERIFY(job != nullptr); 0931 QCOMPARE(mStore->mLastCheckedJob, job); 0932 QCOMPARE(job->error(), (int)Akonadi::FileStore::Job::InvalidStoreState); 0933 QVERIFY(!job->errorText().isEmpty()); 0934 0935 QVERIFY(!job->exec()); 0936 QVERIFY(mStore->mLastProcessedJob == nullptr); 0937 0938 // test with path 0939 mStore->setPath(QStringLiteral("/tmp/test")); 0940 job = mStore->compactStore(); 0941 QVERIFY(job != nullptr); 0942 QCOMPARE(mStore->mLastCheckedJob, job); 0943 QCOMPARE(job->error(), 0); 0944 QVERIFY(job->errorText().isEmpty()); 0945 0946 QVERIFY(job->exec()); 0947 QCOMPARE(mStore->mLastProcessedJob, job); 0948 mStore->mLastProcessedJob = nullptr; 0949 0950 // test template check method 0951 mStore->mErrorCode = QRandomGenerator::global()->generate() + 1; 0952 mStore->mErrorText = KRandom::randomString(10); 0953 0954 job = mStore->compactStore(); 0955 QVERIFY(job != nullptr); 0956 QCOMPARE(mStore->mLastCheckedJob, job); 0957 QCOMPARE(job->error(), mStore->mErrorCode); 0958 QCOMPARE(job->errorText(), mStore->mErrorText); 0959 0960 QVERIFY(!job->exec()); 0961 QVERIFY(mStore->mLastProcessedJob == nullptr); 0962 mStore->mErrorCode = 0; 0963 mStore->mErrorText = QString(); 0964 } 0965 0966 QTEST_MAIN(AbstractLocalStoreTest) 0967 0968 #include "abstractlocalstoretest.moc"