File indexing completed on 2024-05-12 05:17:22

0001 /*
0002     Copyright (c) 2009 Kevin Ottens <ervin@kde.org>
0003     Copyright (c) 2017 Christian Mollekopf <mollekopf@kolabsys.com>
0004 
0005     This library is free software; you can redistribute it and/or modify it
0006     under the terms of the GNU Library General Public License as published by
0007     the Free Software Foundation; either version 2 of the License, or (at your
0008     option) any later version.
0009 
0010     This library is distributed in the hope that it will be useful, but WITHOUT
0011     ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
0012     FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Library General Public
0013     License for more details.
0014 
0015     You should have received a copy of the GNU Library General Public License
0016     along with this library; see the file COPYING.LIB.  If not, write to the
0017     Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
0018     02110-1301, USA.
0019 */
0020 
0021 #ifndef KIMAP2_FETCHJOB_H
0022 #define KIMAP2_FETCHJOB_H
0023 
0024 #include "kimap2_export.h"
0025 
0026 #include "imapset.h"
0027 #include "job.h"
0028 
0029 #include <kmime/kmime_content.h>
0030 #include <kmime/kmime_message.h>
0031 
0032 namespace KIMAP2
0033 {
0034 
0035 class Session;
0036 struct Message;
0037 class FetchJobPrivate;
0038 
0039 typedef QSharedPointer<KMime::Content> ContentPtr;
0040 typedef QMap<QByteArray, ContentPtr> MessageParts;
0041 
0042 typedef QSharedPointer<KMime::Message> MessagePtr;
0043 typedef QList<QByteArray> MessageFlags;
0044 
0045 typedef QPair<QByteArray, QVariant> MessageAttribute;
0046 typedef QList<MessageAttribute> MessageAttributes;
0047 
0048 /**
0049  * Fetch message data from the server
0050  *
0051  * All data is returned using the signals, so you need to connect to
0052  * the relevant signal (or all of them) before starting the job.
0053  *
0054  * This job will always use BODY.PEEK rather than BODY to fetch message
0055  * content, so it will not set the \Seen flag.
0056  *
0057  * This job can only be run when the session is in the selected state.
0058  */
0059 class KIMAP2_EXPORT FetchJob : public Job
0060 {
0061     Q_OBJECT
0062     Q_DECLARE_PRIVATE(FetchJob)
0063 
0064     friend class SessionPrivate;
0065 
0066 public:
0067     /**
0068      * Used to indicate what message data should be fetched.
0069      *
0070      * This doesn't provide the same fine-grained control over
0071      * what is fetched that the IMAP FETCH command normally
0072      * does, but the common cases are catered for.
0073      */
0074     class KIMAP2_EXPORT FetchScope
0075     {
0076     public:
0077         FetchScope();
0078 
0079         /**
0080          * Used to indicate what part of the message should be fetched.
0081          */
0082         enum Mode {
0083             /**
0084              * Fetch RFC-2822 or MIME message headers.
0085              *
0086              * To fetch MIME headers for a MIME part, populate the @p parts field.
0087              *
0088              * If the RFC-2822 headers are requested (so @p parts is empty), the
0089              * returned information is:
0090              * - To, From, Message-id, References In-Reply-To, Subject and Date headers
0091              * - The message size (in octets)
0092              * - The internal date of the message
0093              * - The message flags
0094              * - The message UID
0095              */
0096             Headers,
0097             /**
0098              * Fetch the message flags (the UID is also fetched)
0099              */
0100             Flags,
0101             /**
0102              * Fetch the MIME message body structure (the UID is also fetched)
0103              */
0104             Structure,
0105             /**
0106              * Fetch the message content (the UID is also fetched)
0107              *
0108              * To fetch only certain MIME parts (see Structure), populate the
0109              * @p parts field.
0110              */
0111             Content,
0112             /**
0113              * Fetch the complete message.
0114              */
0115             Full,
0116             /**
0117              * Fetch the message MIME headers and the content of parts specified in the @p parts
0118              * field.
0119              *
0120              * If @p parts is empty, this mode will return the full message, just like
0121              * FetchScope::Content
0122              *
0123              * Use case:
0124              * -# Start a FetchJob with the FetchScope::Structure mode to retrieve the structure
0125              *    of the message.
0126              * -# Parse the structure to identify the parts that are interesting (ie: probably
0127              *    everything but attachments).
0128              * -# Start another FetchJob with FetchScope::HeaderAndContent to fetch those parts.
0129              * -# At the request of the user, you can repeat the step above to fetch the attachments.
0130              */
0131             HeaderAndContent,
0132 
0133             /**
0134              * Fetch message size (in octets), internal date of the message, flags, UID
0135              * and all RFC822 headers.
0136              *
0137              * The @p parts field is ignored when using this scope
0138              */
0139             FullHeaders
0140         };
0141 
0142         /**
0143          * Specify which message parts to operate on.
0144          *
0145          * This refers to multipart-MIME message parts or MIME-IMB encapsulated
0146          * message parts.
0147          *
0148          * Note that this is ignored unless @p mode is Headers or Content.
0149          *
0150          * If @p mode is Headers, this sets the parts to get the MIME headers
0151          * for.  If this list is empty, the headers for the whole message
0152          * (the RFC-2822 headers) are fetched.
0153          *
0154          * If @p mode is Content, this sets the parts to fetch.  Parts are
0155          * fetched wholesale.  If this list is empty, the whole message body
0156          * is fetched (all MIME parts together).
0157          */
0158         QList<QByteArray> parts;
0159 
0160         /**
0161          * Specify what message data should be fetched.
0162          */
0163         Mode mode;
0164 
0165         /**
0166          * Specify to fetch only items with mod-sequence higher then @p changedSince.
0167          *
0168          * The server must have CONDSTORE capability (RFC4551).
0169          *
0170          * Default value is 0 (ignored).
0171          *
0172          */
0173         quint64 changedSince;
0174 
0175         /**
0176         * Enables retrieving of Gmail-specific extensions
0177         *
0178         * The FETCH response will contain X-GM-MSGID, X-GM-THRID and X-GM-LABELS
0179         *
0180         * Do NOT enable this, unless talking to Gmail servers, otherwise the
0181         * request may fail.
0182         */
0183         bool gmailExtensionsEnabled;
0184     };
0185 
0186     class KIMAP2_EXPORT Result
0187     {
0188     public:
0189         qint64 sequenceNumber;
0190         qint64 uid;
0191         qint64 size;
0192         KIMAP2::MessageFlags flags;
0193         KIMAP2::MessagePtr message;
0194         KIMAP2::MessageParts parts;
0195         KIMAP2::MessageAttributes attributes;
0196     };
0197 
0198     explicit FetchJob(Session *session);
0199     virtual ~FetchJob();
0200 
0201     /**
0202      * Set which messages to fetch data for.
0203      *
0204      * If sequence numbers are given, isUidBased() should be false.  If UIDs
0205      * are given, isUidBased() should be true.
0206      *
0207      * @param set  the sequence numbers or UIDs of the messages to fetch data for
0208      */
0209     void setSequenceSet(const ImapSet &set);
0210     /**
0211      * The messages that will be fetched.
0212      */
0213     ImapSet sequenceSet() const;
0214 
0215     /**
0216      * Set how the sequence set should be interpreted.
0217      *
0218      * @param uidBased  if @c true the argument to setSequenceSet will be
0219      *                  interpreted as UIDs, if @c false it will be interpreted
0220      *                  as sequence numbers
0221      */
0222     void setUidBased(bool uidBased);
0223     /**
0224      * How to interpret the sequence set.
0225      *
0226      * @return  if @c true the result of sequenceSet() should be
0227      *          interpreted as UIDs, if @c false it should be interpreted
0228      *          as sequence numbers
0229      */
0230     bool isUidBased() const;
0231 
0232     /**
0233      * Sets what data should be fetched.
0234      *
0235      * The default scope is FetchScope::Content (all content parts).
0236      *
0237      * @param scope  a FetchScope object describing what data
0238      *               should be fetched
0239      */
0240     void setScope(const FetchScope &scope);
0241     /**
0242      * Specifies what data will be fetched.
0243      */
0244     FetchScope scope() const;
0245 
0246     /**
0247      * Avoid calling parse() on returned KMime::Messages
0248      */
0249     void setAvoidParsing(bool);
0250 
0251 Q_SIGNALS:
0252     void resultReceived(const Result &);
0253 
0254 protected:
0255     void doStart() Q_DECL_OVERRIDE;
0256     void handleResponse(const Message &response) Q_DECL_OVERRIDE;
0257 };
0258 
0259 }
0260 
0261 #endif