From db5ddcc4306f3bccd2ad73fee7e4600fa803be77 Mon Sep 17 00:00:00 2001 From: Montel Laurent Date: Thu, 9 Feb 2017 23:20:13 +0100 Subject: [PATCH] Continue to extract code as job --- src/job/createforwardmessagejob.cpp | 25 ++++- src/job/createforwardmessagejob.h | 9 ++ src/job/fillcomposerjob.cpp | 136 ++++++++++++++++++++++- src/job/fillcomposerjob.h | 63 +++++++++++ src/kmcommands.cpp | 41 ++----- src/kmkernel.cpp | 166 ++++++---------------------- src/kmkernel.h | 5 +- 7 files changed, 275 insertions(+), 170 deletions(-) diff --git a/src/job/createforwardmessagejob.cpp b/src/job/createforwardmessagejob.cpp index ec2f240b9..0777d7011 100644 --- a/src/job/createforwardmessagejob.cpp +++ b/src/job/createforwardmessagejob.cpp @@ -51,14 +51,33 @@ void CreateForwardMessageJob::start() MessageComposer::MessageFactory factory(mSettings.mMsg, mSettings.mItem.id(), MailCommon::Util::updatedCollection(mSettings.mItem.parentCollection())); factory.setIdentityManager(KMKernel::self()->identityManager()); factory.setFolderIdentity(MailCommon::Util::folderIdentity(mSettings.mItem)); + factory.setSelection(mSettings.mSelection); + if (!mSettings.mTemplate.isEmpty()) { + factory.setTemplate(mSettings.mTemplate); + } + KMime::Message::Ptr fmsg = factory.createForward(); - fmsg->to()->fromUnicodeString(KEmailAddress::decodeMailtoUrl(mSettings.mUrl).toLower(), "utf-8"); + if (mSettings.mUrl.isValid()) { + fmsg->to()->fromUnicodeString(KEmailAddress::decodeMailtoUrl(mSettings.mUrl).toLower(), "utf-8"); + } bool lastEncrypt = false; bool lastSign = false; KMail::Util::lastEncryptAndSignState(lastEncrypt, lastSign, mSettings.mMsg); - KMail::Composer *win = KMail::makeComposer(fmsg, lastSign, lastEncrypt, KMail::Composer::Forward); - win->show(); + if (mSettings.mUrl.isValid()) { + KMail::Composer *win = KMail::makeComposer(fmsg, lastSign, lastEncrypt, KMail::Composer::Forward); + win->show(); + } else { + uint id = 0; + if (auto hrd = mSettings.mMsg->headerByType("X-KMail-Identity")) { + id = hrd->asUnicodeString().trimmed().toUInt(); + } + if (id == 0) { + id = mSettings.mIdentity; + } + KMail::Composer *win = KMail::makeComposer(fmsg, lastSign, lastEncrypt, KMail::Composer::Forward, id, QString(), mSettings.mTemplate); + win->show(); + } deleteLater(); } diff --git a/src/job/createforwardmessagejob.h b/src/job/createforwardmessagejob.h index 29b5570a2..378845507 100644 --- a/src/job/createforwardmessagejob.h +++ b/src/job/createforwardmessagejob.h @@ -28,9 +28,18 @@ struct CreateForwardMessageJobSettings { + CreateForwardMessageJobSettings() + : mIdentity(0) + { + + } + QUrl mUrl; Akonadi::Item mItem; KMime::Message::Ptr mMsg; + QString mTemplate; + QString mSelection; + uint mIdentity; }; class CreateForwardMessageJob : public QObject diff --git a/src/job/fillcomposerjob.cpp b/src/job/fillcomposerjob.cpp index 6044a6875..c6efce8be 100644 --- a/src/job/fillcomposerjob.cpp +++ b/src/job/fillcomposerjob.cpp @@ -18,9 +18,23 @@ */ #include "fillcomposerjob.h" +#include "config-kmail.h" +#include "kmkernel.h" +#include "composer.h" +#include "editor/kmcomposerwin.h" +#include "messageviewer/messageviewersettings.h" + +#include +#include +//#ifdef KDEPIM_TEMPLATEPARSER_ASYNC_BUILD +//#include +//#else +#include +//#endif FillComposerJob::FillComposerJob(QObject *parent) - : QObject(parent) + : QObject(parent), + mMsg(nullptr) { } @@ -32,5 +46,125 @@ FillComposerJob::~FillComposerJob() void FillComposerJob::start() { + mMsg = KMime::Message::Ptr(new KMime::Message); + MessageHelper::initHeader(mMsg, KMKernel::self()->identityManager()); + mMsg->contentType()->setCharset("utf-8"); + if (!mSettings.mCc.isEmpty()) { + mMsg->cc()->fromUnicodeString(mSettings.mCc, "utf-8"); + } + if (!mSettings.mBcc.isEmpty()) { + mMsg->bcc()->fromUnicodeString(mSettings.mBcc, "utf-8"); + } + if (!mSettings.mSubject.isEmpty()) { + mMsg->subject()->fromUnicodeString(mSettings.mSubject, "utf-8"); + } + if (!mSettings.mTo.isEmpty()) { + mMsg->to()->fromUnicodeString(mSettings.mTo, "utf-8"); + } + if (mSettings.mIdentity > 0) { + KMime::Headers::Generic *h = new KMime::Headers::Generic("X-KMail-Identity"); + h->from7BitString(QByteArray::number(mSettings.mIdentity)); + mMsg->setHeader(h); + } + if (!mSettings.mBody.isEmpty()) { + mMsg->setBody(mSettings.mBody.toUtf8()); + slotOpenComposer(); + } else { + TemplateParser::TemplateParser parser(mMsg, TemplateParser::TemplateParser::NewMessage); + parser.setIdentityManager(KMKernel::self()->identityManager()); + parser.process(KMime::Message::Ptr()); + slotOpenComposer(); + } +} + +void FillComposerJob::slotOpenComposer() +{ + KMail::Composer::TemplateContext context = KMail::Composer::New; + KMime::Content *msgPart = nullptr; + bool iCalAutoSend = false; + bool noWordWrap = false; + bool isICalInvitation = false; + if (!mSettings.mAttachData.isEmpty()) { + isICalInvitation = (mSettings.mAttachName == QLatin1String("cal.ics")) && + mSettings.mAttachType == "text" && + mSettings.mAttachSubType == "calendar" && + mSettings.mAttachParamAttr == "method"; + // Remove BCC from identity on ical invitations (https://intevation.de/roundup/kolab/issue474) + if (isICalInvitation && mSettings.mBcc.isEmpty()) { + mMsg->removeHeader(); + } + if (isICalInvitation && + MessageViewer::MessageViewerSettings::self()->legacyBodyInvites()) { + // KOrganizer invitation caught and to be sent as body instead + mMsg->setBody(mSettings.mAttachData); + mMsg->contentType()->from7BitString( + QStringLiteral("text/calendar; method=%1; " + "charset=\"utf-8\""). + arg(mSettings.mAttachParamValue).toLatin1()); + + iCalAutoSend = true; // no point in editing raw ICAL + noWordWrap = true; // we shant word wrap inline invitations + } else { + // Just do what we're told to do + msgPart = new KMime::Content; + msgPart->contentTransferEncoding()->fromUnicodeString(QLatin1String(mSettings.mAttachCte), "utf-8"); + msgPart->setBody(mSettings.mAttachData); //TODO: check if was setBodyEncoded + msgPart->contentType()->setMimeType(mSettings.mAttachType + '/' + mSettings.mAttachSubType); + msgPart->contentType()->setParameter(QLatin1String(mSettings.mAttachParamAttr), mSettings.mAttachParamValue); //TODO: Check if the content disposition parameter needs to be set! + if (! MessageViewer::MessageViewerSettings::self()->exchangeCompatibleInvitations()) { + msgPart->contentDisposition()->fromUnicodeString(QLatin1String(mSettings.mAttachContDisp), "utf-8"); + } + if (!mSettings.mAttachCharset.isEmpty()) { + // qCDebug(KMAIL_LOG) << "Set attachCharset to" << attachCharset; + msgPart->contentType()->setCharset(mSettings.mAttachCharset); + } + + msgPart->contentType()->setName(mSettings.mAttachName, "utf-8"); + msgPart->assemble(); + // Don't show the composer window if the automatic sending is checked + iCalAutoSend = MessageViewer::MessageViewerSettings::self()->automaticSending(); + } + } + mMsg->assemble(); + + if (!mMsg->body().isEmpty()) { + context = KMail::Composer::NoTemplate; + } + + KMail::Composer *cWin = KMail::makeComposer(KMime::Message::Ptr(), false, false, context); + cWin->setMessage(mMsg, false, false, !isICalInvitation /* mayAutoSign */); + cWin->setSigningAndEncryptionDisabled(isICalInvitation + && MessageViewer::MessageViewerSettings::self()->legacyBodyInvites()); + if (noWordWrap) { + cWin->disableWordWrap(); + } + if (msgPart) { + cWin->addAttach(msgPart); + } + if (isICalInvitation) { + cWin->disableWordWrap(); + cWin->forceDisableHtml(); + cWin->disableForgottenAttachmentsCheck(); + } + if (mSettings.mForceShowWindow || (!mSettings.mHidden && !iCalAutoSend)) { + cWin->show(); + // Activate window - doing this instead of KWin::activateWindow(cWin->winId()); + // so that it also works when called from KMailApplication::newInstance() +#if defined Q_WS_X11 && ! defined K_WS_QTONLY + KStartupInfo::setNewStartupId(cWin, KStartupInfo::startupId()); +#endif + + } else { + // Always disable word wrap when we don't show the composer, since otherwise QTextEdit + // gets the widget size wrong and wraps much too early. + cWin->disableWordWrap(); + cWin->slotSendNow(); + } + deleteLater(); +} + +void FillComposerJob::setSettings(const FillComposerJobSettings &settings) +{ + mSettings = settings; } diff --git a/src/job/fillcomposerjob.h b/src/job/fillcomposerjob.h index d7c9eacd1..a8f24d836 100644 --- a/src/job/fillcomposerjob.h +++ b/src/job/fillcomposerjob.h @@ -21,13 +21,72 @@ #define FILLCOMPOSERJOB_H #include +#include struct FillComposerJobSettings { FillComposerJobSettings() + : mIdentity(0), + mForceShowWindow(false), + mHidden(false) { } + + FillComposerJobSettings(bool hidden, + const QString &to, + const QString &cc, + const QString &bcc, + const QString &subject, + const QString &body, + const QString &attachName, + const QByteArray &attachCte, + const QByteArray &attachData, + const QByteArray &attachType, + const QByteArray &attachSubType, + const QByteArray &attachParamAttr, + const QString &attachParamValue, + const QByteArray &attachContDisp, + const QByteArray &attachCharset, + unsigned int identity, + bool forceShowWindow) + : mTo(to), + mCc(cc), + mBcc(bcc), + mSubject(subject), + mBody(body), + mAttachName(attachName), + mAttachCte(attachCte), + mAttachData(attachData), + mAttachType(attachType), + mAttachSubType(attachSubType), + mAttachParamAttr(attachParamAttr), + mAttachParamValue(attachParamValue), + mAttachContDisp(attachContDisp), + mAttachCharset(attachCharset), + mIdentity(identity), + mForceShowWindow(forceShowWindow), + mHidden(hidden) + { + + } + QString mTo; + QString mCc; + QString mBcc; + QString mSubject; + QString mBody; + QString mAttachName; + QByteArray mAttachCte; + QByteArray mAttachData; + QByteArray mAttachType; + QByteArray mAttachSubType; + QByteArray mAttachParamAttr; + QString mAttachParamValue; + QByteArray mAttachContDisp; + QByteArray mAttachCharset; + unsigned int mIdentity; + bool mForceShowWindow; + bool mHidden; }; @@ -38,8 +97,12 @@ public: explicit FillComposerJob(QObject *parent = nullptr); ~FillComposerJob(); void start(); + void setSettings(const FillComposerJobSettings &settings); + private: + void slotOpenComposer(); FillComposerJobSettings mSettings; + KMime::Message::Ptr mMsg; }; #endif // FILLCOMPOSERJOB_H diff --git a/src/kmcommands.cpp b/src/kmcommands.cpp index fd8fd3f34..50e1613cc 100644 --- a/src/kmcommands.cpp +++ b/src/kmcommands.cpp @@ -150,15 +150,6 @@ using namespace KMime; using namespace MailCommon; -/// Small helper function to get the composer context from a reply -static KMail::Composer::TemplateContext replyContext(MessageFactory::MessageReply reply) -{ - if (reply.replyAll) { - return KMail::Composer::ReplyToAll; - } else { - return KMail::Composer::Reply; - } -} /// Helper to sanely show an error message for a job static void showJobError(KJob *job) @@ -908,31 +899,17 @@ KMCommand::Result KMForwardCommand::createComposer(const Akonadi::Item &item) #ifndef QT_NO_CURSOR KPIM::KCursorSaver busy(KPIM::KBusyPtr::busy()); #endif - MessageFactory factory(msg, item.id(), MailCommon::Util::updatedCollection(item.parentCollection())); - factory.setIdentityManager(KMKernel::self()->identityManager()); - factory.setFolderIdentity(MailCommon::Util::folderIdentity(item)); - factory.setSelection(mSelection); - if (!mTemplate.isEmpty()) { - factory.setTemplate(mTemplate); - } - KMime::Message::Ptr fwdMsg = factory.createForward(); - uint id = 0; - if (auto hrd = msg->headerByType("X-KMail-Identity")) { - id = hrd->asUnicodeString().trimmed().toUInt(); - } - qCDebug(KMAIL_LOG) << "mail" << msg->encodedContent(); - bool lastEncrypt = false; - bool lastSign = false; - KMail::Util::lastEncryptAndSignState(lastEncrypt, lastSign, msg); + CreateForwardMessageJobSettings settings; + settings.mItem = item; + settings.mMsg = msg; + settings.mIdentity = mIdentity; + settings.mTemplate = mTemplate; + settings.mSelection = mSelection; - if (id == 0) { - id = mIdentity; - } - { - KMail::Composer *win = KMail::makeComposer(fwdMsg, lastSign, lastEncrypt, KMail::Composer::Forward, id, QString(), mTemplate); - win->show(); - } + CreateForwardMessageJob *job = new CreateForwardMessageJob; + job->setSettings(settings); + job->start(); return OK; } diff --git a/src/kmkernel.cpp b/src/kmkernel.cpp index 3586c6f50..1bec70b2f 100644 --- a/src/kmkernel.cpp +++ b/src/kmkernel.cpp @@ -7,6 +7,7 @@ #include "job/opencomposerjob.h" #include "job/newmessagejob.h" #include "job/opencomposerhiddenjob.h" +#include "job/fillcomposerjob.h" #include using KPIM::BroadcastStatus; #include "kmstartup.h" @@ -574,27 +575,11 @@ void KMKernel::openComposer(const QString &to, const QString &cc, const QByteArray &attachCharset, unsigned int identity) { - KMail::Composer *cWin; - bool iCalAutoSend = fillComposer(cWin, to, cc, bcc, - subject, body, - attachName, attachCte, attachData, - attachType, attachSubType, attachParamAttr, attachParamValue, - attachContDisp, attachCharset, identity); - - if (!hidden && !iCalAutoSend) { - cWin->show(); - // Activate window - doing this instead of KWin::activateWindow(cWin->winId()); - // so that it also works when called from KMailApplication::newInstance() -#if defined Q_WS_X11 && ! defined K_WS_QTONLY - KStartupInfo::setNewStartupId(cWin, KStartupInfo::startupId()); -#endif - } else { - - // Always disable word wrap when we don't show the composer, since otherwise QTextEdit - // gets the widget size wrong and wraps much too early. - cWin->disableWordWrap(); - cWin->slotSendNow(); - } + fillComposer(hidden, to, cc, bcc, + subject, body, + attachName, attachCte, attachData, + attachType, attachSubType, attachParamAttr, attachParamValue, + attachContDisp, attachCharset, identity, false); } void KMKernel::openComposer(const QString &to, const QString &cc, @@ -611,23 +596,18 @@ void KMKernel::openComposer(const QString &to, const QString &cc, const QByteArray &attachCharset, unsigned int identity) { - KMail::Composer *cWin; - fillComposer(cWin, to, cc, bcc, + fillComposer(false, to, cc, bcc, subject, body, attachName, attachCte, attachData, attachType, attachSubType, attachParamAttr, attachParamValue, - attachContDisp, attachCharset, identity); - cWin->show(); - // Activate window - doing this instead of KWin::activateWindow(cWin->winId()); - // so that it also works when called from KMailApplication::newInstance() -#if defined Q_WS_X11 && ! defined K_WS_QTONLY - KStartupInfo::setNewStartupId(cWin, KStartupInfo::startupId()); -#endif + attachContDisp, attachCharset, identity, true); } -bool KMKernel::fillComposer(KMail::Composer *&cWin, - const QString &to, const QString &cc, - const QString &bcc, const QString &subject, +void KMKernel::fillComposer(bool hidden, + const QString &to, + const QString &cc, + const QString &bcc, + const QString &subject, const QString &body, const QString &attachName, const QByteArray &attachCte, @@ -638,105 +618,29 @@ bool KMKernel::fillComposer(KMail::Composer *&cWin, const QString &attachParamValue, const QByteArray &attachContDisp, const QByteArray &attachCharset, - unsigned int identity) + unsigned int identity, + bool forceShowWindow) { - KMail::Composer::TemplateContext context = KMail::Composer::New; - KMime::Message::Ptr msg(new KMime::Message); - KMime::Content *msgPart = nullptr; - MessageHelper::initHeader(msg, identityManager()); - msg->contentType()->setCharset("utf-8"); - if (!cc.isEmpty()) { - msg->cc()->fromUnicodeString(cc, "utf-8"); - } - if (!bcc.isEmpty()) { - msg->bcc()->fromUnicodeString(bcc, "utf-8"); - } - if (!subject.isEmpty()) { - msg->subject()->fromUnicodeString(subject, "utf-8"); - } - if (!to.isEmpty()) { - msg->to()->fromUnicodeString(to, "utf-8"); - } - if (identity > 0) { - KMime::Headers::Generic *h = new KMime::Headers::Generic("X-KMail-Identity"); - h->from7BitString(QByteArray::number(identity)); - msg->setHeader(h); - } - if (!body.isEmpty()) { - msg->setBody(body.toUtf8()); - } else { - TemplateParser::TemplateParser parser(msg, TemplateParser::TemplateParser::NewMessage); - parser.setIdentityManager(KMKernel::self()->identityManager()); - parser.process(KMime::Message::Ptr()); - } - - bool iCalAutoSend = false; - bool noWordWrap = false; - bool isICalInvitation = false; - if (!attachData.isEmpty()) { - isICalInvitation = (attachName == QLatin1String("cal.ics")) && - attachType == "text" && - attachSubType == "calendar" && - attachParamAttr == "method"; - // Remove BCC from identity on ical invitations (https://intevation.de/roundup/kolab/issue474) - if (isICalInvitation && bcc.isEmpty()) { - msg->removeHeader(); - } - if (isICalInvitation && - MessageViewer::MessageViewerSettings::self()->legacyBodyInvites()) { - // KOrganizer invitation caught and to be sent as body instead - msg->setBody(attachData); - msg->contentType()->from7BitString( - QStringLiteral("text/calendar; method=%1; " - "charset=\"utf-8\""). - arg(attachParamValue).toLatin1()); - - iCalAutoSend = true; // no point in editing raw ICAL - noWordWrap = true; // we shant word wrap inline invitations - } else { - // Just do what we're told to do - msgPart = new KMime::Content; - msgPart->contentTransferEncoding()->fromUnicodeString(QLatin1String(attachCte), "utf-8"); - msgPart->setBody(attachData); //TODO: check if was setBodyEncoded - msgPart->contentType()->setMimeType(attachType + '/' + attachSubType); - msgPart->contentType()->setParameter(QLatin1String(attachParamAttr), attachParamValue); //TODO: Check if the content disposition parameter needs to be set! - if (! MessageViewer::MessageViewerSettings::self()->exchangeCompatibleInvitations()) { - msgPart->contentDisposition()->fromUnicodeString(QLatin1String(attachContDisp), "utf-8"); - } - if (!attachCharset.isEmpty()) { - // qCDebug(KMAIL_LOG) << "Set attachCharset to" << attachCharset; - msgPart->contentType()->setCharset(attachCharset); - } - - msgPart->contentType()->setName(attachName, "utf-8"); - msgPart->assemble(); - // Don't show the composer window if the automatic sending is checked - iCalAutoSend = MessageViewer::MessageViewerSettings::self()->automaticSending(); - } - } - - msg->assemble(); - - if (!msg->body().isEmpty()) { - context = KMail::Composer::NoTemplate; - } - - cWin = KMail::makeComposer(KMime::Message::Ptr(), false, false, context); - cWin->setMessage(msg, false, false, !isICalInvitation /* mayAutoSign */); - cWin->setSigningAndEncryptionDisabled(isICalInvitation - && MessageViewer::MessageViewerSettings::self()->legacyBodyInvites()); - if (noWordWrap) { - cWin->disableWordWrap(); - } - if (msgPart) { - cWin->addAttach(msgPart); - } - if (isICalInvitation) { - cWin->disableWordWrap(); - cWin->forceDisableHtml(); - cWin->disableForgottenAttachmentsCheck(); - } - return iCalAutoSend; + const FillComposerJobSettings settings(hidden, + to, + cc, + bcc, + subject, + body, + attachName, + attachCte, + attachData, + attachType, + attachSubType, + attachParamAttr, + attachParamValue, + attachContDisp, + attachCharset, + identity, + forceShowWindow); + FillComposerJob *job = new FillComposerJob; + job->setSettings(settings); + job->start(); } void KMKernel::openComposer(const QString &to, const QString &cc, diff --git a/src/kmkernel.h b/src/kmkernel.h index ddc14dc34..2b84895a5 100644 --- a/src/kmkernel.h +++ b/src/kmkernel.h @@ -540,9 +540,8 @@ private: /* * Fills a composer cWin * - * @returns true if attached message is a valid iCal message */ - bool fillComposer(KMail::Composer *&cWin, + void fillComposer(bool hidden, const QString &to, const QString &cc, const QString &bcc, const QString &subject, const QString &body, @@ -555,7 +554,7 @@ private: const QString &attachParamValue, const QByteArray &attachContDisp, const QByteArray &attachCharset, - unsigned int identity); + unsigned int identity, bool forceShowWindow); void verifyAccount(); void resourceGoOnLine();