summaryrefslogtreecommitdiffstats
path: root/examples/imapresource
diff options
context:
space:
mode:
Diffstat (limited to 'examples/imapresource')
-rw-r--r--examples/imapresource/imapresource.cpp99
-rw-r--r--examples/imapresource/imapresource.h4
-rw-r--r--examples/imapresource/imapserverproxy.cpp40
-rw-r--r--examples/imapresource/tests/imapmailsynctest.cpp8
-rw-r--r--examples/imapresource/tests/imapmailtest.cpp8
-rw-r--r--examples/imapresource/tests/imapserverproxytest.cpp15
-rw-r--r--examples/imapresource/tests/resetmailbox.sh1
7 files changed, 99 insertions, 76 deletions
diff --git a/examples/imapresource/imapresource.cpp b/examples/imapresource/imapresource.cpp
index e23add8..92f64bf 100644
--- a/examples/imapresource/imapresource.cpp
+++ b/examples/imapresource/imapresource.cpp
@@ -54,8 +54,7 @@
54#define ENTITY_TYPE_MAIL "mail" 54#define ENTITY_TYPE_MAIL "mail"
55#define ENTITY_TYPE_FOLDER "folder" 55#define ENTITY_TYPE_FOLDER "folder"
56 56
57#undef DEBUG_AREA 57SINK_DEBUG_AREA("imapresource")
58#define DEBUG_AREA "resource.imap"
59 58
60using namespace Imap; 59using namespace Imap;
61using namespace Sink; 60using namespace Sink;
@@ -95,7 +94,7 @@ public:
95 94
96 QByteArray createFolder(const QString &folderName, const QString &folderPath, const QString &parentFolderRid, const QByteArray &icon) 95 QByteArray createFolder(const QString &folderName, const QString &folderPath, const QString &parentFolderRid, const QByteArray &icon)
97 { 96 {
98 Trace() << "Creating folder: " << folderName << parentFolderRid; 97 SinkTrace() << "Creating folder: " << folderName << parentFolderRid;
99 const auto remoteId = folderPath.toUtf8(); 98 const auto remoteId = folderPath.toUtf8();
100 const auto bufferType = ENTITY_TYPE_FOLDER; 99 const auto bufferType = ENTITY_TYPE_FOLDER;
101 Sink::ApplicationDomain::Folder folder; 100 Sink::ApplicationDomain::Folder folder;
@@ -118,7 +117,7 @@ public:
118 void synchronizeFolders(const QVector<Folder> &folderList) 117 void synchronizeFolders(const QVector<Folder> &folderList)
119 { 118 {
120 const QByteArray bufferType = ENTITY_TYPE_FOLDER; 119 const QByteArray bufferType = ENTITY_TYPE_FOLDER;
121 Trace() << "Found folders " << folderList.size(); 120 SinkTrace() << "Found folders " << folderList.size();
122 121
123 scanForRemovals(bufferType, 122 scanForRemovals(bufferType,
124 [this, &bufferType](const std::function<void(const QByteArray &)> &callback) { 123 [this, &bufferType](const std::function<void(const QByteArray &)> &callback) {
@@ -154,7 +153,7 @@ public:
154 time->start(); 153 time->start();
155 const QByteArray bufferType = ENTITY_TYPE_MAIL; 154 const QByteArray bufferType = ENTITY_TYPE_MAIL;
156 155
157 Trace() << "Importing new mail." << path; 156 SinkTrace() << "Importing new mail." << path;
158 157
159 const auto folderLocalId = syncStore().resolveRemoteId(ENTITY_TYPE_FOLDER, path.toUtf8()); 158 const auto folderLocalId = syncStore().resolveRemoteId(ENTITY_TYPE_FOLDER, path.toUtf8());
160 159
@@ -163,7 +162,7 @@ public:
163 count++; 162 count++;
164 const auto remoteId = assembleMailRid(folderLocalId, message.uid); 163 const auto remoteId = assembleMailRid(folderLocalId, message.uid);
165 164
166 Trace() << "Found a mail " << remoteId << message.msg->subject(true)->asUnicodeString() << message.flags; 165 SinkTrace() << "Found a mail " << remoteId << message.msg->subject(true)->asUnicodeString() << message.flags;
167 166
168 auto mail = Sink::ApplicationDomain::Mail::create(mResourceInstanceIdentifier); 167 auto mail = Sink::ApplicationDomain::Mail::create(mResourceInstanceIdentifier);
169 mail.setFolder(folderLocalId); 168 mail.setFolder(folderLocalId);
@@ -174,7 +173,7 @@ public:
174 createOrModify(bufferType, remoteId, mail); 173 createOrModify(bufferType, remoteId, mail);
175 } 174 }
176 const auto elapsed = time->elapsed(); 175 const auto elapsed = time->elapsed();
177 Log() << "Synchronized " << count << " mails in " << path << Sink::Log::TraceTime(elapsed) << " " << elapsed/qMax(count, 1) << " [ms/mail]"; 176 SinkLog() << "Synchronized " << count << " mails in " << path << Sink::Log::TraceTime(elapsed) << " " << elapsed/qMax(count, 1) << " [ms/mail]";
178 } 177 }
179 178
180 void synchronizeRemovals(const QString &path, const QSet<qint64> &messages) 179 void synchronizeRemovals(const QString &path, const QSet<qint64> &messages)
@@ -183,7 +182,7 @@ public:
183 time->start(); 182 time->start();
184 const QByteArray bufferType = ENTITY_TYPE_MAIL; 183 const QByteArray bufferType = ENTITY_TYPE_MAIL;
185 184
186 Trace() << "Finding removed mail."; 185 SinkTrace() << "Finding removed mail.";
187 186
188 const auto folderLocalId = syncStore().resolveRemoteId(ENTITY_TYPE_FOLDER, path.toUtf8()); 187 const auto folderLocalId = syncStore().resolveRemoteId(ENTITY_TYPE_FOLDER, path.toUtf8());
189 188
@@ -196,7 +195,7 @@ public:
196 callback(sinkId); 195 callback(sinkId);
197 }, 196 },
198 [&](const Index::Error &error) { 197 [&](const Index::Error &error) {
199 Warning() << "Error in index: " << error.message << property; 198 SinkWarning() << "Error in index: " << error.message << property;
200 }); 199 });
201 }, 200 },
202 [messages, path, &count](const QByteArray &remoteId) -> bool { 201 [messages, path, &count](const QByteArray &remoteId) -> bool {
@@ -209,24 +208,24 @@ public:
209 ); 208 );
210 209
211 const auto elapsed = time->elapsed(); 210 const auto elapsed = time->elapsed();
212 Log() << "Removed " << count << " mails in " << path << Sink::Log::TraceTime(elapsed) << " " << elapsed/qMax(count, 1) << " [ms/mail]"; 211 SinkLog() << "Removed " << count << " mails in " << path << Sink::Log::TraceTime(elapsed) << " " << elapsed/qMax(count, 1) << " [ms/mail]";
213 } 212 }
214 213
215 KAsync::Job<void> synchronizeWithSource() Q_DECL_OVERRIDE 214 KAsync::Job<void> synchronizeWithSource() Q_DECL_OVERRIDE
216 { 215 {
217 Log() << " Synchronizing"; 216 SinkLog() << " Synchronizing";
218 return KAsync::start<void>([this](KAsync::Future<void> future) { 217 return KAsync::start<void>([this](KAsync::Future<void> future) {
219 Trace() << "Connecting to:" << mServer << mPort; 218 SinkTrace() << "Connecting to:" << mServer << mPort;
220 Trace() << "as:" << mUser; 219 SinkTrace() << "as:" << mUser;
221 ImapServerProxy imap(mServer, mPort); 220 ImapServerProxy imap(mServer, mPort);
222 auto loginFuture = imap.login(mUser, mPassword).exec(); 221 auto loginFuture = imap.login(mUser, mPassword).exec();
223 loginFuture.waitForFinished(); 222 loginFuture.waitForFinished();
224 if (loginFuture.errorCode()) { 223 if (loginFuture.errorCode()) {
225 Warning() << "Login failed."; 224 SinkWarning() << "Login failed.";
226 future.setError(1, "Login failed"); 225 future.setError(1, "Login failed");
227 return; 226 return;
228 } else { 227 } else {
229 Trace() << "Login was successful"; 228 SinkTrace() << "Login was successful";
230 } 229 }
231 230
232 QVector<Folder> folderList; 231 QVector<Folder> folderList;
@@ -238,11 +237,11 @@ public:
238 }).exec(); 237 }).exec();
239 folderFuture.waitForFinished(); 238 folderFuture.waitForFinished();
240 if (folderFuture.errorCode()) { 239 if (folderFuture.errorCode()) {
241 Warning() << "Folder sync failed."; 240 SinkWarning() << "Folder sync failed.";
242 future.setError(1, "Folder list sync failed"); 241 future.setError(1, "Folder list sync failed");
243 return; 242 return;
244 } else { 243 } else {
245 Trace() << "Folder sync was successful"; 244 SinkTrace() << "Folder sync was successful";
246 } 245 }
247 246
248 for (const auto &folder : folderList) { 247 for (const auto &folder : folderList) {
@@ -251,7 +250,7 @@ public:
251 } 250 }
252 QSet<qint64> uids; 251 QSet<qint64> uids;
253 auto messagesFuture = imap.fetchMessages(folder, [this, folder, &uids](const QVector<Message> &messages) { 252 auto messagesFuture = imap.fetchMessages(folder, [this, folder, &uids](const QVector<Message> &messages) {
254 Trace() << "Synchronizing mails" << folder.normalizedPath(); 253 SinkTrace() << "Synchronizing mails" << folder.normalizedPath();
255 for (const auto &msg : messages) { 254 for (const auto &msg : messages) {
256 uids << msg.uid; 255 uids << msg.uid;
257 } 256 }
@@ -260,16 +259,16 @@ public:
260 messagesFuture.waitForFinished(); 259 messagesFuture.waitForFinished();
261 commit(); 260 commit();
262 if (messagesFuture.errorCode()) { 261 if (messagesFuture.errorCode()) {
263 Warning() << "Folder sync failed: " << folder.normalizedPath(); 262 SinkWarning() << "Folder sync failed: " << folder.normalizedPath();
264 continue; 263 continue;
265 } 264 }
266 //Remove what there is to remove 265 //Remove what there is to remove
267 synchronizeRemovals(folder.normalizedPath(), uids); 266 synchronizeRemovals(folder.normalizedPath(), uids);
268 commit(); 267 commit();
269 Trace() << "Folder synchronized: " << folder.normalizedPath(); 268 SinkTrace() << "Folder synchronized: " << folder.normalizedPath();
270 } 269 }
271 270
272 Log() << "Done Synchronizing"; 271 SinkLog() << "Done Synchronizing";
273 future.setFinished(); 272 future.setFinished();
274 }); 273 });
275 } 274 }
@@ -310,7 +309,7 @@ public:
310 .then<void, qint64>([imap, mailbox, rid, mail](qint64 uid) { 309 .then<void, qint64>([imap, mailbox, rid, mail](qint64 uid) {
311 const auto remoteId = assembleMailRid(mail, uid); 310 const auto remoteId = assembleMailRid(mail, uid);
312 //FIXME this get's called after the final error handler? WTF? 311 //FIXME this get's called after the final error handler? WTF?
313 Trace() << "Finished creating a new mail: " << remoteId; 312 SinkTrace() << "Finished creating a new mail: " << remoteId;
314 *rid = remoteId; 313 *rid = remoteId;
315 }).then<QByteArray>([rid, imap]() { //FIXME fix KJob so we don't need this extra clause 314 }).then<QByteArray>([rid, imap]() { //FIXME fix KJob so we don't need this extra clause
316 return *rid; 315 return *rid;
@@ -319,19 +318,19 @@ public:
319 const auto folderId = folderIdFromMailRid(oldRemoteId); 318 const auto folderId = folderIdFromMailRid(oldRemoteId);
320 const QString mailbox = syncStore().resolveLocalId(ENTITY_TYPE_FOLDER, folderId); 319 const QString mailbox = syncStore().resolveLocalId(ENTITY_TYPE_FOLDER, folderId);
321 const auto uid = uidFromMailRid(oldRemoteId); 320 const auto uid = uidFromMailRid(oldRemoteId);
322 Trace() << "Removing a mail: " << oldRemoteId << "in the mailbox: " << mailbox; 321 SinkTrace() << "Removing a mail: " << oldRemoteId << "in the mailbox: " << mailbox;
323 KIMAP::ImapSet set; 322 KIMAP::ImapSet set;
324 set.add(uid); 323 set.add(uid);
325 return login.then(imap->remove(mailbox, set)) 324 return login.then(imap->remove(mailbox, set))
326 .then<QByteArray>([imap, oldRemoteId]() { 325 .then<QByteArray>([imap, oldRemoteId]() {
327 Trace() << "Finished removing a mail: " << oldRemoteId; 326 SinkTrace() << "Finished removing a mail: " << oldRemoteId;
328 return QByteArray(); 327 return QByteArray();
329 }); 328 });
330 } else if (operation == Sink::Operation_Modification) { 329 } else if (operation == Sink::Operation_Modification) {
331 const QString mailbox = syncStore().resolveLocalId(ENTITY_TYPE_FOLDER, mail.getFolder()); 330 const QString mailbox = syncStore().resolveLocalId(ENTITY_TYPE_FOLDER, mail.getFolder());
332 const auto uid = uidFromMailRid(oldRemoteId); 331 const auto uid = uidFromMailRid(oldRemoteId);
333 332
334 Trace() << "Modifying a mail: " << oldRemoteId << " in the mailbox: " << mailbox << changedProperties; 333 SinkTrace() << "Modifying a mail: " << oldRemoteId << " in the mailbox: " << mailbox << changedProperties;
335 334
336 QByteArrayList flags; 335 QByteArrayList flags;
337 if (!mail.getUnread()) { 336 if (!mail.getUnread()) {
@@ -344,7 +343,7 @@ public:
344 const bool messageMoved = changedProperties.contains(ApplicationDomain::Mail::Folder::name); 343 const bool messageMoved = changedProperties.contains(ApplicationDomain::Mail::Folder::name);
345 const bool messageChanged = changedProperties.contains(ApplicationDomain::Mail::MimeMessage::name); 344 const bool messageChanged = changedProperties.contains(ApplicationDomain::Mail::MimeMessage::name);
346 if (messageChanged || messageMoved) { 345 if (messageChanged || messageMoved) {
347 Trace() << "Replacing message."; 346 SinkTrace() << "Replacing message.";
348 const auto folderId = folderIdFromMailRid(oldRemoteId); 347 const auto folderId = folderIdFromMailRid(oldRemoteId);
349 const QString oldMailbox = syncStore().resolveLocalId(ENTITY_TYPE_FOLDER, folderId); 348 const QString oldMailbox = syncStore().resolveLocalId(ENTITY_TYPE_FOLDER, folderId);
350 QByteArray content = KMime::LFtoCRLF(mail.getMimeMessage()); 349 QByteArray content = KMime::LFtoCRLF(mail.getMimeMessage());
@@ -355,7 +354,7 @@ public:
355 return login.then(imap->append(mailbox, content, flags, internalDate)) 354 return login.then(imap->append(mailbox, content, flags, internalDate))
356 .then<void, qint64>([imap, mailbox, rid, mail](qint64 uid) { 355 .then<void, qint64>([imap, mailbox, rid, mail](qint64 uid) {
357 const auto remoteId = assembleMailRid(mail, uid); 356 const auto remoteId = assembleMailRid(mail, uid);
358 Trace() << "Finished creating a modified mail: " << remoteId; 357 SinkTrace() << "Finished creating a modified mail: " << remoteId;
359 *rid = remoteId; 358 *rid = remoteId;
360 }) 359 })
361 .then(imap->remove(oldMailbox, set)) 360 .then(imap->remove(oldMailbox, set))
@@ -363,13 +362,13 @@ public:
363 return *rid; 362 return *rid;
364 }); 363 });
365 } else { 364 } else {
366 Trace() << "Updating flags only."; 365 SinkTrace() << "Updating flags only.";
367 KIMAP::ImapSet set; 366 KIMAP::ImapSet set;
368 set.add(uid); 367 set.add(uid);
369 return login.then(imap->select(mailbox)) 368 return login.then(imap->select(mailbox))
370 .then(imap->storeFlags(set, flags)) 369 .then(imap->storeFlags(set, flags))
371 .then<void>([imap, mailbox]() { 370 .then<void>([imap, mailbox]() {
372 Trace() << "Finished modifying mail"; 371 SinkTrace() << "Finished modifying mail";
373 }) 372 })
374 .then<QByteArray>([oldRemoteId, imap]() { 373 .then<QByteArray>([oldRemoteId, imap]() {
375 return oldRemoteId; 374 return oldRemoteId;
@@ -388,11 +387,11 @@ public:
388 if (!folder.getParent().isEmpty()) { 387 if (!folder.getParent().isEmpty()) {
389 parentFolder = syncStore().resolveLocalId(ENTITY_TYPE_FOLDER, folder.getParent()); 388 parentFolder = syncStore().resolveLocalId(ENTITY_TYPE_FOLDER, folder.getParent());
390 } 389 }
391 Trace() << "Creating a new folder: " << parentFolder << folder.getName(); 390 SinkTrace() << "Creating a new folder: " << parentFolder << folder.getName();
392 auto rid = QSharedPointer<QByteArray>::create(); 391 auto rid = QSharedPointer<QByteArray>::create();
393 auto createFolder = login.then<QString>(imap->createSubfolder(parentFolder, folder.getName())) 392 auto createFolder = login.then<QString>(imap->createSubfolder(parentFolder, folder.getName()))
394 .then<void, QString>([imap, rid](const QString &createdFolder) { 393 .then<void, QString>([imap, rid](const QString &createdFolder) {
395 Trace() << "Finished creating a new folder: " << createdFolder; 394 SinkTrace() << "Finished creating a new folder: " << createdFolder;
396 *rid = createdFolder.toUtf8(); 395 *rid = createdFolder.toUtf8();
397 }); 396 });
398 if (folder.getSpecialPurpose().isEmpty()) { 397 if (folder.getSpecialPurpose().isEmpty()) {
@@ -414,15 +413,15 @@ public:
414 for (const auto &purpose : folder.getSpecialPurpose()) { 413 for (const auto &purpose : folder.getSpecialPurpose()) {
415 if (specialPurposeFolders->contains(purpose)) { 414 if (specialPurposeFolders->contains(purpose)) {
416 auto f = specialPurposeFolders->value(purpose); 415 auto f = specialPurposeFolders->value(purpose);
417 Trace() << "Merging specialpurpose folder with: " << f << " with purpose: " << purpose; 416 SinkTrace() << "Merging specialpurpose folder with: " << f << " with purpose: " << purpose;
418 *rid = f.toUtf8(); 417 *rid = f.toUtf8();
419 return KAsync::null<void>(); 418 return KAsync::null<void>();
420 } 419 }
421 } 420 }
422 Trace() << "No match found for merging, creating a new folder"; 421 SinkTrace() << "No match found for merging, creating a new folder";
423 return imap->createSubfolder(parentFolder, folder.getName()) 422 return imap->createSubfolder(parentFolder, folder.getName())
424 .then<void, QString>([imap, rid](const QString &createdFolder) { 423 .then<void, QString>([imap, rid](const QString &createdFolder) {
425 Trace() << "Finished creating a new folder: " << createdFolder; 424 SinkTrace() << "Finished creating a new folder: " << createdFolder;
426 *rid = createdFolder.toUtf8(); 425 *rid = createdFolder.toUtf8();
427 }); 426 });
428 427
@@ -433,18 +432,18 @@ public:
433 return mergeJob; 432 return mergeJob;
434 } 433 }
435 } else if (operation == Sink::Operation_Removal) { 434 } else if (operation == Sink::Operation_Removal) {
436 Trace() << "Removing a folder: " << oldRemoteId; 435 SinkTrace() << "Removing a folder: " << oldRemoteId;
437 return login.then<void>(imap->remove(oldRemoteId)) 436 return login.then<void>(imap->remove(oldRemoteId))
438 .then<QByteArray>([oldRemoteId, imap]() { 437 .then<QByteArray>([oldRemoteId, imap]() {
439 Trace() << "Finished removing a folder: " << oldRemoteId; 438 SinkTrace() << "Finished removing a folder: " << oldRemoteId;
440 return QByteArray(); 439 return QByteArray();
441 }); 440 });
442 } else if (operation == Sink::Operation_Modification) { 441 } else if (operation == Sink::Operation_Modification) {
443 Trace() << "Renaming a folder: " << oldRemoteId << folder.getName(); 442 SinkTrace() << "Renaming a folder: " << oldRemoteId << folder.getName();
444 auto rid = QSharedPointer<QByteArray>::create(); 443 auto rid = QSharedPointer<QByteArray>::create();
445 return login.then<QString>(imap->renameSubfolder(oldRemoteId, folder.getName())) 444 return login.then<QString>(imap->renameSubfolder(oldRemoteId, folder.getName()))
446 .then<void, QString>([imap, rid](const QString &createdFolder) { 445 .then<void, QString>([imap, rid](const QString &createdFolder) {
447 Trace() << "Finished renaming a folder: " << createdFolder; 446 SinkTrace() << "Finished renaming a folder: " << createdFolder;
448 *rid = createdFolder.toUtf8(); 447 *rid = createdFolder.toUtf8();
449 }) 448 })
450 .then<QByteArray>([rid](){ 449 .then<QByteArray>([rid](){
@@ -515,7 +514,7 @@ KAsync::Job<void> ImapResource::inspect(int inspectionType, const QByteArray &in
515 auto entityStore = QSharedPointer<Sink::EntityStore>::create(mResourceType, mResourceInstanceIdentifier, transaction); 514 auto entityStore = QSharedPointer<Sink::EntityStore>::create(mResourceType, mResourceInstanceIdentifier, transaction);
516 auto syncStore = QSharedPointer<Sink::RemoteIdMap>::create(synchronizationTransaction); 515 auto syncStore = QSharedPointer<Sink::RemoteIdMap>::create(synchronizationTransaction);
517 516
518 Trace() << "Inspecting " << inspectionType << domainType << entityId << property << expectedValue; 517 SinkTrace() << "Inspecting " << inspectionType << domainType << entityId << property << expectedValue;
519 518
520 if (domainType == ENTITY_TYPE_MAIL) { 519 if (domainType == ENTITY_TYPE_MAIL) {
521 const auto mail = entityStore->read<Sink::ApplicationDomain::Mail>(entityId); 520 const auto mail = entityStore->read<Sink::ApplicationDomain::Mail>(entityId);
@@ -523,11 +522,11 @@ KAsync::Job<void> ImapResource::inspect(int inspectionType, const QByteArray &in
523 const auto folderRemoteId = syncStore->resolveLocalId(ENTITY_TYPE_FOLDER, mail.getFolder()); 522 const auto folderRemoteId = syncStore->resolveLocalId(ENTITY_TYPE_FOLDER, mail.getFolder());
524 const auto mailRemoteId = syncStore->resolveLocalId(ENTITY_TYPE_MAIL, mail.identifier()); 523 const auto mailRemoteId = syncStore->resolveLocalId(ENTITY_TYPE_MAIL, mail.identifier());
525 if (mailRemoteId.isEmpty() || folderRemoteId.isEmpty()) { 524 if (mailRemoteId.isEmpty() || folderRemoteId.isEmpty()) {
526 Warning() << "Missing remote id for folder or mail. " << mailRemoteId << folderRemoteId; 525 SinkWarning() << "Missing remote id for folder or mail. " << mailRemoteId << folderRemoteId;
527 return KAsync::error<void>(); 526 return KAsync::error<void>();
528 } 527 }
529 const auto uid = uidFromMailRid(mailRemoteId); 528 const auto uid = uidFromMailRid(mailRemoteId);
530 Trace() << "Mail remote id: " << folderRemoteId << mailRemoteId << mail.identifier() << folder.identifier(); 529 SinkTrace() << "Mail remote id: " << folderRemoteId << mailRemoteId << mail.identifier() << folder.identifier();
531 530
532 KIMAP::ImapSet set; 531 KIMAP::ImapSet set;
533 set.add(uid); 532 set.add(uid);
@@ -538,8 +537,8 @@ KAsync::Job<void> ImapResource::inspect(int inspectionType, const QByteArray &in
538 scope.mode = KIMAP::FetchJob::FetchScope::Full; 537 scope.mode = KIMAP::FetchJob::FetchScope::Full;
539 auto imap = QSharedPointer<ImapServerProxy>::create(mServer, mPort); 538 auto imap = QSharedPointer<ImapServerProxy>::create(mServer, mPort);
540 auto messageByUid = QSharedPointer<QHash<qint64, Imap::Message>>::create(); 539 auto messageByUid = QSharedPointer<QHash<qint64, Imap::Message>>::create();
541 Trace() << "Connecting to:" << mServer << mPort; 540 SinkTrace() << "Connecting to:" << mServer << mPort;
542 Trace() << "as:" << mUser; 541 SinkTrace() << "as:" << mUser;
543 auto inspectionJob = imap->login(mUser, mPassword) 542 auto inspectionJob = imap->login(mUser, mPassword)
544 .then<void>(imap->select(folderRemoteId)) 543 .then<void>(imap->select(folderRemoteId))
545 .then<void>(imap->fetch(set, scope, [imap, messageByUid](const QVector<Imap::Message> &messages) { 544 .then<void>(imap->fetch(set, scope, [imap, messageByUid](const QVector<Imap::Message> &messages) {
@@ -574,8 +573,8 @@ KAsync::Job<void> ImapResource::inspect(int inspectionType, const QByteArray &in
574 if (inspectionType == Sink::ResourceControl::Inspection::ExistenceInspectionType) { 573 if (inspectionType == Sink::ResourceControl::Inspection::ExistenceInspectionType) {
575 return inspectionJob.then<void, KAsync::Job<void>>([=]() { 574 return inspectionJob.then<void, KAsync::Job<void>>([=]() {
576 if (!messageByUid->contains(uid)) { 575 if (!messageByUid->contains(uid)) {
577 Warning() << "Existing messages are: " << messageByUid->keys(); 576 SinkWarning() << "Existing messages are: " << messageByUid->keys();
578 Warning() << "We're looking for: " << uid; 577 SinkWarning() << "We're looking for: " << uid;
579 return KAsync::error<void>(1, "Couldn't find message: " + mailRemoteId); 578 return KAsync::error<void>(1, "Couldn't find message: " + mailRemoteId);
580 } 579 }
581 return KAsync::null<void>(); 580 return KAsync::null<void>();
@@ -587,7 +586,7 @@ KAsync::Job<void> ImapResource::inspect(int inspectionType, const QByteArray &in
587 const auto folder = entityStore->read<Sink::ApplicationDomain::Folder>(entityId); 586 const auto folder = entityStore->read<Sink::ApplicationDomain::Folder>(entityId);
588 587
589 if (inspectionType == Sink::ResourceControl::Inspection::CacheIntegrityInspectionType) { 588 if (inspectionType == Sink::ResourceControl::Inspection::CacheIntegrityInspectionType) {
590 Log() << "Inspecting cache integrity" << remoteId; 589 SinkLog() << "Inspecting cache integrity" << remoteId;
591 590
592 int expectedCount = 0; 591 int expectedCount = 0;
593 Index index("mail.index.folder", transaction); 592 Index index("mail.index.folder", transaction);
@@ -595,7 +594,7 @@ KAsync::Job<void> ImapResource::inspect(int inspectionType, const QByteArray &in
595 expectedCount++; 594 expectedCount++;
596 }, 595 },
597 [&](const Index::Error &error) { 596 [&](const Index::Error &error) {
598 Warning() << "Error in index: " << error.message << property; 597 SinkWarning() << "Error in index: " << error.message << property;
599 }); 598 });
600 599
601 auto set = KIMAP::ImapSet::fromImapSequenceSet("1:*"); 600 auto set = KIMAP::ImapSet::fromImapSequenceSet("1:*");
@@ -630,10 +629,10 @@ KAsync::Job<void> ImapResource::inspect(int inspectionType, const QByteArray &in
630 *folderByName << f.pathParts.last(); 629 *folderByName << f.pathParts.last();
631 } 630 }
632 })) 631 }))
633 .then<void, KAsync::Job<void>>([folderByName, folderByPath, folder, remoteId, imap]() { 632 .then<void, KAsync::Job<void>>([this, folderByName, folderByPath, folder, remoteId, imap]() {
634 if (!folderByName->contains(folder.getName())) { 633 if (!folderByName->contains(folder.getName())) {
635 Warning() << "Existing folders are: " << *folderByPath; 634 SinkWarning() << "Existing folders are: " << *folderByPath;
636 Warning() << "We're looking for: " << folder.getName(); 635 SinkWarning() << "We're looking for: " << folder.getName();
637 return KAsync::error<void>(1, "Wrong folder name: " + remoteId); 636 return KAsync::error<void>(1, "Wrong folder name: " + remoteId);
638 } 637 }
639 return KAsync::null<void>(); 638 return KAsync::null<void>();
diff --git a/examples/imapresource/imapresource.h b/examples/imapresource/imapresource.h
index 0c3b541..534a04e 100644
--- a/examples/imapresource/imapresource.h
+++ b/examples/imapresource/imapresource.h
@@ -26,7 +26,7 @@
26#include <flatbuffers/flatbuffers.h> 26#include <flatbuffers/flatbuffers.h>
27 27
28//TODO: a little ugly to have this in two places, once here and once in Q_PLUGIN_METADATA 28//TODO: a little ugly to have this in two places, once here and once in Q_PLUGIN_METADATA
29#define PLUGIN_NAME "org.kde.imap" 29#define PLUGIN_NAME "sink.imap"
30 30
31class ImapMailAdaptorFactory; 31class ImapMailAdaptorFactory;
32class ImapFolderAdaptorFactory; 32class ImapFolderAdaptorFactory;
@@ -56,7 +56,7 @@ private:
56class ImapResourceFactory : public Sink::ResourceFactory 56class ImapResourceFactory : public Sink::ResourceFactory
57{ 57{
58 Q_OBJECT 58 Q_OBJECT
59 Q_PLUGIN_METADATA(IID "org.kde.imap") 59 Q_PLUGIN_METADATA(IID "sink.imap")
60 Q_INTERFACES(Sink::ResourceFactory) 60 Q_INTERFACES(Sink::ResourceFactory)
61 61
62public: 62public:
diff --git a/examples/imapresource/imapserverproxy.cpp b/examples/imapresource/imapserverproxy.cpp
index 1b0a2ec..73ec654 100644
--- a/examples/imapresource/imapserverproxy.cpp
+++ b/examples/imapresource/imapserverproxy.cpp
@@ -37,6 +37,8 @@
37 37
38#include "log.h" 38#include "log.h"
39 39
40SINK_DEBUG_AREA("imapserverproxy")
41
40using namespace Imap; 42using namespace Imap;
41 43
42const char* Imap::Flags::Seen = "\\Seen"; 44const char* Imap::Flags::Seen = "\\Seen";
@@ -54,16 +56,16 @@ static KAsync::Job<T> runJob(KJob *job, const std::function<T(KJob*)> &f)
54{ 56{
55 return KAsync::start<T>([job, f](KAsync::Future<T> &future) { 57 return KAsync::start<T>([job, f](KAsync::Future<T> &future) {
56 QObject::connect(job, &KJob::result, [&future, f](KJob *job) { 58 QObject::connect(job, &KJob::result, [&future, f](KJob *job) {
57 Trace() << "Job done: " << job->metaObject()->className(); 59 SinkTrace() << "Job done: " << job->metaObject()->className();
58 if (job->error()) { 60 if (job->error()) {
59 Warning() << "Job failed: " << job->errorString(); 61 SinkWarning() << "Job failed: " << job->errorString();
60 future.setError(job->error(), job->errorString()); 62 future.setError(job->error(), job->errorString());
61 } else { 63 } else {
62 future.setValue(f(job)); 64 future.setValue(f(job));
63 future.setFinished(); 65 future.setFinished();
64 } 66 }
65 }); 67 });
66 Trace() << "Starting job: " << job->metaObject()->className(); 68 SinkTrace() << "Starting job: " << job->metaObject()->className();
67 job->start(); 69 job->start();
68 }); 70 });
69} 71}
@@ -72,15 +74,15 @@ static KAsync::Job<void> runJob(KJob *job)
72{ 74{
73 return KAsync::start<void>([job](KAsync::Future<void> &future) { 75 return KAsync::start<void>([job](KAsync::Future<void> &future) {
74 QObject::connect(job, &KJob::result, [&future](KJob *job) { 76 QObject::connect(job, &KJob::result, [&future](KJob *job) {
75 Trace() << "Job done: " << job->metaObject()->className(); 77 SinkTrace() << "Job done: " << job->metaObject()->className();
76 if (job->error()) { 78 if (job->error()) {
77 Warning() << "Job failed: " << job->errorString(); 79 SinkWarning() << "Job failed: " << job->errorString();
78 future.setError(job->error(), job->errorString()); 80 future.setError(job->error(), job->errorString());
79 } else { 81 } else {
80 future.setFinished(); 82 future.setFinished();
81 } 83 }
82 }); 84 });
83 Trace() << "Starting job: " << job->metaObject()->className(); 85 SinkTrace() << "Starting job: " << job->metaObject()->className();
84 job->start(); 86 job->start();
85 }); 87 });
86} 88}
@@ -117,11 +119,11 @@ KAsync::Job<void> ImapServerProxy::login(const QString &username, const QString
117 auto namespaceJob = new KIMAP::NamespaceJob(mSession); 119 auto namespaceJob = new KIMAP::NamespaceJob(mSession);
118 120
119 return runJob(loginJob).then(runJob(capabilitiesJob)).then<void>([this](){ 121 return runJob(loginJob).then(runJob(capabilitiesJob)).then<void>([this](){
120 Trace() << "Supported capabilities: " << mCapabilities; 122 SinkTrace() << "Supported capabilities: " << mCapabilities;
121 QStringList requiredExtensions = QStringList() << "UIDPLUS" << "NAMESPACE"; 123 QStringList requiredExtensions = QStringList() << "UIDPLUS" << "NAMESPACE";
122 for (const auto &requiredExtension : requiredExtensions) { 124 for (const auto &requiredExtension : requiredExtensions) {
123 if (!mCapabilities.contains(requiredExtension)) { 125 if (!mCapabilities.contains(requiredExtension)) {
124 Warning() << "Server doesn't support required capability: " << requiredExtension; 126 SinkWarning() << "Server doesn't support required capability: " << requiredExtension;
125 //TODO fail the job 127 //TODO fail the job
126 } 128 }
127 } 129 }
@@ -138,9 +140,9 @@ KAsync::Job<void> ImapServerProxy::login(const QString &username, const QString
138 mUserNamespaces << ns.name; 140 mUserNamespaces << ns.name;
139 mUserNamespaceSeparator = ns.separator; 141 mUserNamespaceSeparator = ns.separator;
140 } 142 }
141 Trace() << "Found personal namespaces: " << mPersonalNamespaces << mPersonalNamespaceSeparator; 143 SinkTrace() << "Found personal namespaces: " << mPersonalNamespaces << mPersonalNamespaceSeparator;
142 Trace() << "Found shared namespaces: " << mSharedNamespaces << mSharedNamespaceSeparator; 144 SinkTrace() << "Found shared namespaces: " << mSharedNamespaces << mSharedNamespaceSeparator;
143 Trace() << "Found user namespaces: " << mUserNamespaces << mUserNamespaceSeparator; 145 SinkTrace() << "Found user namespaces: " << mUserNamespaces << mUserNamespaceSeparator;
144 }); 146 });
145} 147}
146 148
@@ -291,8 +293,8 @@ KAsync::Job<QList<qint64>> ImapServerProxy::fetchHeaders(const QString &mailbox)
291 const QMap<qint64,KIMAP::MessageAttribute> &attrs, 293 const QMap<qint64,KIMAP::MessageAttribute> &attrs,
292 const QMap<qint64,KIMAP::MessageFlags> &flags, 294 const QMap<qint64,KIMAP::MessageFlags> &flags,
293 const QMap<qint64,KIMAP::MessagePtr> &messages) { 295 const QMap<qint64,KIMAP::MessagePtr> &messages) {
294 Trace() << "Received " << uids.size() << " headers from " << mailbox; 296 SinkTrace() << "Received " << uids.size() << " headers from " << mailbox;
295 Trace() << uids.size() << sizes.size() << attrs.size() << flags.size() << messages.size(); 297 SinkTrace() << uids.size() << sizes.size() << attrs.size() << flags.size() << messages.size();
296 298
297 //TODO based on the data available here, figure out which messages to actually fetch 299 //TODO based on the data available here, figure out which messages to actually fetch
298 //(we only fetched headers and structure so far) 300 //(we only fetched headers and structure so far)
@@ -344,7 +346,7 @@ KAsync::Job<QString> ImapServerProxy::createSubfolder(const QString &parentMailb
344 } else { 346 } else {
345 *folder = parentMailbox + mPersonalNamespaceSeparator + folderName; 347 *folder = parentMailbox + mPersonalNamespaceSeparator + folderName;
346 } 348 }
347 Trace() << "Creating subfolder: " << *folder; 349 SinkTrace() << "Creating subfolder: " << *folder;
348 return create(*folder); 350 return create(*folder);
349 }) 351 })
350 .then<QString>([=]() { 352 .then<QString>([=]() {
@@ -360,7 +362,7 @@ KAsync::Job<QString> ImapServerProxy::renameSubfolder(const QString &oldMailbox,
360 auto parts = oldMailbox.split(mPersonalNamespaceSeparator); 362 auto parts = oldMailbox.split(mPersonalNamespaceSeparator);
361 parts.removeLast(); 363 parts.removeLast();
362 *folder = parts.join(mPersonalNamespaceSeparator) + mPersonalNamespaceSeparator + newName; 364 *folder = parts.join(mPersonalNamespaceSeparator) + mPersonalNamespaceSeparator + newName;
363 Trace() << "Renaming subfolder: " << oldMailbox << *folder; 365 SinkTrace() << "Renaming subfolder: " << oldMailbox << *folder;
364 return rename(oldMailbox, *folder); 366 return rename(oldMailbox, *folder);
365 }) 367 })
366 .then<QString>([=]() { 368 .then<QString>([=]() {
@@ -370,14 +372,14 @@ KAsync::Job<QString> ImapServerProxy::renameSubfolder(const QString &oldMailbox,
370 372
371KAsync::Job<void> ImapServerProxy::fetchFolders(std::function<void(const QVector<Folder> &)> callback) 373KAsync::Job<void> ImapServerProxy::fetchFolders(std::function<void(const QVector<Folder> &)> callback)
372{ 374{
373 Trace() << "Fetching folders"; 375 SinkTrace() << "Fetching folders";
374 return list(KIMAP::ListJob::IncludeUnsubscribed, [callback](const QList<KIMAP::MailBoxDescriptor> &mailboxes, const QList<QList<QByteArray> > &flags){ 376 return list(KIMAP::ListJob::IncludeUnsubscribed, [callback](const QList<KIMAP::MailBoxDescriptor> &mailboxes, const QList<QList<QByteArray> > &flags){
375 QVector<Folder> list; 377 QVector<Folder> list;
376 for (int i = 0; i < mailboxes.size(); i++) { 378 for (int i = 0; i < mailboxes.size(); i++) {
377 const auto mailbox = mailboxes[i]; 379 const auto mailbox = mailboxes[i];
378 const auto mailboxFlags = flags[i]; 380 const auto mailboxFlags = flags[i];
379 bool noselect = mailboxFlags.contains(QByteArray(FolderFlags::Noselect).toLower()) || mailboxFlags.contains(QByteArray(FolderFlags::Noselect)); 381 bool noselect = mailboxFlags.contains(QByteArray(FolderFlags::Noselect).toLower()) || mailboxFlags.contains(QByteArray(FolderFlags::Noselect));
380 Log() << "Found mailbox: " << mailbox.name << mailboxFlags << FolderFlags::Noselect << noselect; 382 SinkLog() << "Found mailbox: " << mailbox.name << mailboxFlags << FolderFlags::Noselect << noselect;
381 list << Folder{mailbox.name.split(mailbox.separator), mailbox.name, mailbox.separator, noselect}; 383 list << Folder{mailbox.name.split(mailbox.separator), mailbox.name, mailbox.separator, noselect};
382 } 384 }
383 callback(list); 385 callback(list);
@@ -395,9 +397,9 @@ KAsync::Job<void> ImapServerProxy::fetchMessages(const Folder &folder, std::func
395 Q_ASSERT(!mPersonalNamespaceSeparator.isNull()); 397 Q_ASSERT(!mPersonalNamespaceSeparator.isNull());
396 return select(mailboxFromFolder(folder)).then<void, KAsync::Job<void>>([this, callback, folder]() -> KAsync::Job<void> { 398 return select(mailboxFromFolder(folder)).then<void, KAsync::Job<void>>([this, callback, folder]() -> KAsync::Job<void> {
397 return fetchHeaders(mailboxFromFolder(folder)).then<void, KAsync::Job<void>, QList<qint64>>([this, callback](const QList<qint64> &uidsToFetch){ 399 return fetchHeaders(mailboxFromFolder(folder)).then<void, KAsync::Job<void>, QList<qint64>>([this, callback](const QList<qint64> &uidsToFetch){
398 Trace() << "Uids to fetch: " << uidsToFetch; 400 SinkTrace() << "Uids to fetch: " << uidsToFetch;
399 if (uidsToFetch.isEmpty()) { 401 if (uidsToFetch.isEmpty()) {
400 Trace() << "Nothing to fetch"; 402 SinkTrace() << "Nothing to fetch";
401 callback(QVector<Message>()); 403 callback(QVector<Message>());
402 return KAsync::null<void>(); 404 return KAsync::null<void>();
403 } 405 }
diff --git a/examples/imapresource/tests/imapmailsynctest.cpp b/examples/imapresource/tests/imapmailsynctest.cpp
index 968cde5..fcc659d 100644
--- a/examples/imapresource/tests/imapmailsynctest.cpp
+++ b/examples/imapresource/tests/imapmailsynctest.cpp
@@ -17,6 +17,7 @@
17 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. 17 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18 */ 18 */
19#include <QtTest> 19#include <QtTest>
20#include <QTcpSocket>
20 21
21#include <tests/mailsynctest.h> 22#include <tests/mailsynctest.h>
22#include "../imapresource.h" 23#include "../imapresource.h"
@@ -38,6 +39,13 @@ class ImapMailSyncTest : public Sink::MailSyncTest
38 Q_OBJECT 39 Q_OBJECT
39 40
40protected: 41protected:
42 bool isBackendAvailable() Q_DECL_OVERRIDE
43 {
44 QTcpSocket socket;
45 socket.connectToHost("localhost", 993);
46 return socket.waitForConnected(200);
47 }
48
41 void resetTestEnvironment() Q_DECL_OVERRIDE 49 void resetTestEnvironment() Q_DECL_OVERRIDE
42 { 50 {
43 system("resetmailbox.sh"); 51 system("resetmailbox.sh");
diff --git a/examples/imapresource/tests/imapmailtest.cpp b/examples/imapresource/tests/imapmailtest.cpp
index c94a731..e6f41f4 100644
--- a/examples/imapresource/tests/imapmailtest.cpp
+++ b/examples/imapresource/tests/imapmailtest.cpp
@@ -1,4 +1,5 @@
1#include <QtTest> 1#include <QtTest>
2#include <QTcpSocket>
2 3
3#include <tests/mailtest.h> 4#include <tests/mailtest.h>
4 5
@@ -18,6 +19,13 @@ class ImapMailTest : public Sink::MailTest
18 Q_OBJECT 19 Q_OBJECT
19 20
20protected: 21protected:
22 bool isBackendAvailable() Q_DECL_OVERRIDE
23 {
24 QTcpSocket socket;
25 socket.connectToHost("localhost", 993);
26 return socket.waitForConnected(200);
27 }
28
21 void resetTestEnvironment() Q_DECL_OVERRIDE 29 void resetTestEnvironment() Q_DECL_OVERRIDE
22 { 30 {
23 system("resetmailbox.sh"); 31 system("resetmailbox.sh");
diff --git a/examples/imapresource/tests/imapserverproxytest.cpp b/examples/imapresource/tests/imapserverproxytest.cpp
index e32298c..ef695b3 100644
--- a/examples/imapresource/tests/imapserverproxytest.cpp
+++ b/examples/imapresource/tests/imapserverproxytest.cpp
@@ -2,6 +2,7 @@
2 2
3#include <QString> 3#include <QString>
4#include <KMime/Message> 4#include <KMime/Message>
5#include <QTcpSocket>
5 6
6#include "../imapserverproxy.h" 7#include "../imapserverproxy.h"
7 8
@@ -11,6 +12,8 @@
11 12
12using namespace Imap; 13using namespace Imap;
13 14
15SINK_DEBUG_AREA("imapserverproxytest")
16
14/** 17/**
15 */ 18 */
16class ImapServerProxyTest : public QObject 19class ImapServerProxyTest : public QObject
@@ -22,7 +25,9 @@ class ImapServerProxyTest : public QObject
22private slots: 25private slots:
23 void initTestCase() 26 void initTestCase()
24 { 27 {
25 Sink::Log::setDebugOutputLevel(Sink::Log::Trace); 28 QTcpSocket socket;
29 socket.connectToHost("localhost", 993);
30 QVERIFY(socket.waitForConnected(200));
26 system("resetmailbox.sh"); 31 system("resetmailbox.sh");
27 } 32 }
28 33
@@ -77,8 +82,8 @@ private slots:
77 const QMap<qint64,KIMAP::MessageAttribute> &attrs, 82 const QMap<qint64,KIMAP::MessageAttribute> &attrs,
78 const QMap<qint64,KIMAP::MessageFlags> &flags, 83 const QMap<qint64,KIMAP::MessageFlags> &flags,
79 const QMap<qint64,KIMAP::MessagePtr> &messages) { 84 const QMap<qint64,KIMAP::MessagePtr> &messages) {
80 Trace() << "Received " << uids.size() << " messages from " << mailbox; 85 SinkTrace() << "Received " << uids.size() << " messages from " << mailbox;
81 Trace() << uids.size() << sizes.size() << attrs.size() << flags.size() << messages.size(); 86 SinkTrace() << uids.size() << sizes.size() << attrs.size() << flags.size() << messages.size();
82 count += uids.size(); 87 count += uids.size();
83 })); 88 }));
84 89
@@ -102,8 +107,8 @@ private slots:
102 const QMap<qint64,KIMAP::MessageAttribute> &attrs, 107 const QMap<qint64,KIMAP::MessageAttribute> &attrs,
103 const QMap<qint64,KIMAP::MessageFlags> &flags, 108 const QMap<qint64,KIMAP::MessageFlags> &flags,
104 const QMap<qint64,KIMAP::MessagePtr> &messages) { 109 const QMap<qint64,KIMAP::MessagePtr> &messages) {
105 Trace() << "Received " << uids.size() << " messages from " << mailbox; 110 SinkTrace() << "Received " << uids.size() << " messages from " << mailbox;
106 Trace() << uids.size() << sizes.size() << attrs.size() << flags.size() << messages.size(); 111 SinkTrace() << uids.size() << sizes.size() << attrs.size() << flags.size() << messages.size();
107 count += uids.size(); 112 count += uids.size();
108 })); 113 }));
109 114
diff --git a/examples/imapresource/tests/resetmailbox.sh b/examples/imapresource/tests/resetmailbox.sh
index 8834b51..6ed198e 100644
--- a/examples/imapresource/tests/resetmailbox.sh
+++ b/examples/imapresource/tests/resetmailbox.sh
@@ -4,6 +4,7 @@ sudo echo "sam user.doe.* cyrus c" | cyradm --auth PLAIN -u cyrus -w admin local
4sudo echo "dm user.doe.*" | cyradm --auth PLAIN -u cyrus -w admin localhost 4sudo echo "dm user.doe.*" | cyradm --auth PLAIN -u cyrus -w admin localhost
5sudo echo "cm user.doe.test" | cyradm --auth PLAIN -u cyrus -w admin localhost 5sudo echo "cm user.doe.test" | cyradm --auth PLAIN -u cyrus -w admin localhost
6sudo echo "cm user.doe.Drafts" | cyradm --auth PLAIN -u cyrus -w admin localhost 6sudo echo "cm user.doe.Drafts" | cyradm --auth PLAIN -u cyrus -w admin localhost
7sudo echo "cm user.doe.Trash" | cyradm --auth PLAIN -u cyrus -w admin localhost
7sudo echo "sam user.doe cyrus c" | cyradm --auth PLAIN -u cyrus -w admin localhost 8sudo echo "sam user.doe cyrus c" | cyradm --auth PLAIN -u cyrus -w admin localhost
8sudo cp /work/source/Sink/examples/imapresource/tests/data/1365777830.R28.localhost.localdomain\:2\,S /var/spool/imap/d/user/doe/test/1. 9sudo cp /work/source/Sink/examples/imapresource/tests/data/1365777830.R28.localhost.localdomain\:2\,S /var/spool/imap/d/user/doe/test/1.
9sudo chown cyrus:mail /var/spool/imap/d/user/doe/test/1. 10sudo chown cyrus:mail /var/spool/imap/d/user/doe/test/1.