Warning, /pim/trojita/docs/masters/extensions.tex is written in an unsupported language. File is not indexed.

0001 % vim: spelllang=en spell textwidth=120
0002 \documentclass[trojita]{subfiles}
0003 
0004 \begin{document}
0005 
0006 \chapter{IMAP Extensions}
0007 \label{sec:imap-extensions}
0008 
0009 It might be concluded from the brief analysis presented in the previous chapter that certain features of the IMAP
0010 protocol are rather limiting in its real-world deployment.  Fortunately, IMAP was designed to include support for
0011 extensions which allow rather substantial changes to its mode of operation.  Throughout this chapter, I provide a
0012 detailed analysis of opportunities where the baseline IMAP protocol leaves something to be desired.  Many such gaps have
0013 been addressed by various extensions over the last twenty years; these extensions are thoroughly explained and evaluated
0014 on their merits.  Information about their support in Trojitá is also included.
0015 
0016 \section{Optimizing the Protocol}
0017 
0018 Before dwelling into more advanced topics like improving the synchronization performance or adding new features, let's
0019 have a look at the basic layer of the IMAP protocol and investigate how these affect performance.
0020 
0021 \subsection{The LITERAL+ Extension}
0022 \label{sec:imap-literalplus}
0023 
0024 One of the lowest-hanging optimization fruit to cater are IMAP's synchronizing literals.  In the basic IMAP, before a
0025 client proceeds with tasks involving upload of binary data (or any data over a certain size, for that matter), it has to
0026 ask for an explicit server's approval based on the length of the data in question.  As it has been shown previously,
0027 this confirmation imposes a full round trip over the network, inducing latency and destroying any potential pipelining
0028 improvements.
0029 
0030 The LITERAL+ extension (RFC~2088~\cite{rfc2088}) simply lifts the requirement of having to wait for the server's
0031 continuation requests by a subtle change of the syntax.  Adding an overhead of just one byte, the latency is completely
0032 eliminated and communication gets rapidly streamlined.  One can go as far as to say that the code paths for dealing with
0033 LITERAL+ data are actually simpler than having to deal with the old-fashioned synchronizing literals.  Consider the
0034 following example:
0035 
0036 \begin{minted}{text}
0037   S: * OK
0038   C: A001 LOGIN {11}
0039   # The client has to wait for server's response before proceeding any further
0040   S: + go ahead
0041   C: FRED FOOBAR {7}
0042   # A second round-trip wait occurs here
0043   S: + go ahead
0044   C: fat man
0045   S: A001 OK LOGIN completed
0046 \end{minted}
0047 
0048 When using the LITERAL+ syntax, the whole interaction happens without having to wait for the server:
0049 
0050 \begin{minted}{text}
0051   S: * OK
0052   C: A001 LOGIN {11+}
0053   C: FRED FOOBAR {7+}
0054   C: fat man
0055   S: A001 OK LOGIN completed
0056 \end{minted}
0057 
0058 \begin{trojitabehavior}
0059 Trojitá includes full support for the LITERAL+ extension --- when it detects the {\tt LITERAL+} capability, it will
0060 immediately switch to using non-synchronizing literals for increased performance.
0061 \end{trojitabehavior}
0062 
0063 \subsection{Data Compression}
0064 
0065 IMAP is a textual, line-based protocol.  As such, it presents extremely good opportunities for compression --- using the
0066 tried DEFLATE algorithm~\cite{rfc1951}, the basic IMAP chatter can be easily compressed to 25~-~40~\% of its original
0067 size~\cite[p. 4]{rfc4978}.  RFC~4978~\cite{rfc4978} provides mechanism for exactly this functionality through the {\tt
0068 COMPRESS=DEFLATE} capability.
0069 
0070 \begin{trojitabehavior}
0071 Trojitá ships with full support for this extension through the permissively licensed {\tt zlib} library.  Unfortunately,
0072 the Qt's {\tt QSslSocket} currently doesn't provide a way to reliably tell whether the SSL connection is already
0073 employing compression.  When combined with IMAP servers hidden behind SSL accelerators or load balancers (i.e. in
0074 situations where the server does not have a clear idea whether the session is already compressed either), this has a
0075 risk of needlessly trying to compress data twice.  This is a limitation in system libraries which cannot be overcome
0076 without resorting to patching system components or conducting non-portable hacks.
0077 \end{trojitabehavior}
0078 
0079 \subsection{Improving Security through Cryptography}
0080 
0081 RFC~2595~\cite{rfc2595} deals with best practices for establishing SSL/TLS connections to the IMAP server.
0082 
0083 \begin{trojitabehavior}
0084 Trojitá
0085 follows these recommendations, most notably it tries to establish a secure channel over {\tt STARTTLS} command even
0086 without an explicit action on the user's side, should the server be configured to advertise itself as not accepting
0087 logins over insecure connections through the {\tt LOGINDISABLED} capability.  A manual override is available in
0088 situations where the SSL encryption is not available.
0089 
0090 In advent of the recent breaches of many well-known (and widely trusted) Certificate Authorities~\cite{ssl-breaches},
0091 Trojitá also comes with support for SSL key pinning~\cite{ssl-pinning}.  The trust model presented to the user is
0092 similar to handling of SSH servers' public keys with OpenSSH --- upon first connection, the user is always presented with
0093 a choice of whether to accept the certificate or not, along with a confirmation about whether the operating system and
0094 its policy considers the certificate as ``trusted''.  No matter what the system-wide policy says, a changed public key
0095 is always considered a threat and the situation is presented to the user accordingly.
0096 \end{trojitabehavior}
0097 
0098 \subsection{The IDLE Mode}
0099 \label{sec:imap-idle}
0100 
0101 I have mentioned that even though the protocol requires clients to be ready to accept any responses at any time, in
0102 practice, servers are forbidden to send {\tt EXPUNGE}s when no command is in progress.  This requirement is necessary to
0103 prevent a dangerous resynchronization as the server cannot possibly know whether the client has started to issue an
0104 UID-less {\tt STORE} command which references messages through their sequence numbers.  Unfortunately, this directly
0105 translates to clients having to {\em poll} the server quite often if they care about updates concerning the deleted
0106 messages.
0107 
0108 Any protocol which uses polling looks bad on paper --- having to poll leads to increased latency and higher power usage
0109 because the equipment has to actively check for updates every now and then.  In contrast, {\em push-based} updates allow
0110 the client to enter a low-power state where it merely waits to be woken up when a change occurs.  Such a mode is exactly
0111 what the IDLE extension defined by RFC~2177~\cite{rfc2177} adds to IMAP.  It must, however, be said that real-world
0112 concerns related to firewall timeouts and especially the NAT traversal has limited the usefulness of the IDLE command
0113 somewhat, even to the extent where Mark Crispin, the original author of the IMAP protocol, claims that ``I see no
0114 particular benefit to use of IDLE on a desktop machine''~\cite{crispin-idle-useless} --- a view which is not shared by
0115 the wider community~\cite{tss-idle-keepalive} \cite{android-idle}, yet certainly worth a consideration.
0116 
0117 The IDLE extension is basically a hack on top of the IMAP protocol which reverses a mantra of the basic IMAP
0118 specification~\cite[p. 72]{rfc3501}:
0119 
0120 \begin{quote}
0121   A command is not ``in progress'' until the complete command has been received; in particular, a command is not ``in
0122   progress'' during the negotiation of command continuation.
0123 \end{quote}
0124 
0125 With IDLE, a typical interaction might look like this one:
0126 
0127 \begin{minted}{text}
0128   C: A004 IDLE
0129   S: * 2 EXPUNGE
0130   S: * 3 EXISTS
0131   S: + idling
0132   ...time passes; another client expunges message 3...
0133   S: * 3 EXPUNGE
0134   S: * 2 EXISTS
0135   ...time passes; new mail arrives...
0136   S: * 3 EXISTS
0137   C: DONE
0138   S: A004 OK IDLE terminated
0139   C: A005 FETCH 3 ALL
0140   S: * 3 FETCH (...)
0141   S: A005 OK FETCH completed
0142   C: A006 IDLE
0143 \end{minted}
0144 
0145 The whole effect of the {\tt IDLE} command is therefore to indicate to the server that the client is {\em really}
0146 willing to listen for any updates to the mailbox state.  Because of compatibility concerns with legacy mail stores, the
0147 IDLE extension still does {\em not} mandate the server to actually send updates about any changes as soon as they are
0148 conducted --- indeed, a server which internally polls every fifteen minutes to check whether a message has arrived is
0149 fully compliant with the IDLE extension, albeit rather useless to user who might expect (and, one might add, rightly so)
0150 to be {\em instantly} notified about changes to the mailbox.
0151 
0152 \begin{trojitabehavior}
0153 Trojitá includes full support for the IDLE extension and will enter that mode automatically shortly after a mailbox is
0154 selected.  A simple heuristics is implemented which delays re-entering the IDLE command if it is likely that the
0155 connection will be reused for any other purpose in near future, further eliminating needless data transfers.
0156 Unfortunately, Trojitá is at the mercy of the IMAP server when it comes to superfluous data transfers, so it cannot
0157 prevent the ``pings'' sent even when the connection does not contain a gateway with overly short timeouts.
0158 \end{trojitabehavior}
0159 
0160 \section{Improving Mailbox Synchronization}
0161 
0162 The previous section dealt with optimizing the overall IMAP protocol as a whole.  At this stage, let's have a look at
0163 more specific issues which cannot be easily overcome through generic measures like data compression using off-the-shelf
0164 algorithms or updates to the basic protocol flows.
0165 
0166 In the basic IMAP, neither the server nor the client are required to keep any persistent state.  Clearly, it is
0167 beneficiary for a client to keep downloaded copies of the immutable mailbox/message data (consult
0168 \secref{sec:imap-immutable-data} in its persistent cache for some time, should the device constraints allow such a
0169 storage.  There is still quite a lot of other data which has to be validated while the mailbox is being resynchronized.
0170 Consider the following scenario where a mail user agent opens a mailbox with a thousand of messages which has witnessed
0171 expunges and new arrivals since the last time it was opened:
0172 
0173 \begin{minted}{text}
0174   C: y1 SELECT foo
0175   S: * 1000 EXISTS
0176   S: * OK [UIDVALIDITY 12345] UIDs valid
0177   S: * OK [UIDNEXT 2345] Next UID
0178   S: y1 OK Selected
0179   C: y2 UID SEARCH ALL
0180 
0181     The following response has been shortened for demonstration purposes. In
0182     practice, it will have to contain a thousand of numbers.
0183 
0184   S: * SEARCH 2 4 5 6 7 8 9 10 ... 2290 2310 2311 2312 2333
0185   S: y2 OK Search completed
0186   C: y3 FETCH 1:1000 (FLAGS)
0187   S: * 1 FETCH (FLAGS ())
0188   S: * 2 FETCH (FLAGS (\\Seen))
0189   S: * 3 FETCH (FLAGS (\\Recent \$Answered))
0190 
0191     996 additional FETCH responses were omitted from this example for brevity.
0192 
0193   S: * 1000 FETCH (FLAGS (\\Seen))
0194   S: y3 OK fetched
0195 \end{minted}
0196 
0197 Let's identify two steps which substantially contribute to the transferred data:
0198 
0199 \begin{itemize}
0200   \item synchronizing the UIDs,
0201   \item updating flags.
0202 \end{itemize}
0203 
0204 The rest of this section takes a look at optimization opportunities at each of these stages.  Please keep in mind that
0205 some basic optimization heuristics concerning the UID synchronization were discussed in \secref{sec:imap-mailbox-sync}
0206 along with reasons on why these steps are necessary in clients willing to maintain an offline cache of immutable data.
0207 
0208 \subsection{The ESEARCH Extension}
0209 
0210 As seen in the protocol sample, the {\tt SEARCH} response containing UIDs of all messages in a mailbox can be rather
0211 large.  At the same time, chances are that at least some of the adjacent messages might have been assigned contiguous
0212 UIDs --- this is certainly not a requirement per se, but quite a few IMAP servers internally {\em do} assign UIDs from a
0213 per-mailbox counter.  Real-world, albeit anecdotal evidence \cite{cridland-uids-are-often-monotonic} indicates that this
0214 scenario is very common, and therefore it might make sense to transmit the UIDs of all messages using the {\tt
0215 sequence-set} \cite[p. 89]{rfc3501} syntax.  The ESEARCH extension, as defined in RFC~4731~\cite{rfc4731}, allows
0216 exactly that:
0217 
0218 \begin{minted}{text}
0219   S: * ESEARCH [TAG "y12"] UID 1,3:9,17:25,30:1000
0220 \end{minted}
0221 
0222 At the time of the ESEARCH adoption, the imap-protocol mailing list witnessed a disagreement on how exactly the {\tt
0223 sequence-set} shall be interpreted.  Mark Crispin, the author of the original IMAP protocol (but not of the ESEARCH
0224 extension) implemented ESEARCH in a different manner.  He chose to take an advantage of the RFC3501-style definition of
0225 UID sequences where the RFC mandates that servers shall treat non-existent UIDs given in sequence sets as if they
0226 weren't referenced from the command at all.  For example, if the mailbox contained just UIDs 3, 5 and 10, a client using
0227 the {\tt 3:10} construct has to be interpreted as if it requested {\tt sequence-set 3,5,10}.  Doing so present certain
0228 optimization opportunities to the servers, for example when the client already knows the UID mapping and performs a
0229 server-side search for messages matching certain criteria {\em and} the result set accurately matches an adjacent range
0230 of messages, the server could take advantage of this adjacency a return a {\tt sequence-set} in the form of {\tt
0231 10:150}, even though the mailbox contains only a few UIDs from this range~\cite{crispin-esearch-flawed}.  Furthermore,
0232 his another point is that the clients already have two other ways of obtaining the UID mapping, either through the {\tt
0233 UID SEARCH ALL} command or via an explicit {\tt UID FETCH 1:*}.  Needless to say, such a reasoning fails to take into
0234 account potential bandwidth savings which can be rather substantial on ``reasonable'' mailboxes.  In the end, the
0235 authors of the RFC 4731 disagreed with Crispin \cite{melnikov-esearch-interpretation}
0236 \cite{cridland-esearch-interpretation}.
0237 
0238 \begin{trojitabehavior}
0239 The ESEARCH extension allows nice bandwidth savings, so Trojitá tries to use it if the server says that it is supported.
0240 \end{trojitabehavior}
0241 
0242 In addition to that, format of the returned responses is changed so that it also includes the tag of the command which
0243 caused it, allowing much more aggressive pipelining --- for example, clients are free to perform the UID discovery at the
0244 same time as running a user-initiated search.  On the other hand, even in presence of ESEARCH, the UID mapping still has
0245 to be synchronized explicitly.  This requirement is only lifted in the QRESYNC extension
0246 (\secref{sec:extension-qresync}).  Before describing that, though, it is necessary to have a look at the CONDSTORE.
0247 
0248 \subsection{Avoiding Flags Resynchronization via CONDSTORE}
0249 
0250 Leaving the UID synchronization alone for a while, let's have a look at various ways of eliminating the need to ask for
0251 changed message flags.  In this case, no extension trying to reduce the data overhead of the {\tt FETCH} response was
0252 proposed, but the problem got attacked from another side.
0253 
0254 The whole point of flags synchronization is to be able to pick up changes which have happened since the last time the
0255 mailbox was selected.  If only the server was somehow able to assign a ``serial number'' to each change, clients could
0256 subsequently ask for all changes which have happened after a certain point.  The CONDSTORE extension from RFC 4551
0257 \cite{rfc4551} works in this way.
0258 
0259 CONDSTORE-capable servers share a concept of ``modification sequence'', a {\tt MODSEQ}.  Each message in a mailbox is
0260 assigned an unsigned 64bit integer.  Whenever message metadata (like its flags) change, the {\tt MODSEQ} of that
0261 particular message gets increased.  Each increment is also required to reach a value which is higher than {\tt MODSEQ}
0262 of any other message in that mailbox.  Similarly, a mailbox is assigned a {\tt HIGHESTMODSEQ}, an unsigned 64bit integer
0263 which is interpreted as ``no message has ever had a {\tt MODSEQ} higher than this number'' --- of course subject to the
0264 usual {\tt UIDVALIDITY} rules.~\footnote{As always, any change in {\tt UIDVALIDITY} directly translates to a full cache
0265 flush and discarding any data previously remembered for the affected mailbox.  This includes not only the immutable data
0266 of messages, but also the UIDs, message flags and --- in this extension --- the {\tt MODSEQ} and {\tt HIGHESTMODSEQ}
0267 values.}
0268 
0269 When a CONDSTORE-capable client opens a mailbox which was previously synced (and if the server supports CONDSTORE as
0270 well, of course --- keep in mind that the IMAP extensions are strictly voluntary in their nature), at first it synces the
0271 UID mapping as usual, possibly through the ESEARCH command discussed earlier.  After that, the client can use an
0272 extended variant of the {\tt FETCH} command to ask for flags of those messages whose {\em current} {\tt MODSEQ} is
0273 higher than the {\tt HIGHESTMODSEQ} which the client has remembered previously.  The server will respond with regular
0274 {\tt FETCH} responses for each affected message.  In result, after this interaction is completed, the client is aware of
0275 all pending flag changes and is fully resynchronized again.
0276 
0277 This is how a typical synchronization might look like:
0278 
0279 \begin{minted}{text}
0280   C: y1 SELECT foo (CONDSTORE)
0281   S: * 1000 EXISTS
0282   S: * OK [UIDVALIDITY 12345] UIDs valid
0283   S: * OK [UIDNEXT 2345] Next UID
0284   S: * OK [HIGHESTMODSEQ 715194045007]
0285   S: y1 OK Selected
0286 
0287     At this point, the client will obtain the UID mapping, likely through the
0288     UID SEARCH or its ESEARCH variant:
0289 
0290   C: y2 UID SEARCH RETURN () ALL
0291   S: * ESEARCH (TAG "y2") UID ALL 2,4:10,21:1008,2290,2310:2312,2333
0292   S: y2 OK Search completed
0293 
0294     At this point the CONDSTORE extension can be finally utilized -- only changed
0295     flags will be transmitted:
0296 
0297   C: y3 UID FETCH 1:1000 (FLAGS) (CHANGEDSINCE 613184045007)
0298   S: * 997 FETCH (UID 2310 MODSEQ 715194045007 FLAGS (\\Seen \\Deleted))
0299   S: * 1000 FETCH (UID 2333 MODSEQ 715194045005 FLAGS (\\Seen))
0300   S: y3 OK Fetched
0301 \end{minted}
0302 
0303 The algorithm is race-free --- as every message has a separate {\tt MODSEQ} counter, the delay between the {\tt SELECT}
0304 and {\tt FETCH} command doesn't lead to data loss; by the time the {\tt FETCH} completes, the server guarantees that the
0305 client has received any pending updates since the last synchronization.
0306 
0307 The CONDSTORE is an extremely valuable extension; its savings on big mailboxes are predictable and automatic --- instead
0308 of having to transmit $O(n)$ responses where $n$ is the number of {\em messages}, only $O(m)$ are required under QRESYNC
0309 with $m$ being the number of {\em modifications}.  This is an extension which, unfortunately, places a certain burden on
0310 the IMAP server which has to track the serial numbers of messages' metadata; however, given the obvious reductions in
0311 bandwidth, many servers have already implemented it, most notably the Dovecot and Cyrus open source IMAP servers.
0312 
0313 \begin{trojitabehavior}
0314 Trojitá includes full support for this extension, making use of it whenever it is available.
0315 \end{trojitabehavior}
0316 
0317 \subsection{Optimizing UID Synchronization with QRESYNC}
0318 \label{sec:extension-qresync}
0319 
0320 The CONDSTORE extension discussed earlier has brought in the concept of a server-side state tracking and used that to
0321 allow bandwidth-efficient way of synchronizing flag changes.  Given that a CONDSTORE-capable server already tracks
0322 certain state, it might be worthwhile to somehow extend this state to cover the deleted messages as well.  As it turns
0323 out, such a mechanism is implemented in the QRESYNC extension which is defined by RFC 5162 \cite{rfc5162}.
0324 
0325 The basic idea behind QRESYNC is that as long as the UID mapping was fresh at some point in past, it is only necessary
0326 to inform the client about which UIDs from that set are no longer there and push out the UIDs of newly arrived messages.
0327 
0328 The QRESYNC extension modifies the {\tt SELECT command} so that it includes a few more parameters.  First of all, the
0329 updated version of this command includes a tuple of {\tt (UIDNEXT, HIGHESTMODSEQ)} as known to the client.  If the {\tt
0330 UIDNEXT} did not change, the server will have a look at the {\tt HIGHESTMODSEQ} value and in addition to essentially
0331 behaving as a CONDSTORE server, it also sends out a list of expunged messages.~\footnote{Technically, the expunges are
0332 sent out before the information about the updated flags, but that isn't the point here.}  A new response is defined for
0333 this purpose, the {\tt VANISHED EARLIER}.
0334 
0335 In format similar to the {\tt ESEARCH} response, the {\tt VANISHED EARLIER} contains a {\tt sequence-set} of UIDs which
0336 the server believes that the client considers to be present in the mailbox.  Not only are these UIDs transmitted in a
0337 compact syntax, thanks to the {\tt sequence-set} format, but the response typically contains only such UIDs which were
0338 {\em just} removed.  The actual wording (and therefore the implications of this extension) are slightly different --- the
0339 server is free to inform the clients about any UIDs, as long as they aren't in the mailbox right now, at the time of the
0340 sync.  This is motivated by the need to relieve the servers from having to maintain a list of expunged UIDs
0341 indefinitely, just in case a QRESYNC-enabled client reconnects after two years of inactivity.  When such a situation
0342 happens, a server which cannot remember expunges going so far in history has no other option but to send a {\tt
0343 VANISHED EARLIER} for {\em all} UIDs lower than the {\tt UIDNEXT}, no matter if they {\em ever} were present in the
0344 mailbox.  This fallback suggests that the QRESYNC extension could very well have a negative net effect overall, at least
0345 in certain pathological situations --- essentially when the list of expunges grows so long that the server decides to
0346 prune some of its records.
0347 
0348 In order to mitigate this issue, a few other options were added to QRESYNC.  The first of them is a way of indicating to
0349 the server the range of UIDs about which the client actually cares.  The idea here is that if the client only cached a
0350 subset of messages (for example those with UID higher than 50000), there isn't much point in informing the client about
0351 each and every UID which might had been in the mailbox before (like those 49,999 of UIDs lower than 50,000).
0352 
0353 However, chances are that this optimization is not enough to overcome the danger of having to sync too many UIDs --- and
0354 indeed, some user agents might want to preemptively load messages both from the beginning {\em and} from the end of the
0355 mailbox in an effort to optimize preloading.  Such user agents would not be able to benefit from the ``range of known
0356 UIDs'' optimization.
0357 
0358 Fortunately, the {\tt SELECT QRESYNC} command includes provisions for passing another type of data around --- it is also
0359 possible to provide a representative list of $(sequence, UID)$ pairs.  Using technique similar to the proposed binary
0360 search when discovering UIDs, the client can decide to send along a UID from roughly middle of the mailbox as the first
0361 one, followed by another one located at circa 75~\% of the mapping, next one from $7 \over 8$ etc., halving the interval
0362 in each step.  The concrete strategy to be pursuit is left to the client, as it is basically a policy decision.  Using
0363 more fine-grained interval means that more data is sent along during each resynchronization without a direct merit (i.e.
0364 when the server {\em still} remembers the previous {\tt HIGHESTMODSEQ} and can provide the client with relevant data),
0365 while on the other hand sending less UIDs leads to minor data savings during ordinary reconnects while causing
0366 potentially huge amounts of data to be transfered when the server is unable to use the --- perhaps very old or otherwise
0367 stale --- {\tt HIGHESTMODSEQ}.
0368 
0369 \begin{trojitabehavior}
0370 The presented version of Trojitá always uses halving of sequences, effectively transmitting $log_2(n)$ sequence-UID
0371 pairs:
0372 \end{trojitabehavior}
0373 
0374 \begin{minted}{c++}
0375     Sequence knownSeq, knownUid;
0376     int i = oldUidMap.size() / 2;
0377     while (i < oldUidMap.size()) {
0378         // Message sequence number is one-based, our indexes are zero-based
0379         knownSeq.add(i + 1);
0380         knownUid.add(oldUidMap[i]);
0381         i += (oldUidMap.size() - i) / 2 + 1;
0382     }
0383 \end{minted}
0384 
0385 Our example synchronization (a thousand messages in a mailbox, unspecified changed since the last time) could therefore
0386 look like this --- the client has fresh enough UID mapping up to UID 1008 (sequence number 995).  The server does not
0387 remember deletions so far to the past, but the passed UID mapping fragment could nevertheless be used to optimize the
0388 delivered data:
0389 
0390 \begin{minted}{text}
0391   C: SELECT foo (QRESYNC 12345 613184045007 (500,750,875,937,968,983,990,995,997
0392   512,772,887,949,980,985,995,1002,1008,1111))
0393   S: * 1000 EXISTS
0394   S: * OK [UIDVALIDITY 12345] UIDs valid
0395   S: * OK [UIDNEXT 2345] Next UID
0396   S: * OK [HIGHESTMODSEQ 715194045007]
0397   S: * VANISHED (EARLIER) 1009:2289,2291:2309,2313:2332,2343,2344
0398   S: * 997 FETCH (UID 2310 MODSEQ 715194045007 FLAGS (\\Seen \\Deleted))
0399   S: * 1000 FETCH (UID 2333 MODSEQ 715194045005 FLAGS (\\Seen))
0400   S: y1 OK Selected
0401 \end{minted}
0402 
0403 The received data contain enough information to reconstruct complete UID mapping even under these unfavorable
0404 conditions.  The redundant UID information in the {\tt FETCH} responses can be also used to make sure that both sides of
0405 the connection arrive to the same final state. 
0406 
0407 \begin{trojitabehavior}
0408 Trojitá will throw an error when it detects failure at any time.
0409 \end{trojitabehavior}
0410 
0411 To further reduce the amount of data transmitted during the IMAP session, the QRESYNC extension also introduces a second
0412 kind of the {\tt VANISHED} response --- the one without the {\tt EARLIER} modifier.  Serving as a substitute for the
0413 ordinary {\tt EXPUNGE}, the {\tt VANISHED}'s biggest advantage is that it can inform about multiple expunges in a single
0414 response.  Somewhat ironically, this modification also relieves the clients of their need to maintain a complete
0415 UID-sequence mapping at all times --- but only after providing a method of making this synchronization severely less
0416 painful in the first place.  The whole matter is a bit more complicated by the wording of the RFC which is pretty clear
0417 on that the {\tt VANISHED} responses {\em should} be sent instead of {\tt EXPUNGE} --- a language which, in RFC terms,
0418 means that the servers are supposed to do so, yet the clients are forbidden from relying on such behavior because under
0419 special circumstances, the servers might very well have a good reason to defer back to the {\tt EXPUNGE}~\cite{rfc2119}.
0420 
0421 Unfortunately, the combination of offset-based {\tt EXISTS} (which is a response used to inform the client about growth
0422 of the number of messages in a mailbox) with UID-based {\tt VANISHED} can lead to races, a dangerous condition which I
0423 have identified~\cite{kundrat-vanished-race}.  The problem lies in QRESYNC's allowance for non-existent UIDs to be
0424 included in the {\tt VANISHED} response.  Consider the following scenario where the client is fully synced with a
0425 mailbox with just a single message bearing UID 5.  The mailbox' {\tt UIDNEXT} is 11:
0426 
0427 \begin{minted}{text}
0428   S: * 3 EXISTS
0429   C: x UID FETCH 11:* (FLAGS)
0430   S: * VANISHED 12:20
0431 \end{minted}
0432 
0433 The server is telling the client that any UIDs between 12 and 20 are gone.  The problem is that the client cannot
0434 possibly know whether any message has got any of these particular UIDs, i.e. whether the messages \#2 and \#3 (the first
0435 and second arrival) fall into that range.  Trojitá will immediately send out a request for UIDs of the new arrivals
0436 (that is the {\tt UID FETCH} command in the previous example), but due to the timing issues, it is perfectly possible
0437 that these messages are ``long'' gone (and the appropriate {\tt VANISHED} sent) by the time the server receives the {\tt
0438 UID FETCH} command.  There isn't much that a compliant IMAP client can do at this point besides issuing an explicit
0439 command for finding out whether any new messages have actually remained in the mailbox.  This is a minor deficiency in
0440 the QRESYNC extension which could be easily avoided by replacing the {\tt EXISTS} in manner similar to how {\tt EXPUNGE}
0441 got replaced by {\tt VANISHED}.  The previous example would look like this one, eliminating any possibility of races:
0442 
0443 \begin{minted}{text}
0444   S: * ARRIVED 12,33
0445   C: x UID FETCH 11:* (FLAGS)
0446   S: * VANISHED 12:20
0447 \end{minted}
0448 
0449 The {\tt ARRIVED} command is defined in a proposed draft in \secref{sec:draft-arrived}.  A similar functionality could
0450 be achieved through the NOTIFY extension defined by RFC 5465 \cite{rfc5465}, but supporting NOTIFY is a rather strong
0451 undertaking for an IMAP server and --- as of July 2012 --- support for that extension is still rather
0452 scarce.~\footnote{None of the widely deployed open source IMAP servers supported {\tt NOTIFY} at the time this thesis
0453 was written.  The Dovecot IMAP server had an experimental branch with partial support which would be enough to serve as
0454 a replacement for {\tt ARRIVED}, but it could not be discovered through the IMAP capabilities because {\tt NOTIFY} is an
0455 all-or-nothing extension; it mandates full server support and doesn't include provisions for partial functionality which
0456 would have been enough in this case.}
0457 
0458 The QRESYNC extension also mandates an interesting mechanism for its activation.  The {\tt SELECT \ldots QRESYNC}
0459 command does not work when the IMAP client opens a mailbox for the first time --- the client has no cached state, so it
0460 cannot construct any of the optional arguments to the {\tt QRESYNC} select modifier.  Furthermore, it cannot fabricate a
0461 proper {\tt HIGHESTMODSEQ} in a safe way -- using value too low would result in needlessly sending a huge number of {\tt
0462 VANISHED EARLIER} responses, while using a too high value could confuse the server and treat the client as a buggy one.
0463 This is why a special {\tt ENABLE QRESYNC} command (from the ENABLE extension, RFC~5161 \cite{rfc5161}) is defined to be
0464 a {\em QRESYNC-enabling command}, activating any necessary {\tt MODSEQ} tracking on the server side.  This requirement
0465 might be non-obvious at first, for the {\tt SELECT \ldots QRESYNC} on its own should be sufficient to inform the server
0466 that the client indeed wants to speak QRESYNC.
0467 
0468 Unfortunately, there is also a certain murkiness about the {\tt ENABLE} command --- the errata \#1365 for RFC 5162
0469 \cite{rfc5162-errata} proposes to add an explicit note that ``(A server MUST respond with a tagged BAD
0470 response if) (\ldots) or the server has not positively responded to that command with "ENABLED QRESYNC", in the current
0471 connection'', even though the RFC 5161 explicitly allows for aggressive pipelining of {\tt ENABLE} and {\tt
0472 SELECT}.~\footnote{``There are no limitations on pipelining ENABLE.  For example, it is possible to send ENABLE and then
0473 immediately SELECT, or a LOGIN immediately followed by ENABLE. \cite[p. 2]{rfc5161}}  I have raised this issue on the
0474 {\tt imap-protocol} mailing list and the consensus there was that it is indeed allowed not to wait for the server's {\tt
0475 ENABLED} before issuing a {\tt SELECT \ldots QRESYNC} \cite{melnikov-qresync-enable}.  I fully support such an outcome
0476 as it would be rather awkward to see a requirement for extra network round trips in contemporary IMAP extensions.
0477 
0478 \section{Fetching the Data}
0479 
0480 The IMAP protocol contains rather rich set of features aimed at downloading the message data in an efficient manner;
0481 clients can defer parsing of the MIME message parts~\cite{rfc2045} to the server and deal with the individual data
0482 separately.  In spite of that, there are a few optimization opportunities which can drastically reduce the amount of
0483 data to be transfered.
0484 
0485 \subsection{The BINARY Extension}
0486 
0487 Historically, e-mail messages could only contain English text, for which a 7-bit character set and the US-ASCII encoding
0488 was adequate.  However, with the advent of ``multimedia'', a steady pressure had emerged, leading to the MIME standard
0489 family.  Using MIME, complex tree-like structures can be embedded in e-mail messages and transmitted over the Internet
0490 mail.  However, at the time these were introduced, there was a real risk of not being able to transmit such complex
0491 messages over traditional communication channels which were often only 7-bit safe.  Due to these backward compatibility
0492 concerns, a few standard method of converting arbitrary data to a textual form were conceived under the name of {\em
0493 Content-Transfer-Encoding}.
0494 
0495 The two most common encoding schemes are Quoted-Printable~\cite[p. 18]{rfc2045} and Base64~\cite[p. 23]{rfc2045}, the
0496 latter of which is especially suitable for converting arbitrary binary data to a 7-bit form.  However, it is clear that
0497 mapping generic 8-bit data into 7-bit octets (and eliminating the appearance of certain ``magic'' characters in the
0498 process) cannot possibly work without inflating the total size of the transferred data.  For the Base64
0499 Content-Transfer-Encoding, the mapping converts 8-bit input (i.e. 256 values per octets) into a target alphabet of only
0500 64 characters, imposing an overhead of roughly 33~\% compared to the raw binary form.  Whenever the MIME-encoded message
0501 is transmitted, the amount of transferred data is therefore roughly one-third higher than strictly required.
0502 
0503 RFC 3516 \cite{rfc3516} adds a feature to work around this limitation through the {\tt BINARY} extension.  When the
0504 server supports this feature, clients can delegate the Content-Transfer-Encoding processing to the server and receive
0505 the raw binary data.  Perhaps surprisingly, the {\tt BINARY} extension was not supported in Dovecot, one of the most
0506 popular IMAP servers, at the time this thesis was written.
0507 
0508 \begin{trojitabehavior}
0509 Nevertheless, Trojitá includes full support for this extension and will automatically fetch data using the appropriate
0510 FETCH modifier in order to reduce the amount of data to send over the network.
0511 \end{trojitabehavior}
0512 
0513 \subsection{Server-side Conversions via CONVERT}
0514 
0515 Certain devices might have limitations which the sender might not have expected when she was preparing the message.  For
0516 example, a screen of a cell phone could have a very low resolution.  Unless the user really wants to see the full
0517 details after zooming in eight times, it might make sense to reduce the resolution of that 22-megapixel $5760 \times
0518 3840$ image produced by Canon 5D~Mk.~III to fit on a $480 \times 800$ pixels screen of a high-end smart phone from 2012.
0519 Even if the user actually wants to see the real image, it might be worthwhile to offer an access to a lower-resolution
0520 version for a quick preview.  This server-side conversion is what the {\tt CONVERT} extension from RFC 5259
0521 \cite{rfc5259} enables.
0522 
0523 Unfortunately, it appears that there are actually {\em no} publicly available servers which offer support for
0524 server-side conversions and the most popular open source implementations have not expressed much interest when asked for
0525 their future plans.
0526 
0527 \begin{trojitabehavior}
0528 Due to this induced inability to test this feature for interoperability, Trojitá doesn't support the {\tt CONVERT}
0529 extension at this point.
0530 \end{trojitabehavior}
0531 
0532 \subsection{Metadata Decoding}
0533 
0534 IMAP requires compliant servers to support MIME message parsing and RFC 2822 header decoding.  One feature which is
0535 notably absent, though, is a support for server-side decoding of RFC 2047-formatted message headers and IMAP's {\tt
0536 ENVELOPE} fields.  This shortcoming is partially addressed by two RFCs --- the already mentioned {\tt CONVERT} extension
0537 mandates support for character set decoding and conversions of RFC 2822 message headers while an experimental RFC 5738
0538 \cite{rfc5738} adds an ``UTF-8'' mode which switches all {\tt FETCH} commands to return the decoded Unicode data,
0539 including the IMAP's {\tt ENVELOPE}.  Sadly, support for this extension is similar to what has been already said for the
0540 {\tt CONVERT} and one can also safely claim that the possible data savings are minuscule, if any.  In addition, the
0541 UTF-8 extension changes quite a lot of assumptions from the traditional IMAP protocol, to the extent that one could very
0542 well propose yet another extension which would {\em just} enable access to the decoded {\tt ENVELOPE} and RFC 2822
0543 header data.  No such extension exists at this point, though.
0544 
0545 \begin{trojitabehavior}
0546 If the IMAP protocol was designed today, mandating a full-featured RFC 2047 decoder would be an obvious addition, but
0547 with the legacy of the protocol history, a requirement to implement a client-side decoder anyway and no available server
0548 support and the RFC being marked as {\em experimental}, Trojitá does not try to use the {\tt SELECT \ldots UTF8}
0549 parameter.
0550 \end{trojitabehavior}
0551 
0552 \section{Updating Mailboxes}
0553 
0554 Previous sections have introduced the existing extensions aimed at improving mailbox synchronization and data download.
0555 In this part, I will talk about how to optimize access to an already selected mailbox and how to get updated information
0556 about other mailboxes.
0557 
0558 \subsection{Sorting Messages}
0559 
0560 In a typical IMAP scenario, the server can access data for any message in a mailbox in a very cheap way.  This is in a
0561 strong contrast to its clients which are typically connected over a network whose quality could leave much to be
0562 desired.  It might therefore make sense to offload the data-intensive processing to the IMAP server and only send the
0563 results to the client.
0564 
0565 RFC 5256 \cite{rfc5256} adds support for server-side sorting.  Using these features allows clients to request the server
0566 to sort a subset of messages using predefined sorting criteria like the message date, the time of its arrival, name of
0567 the sender, contents of the subject field etc.  This feature set is subsequently augmented by RFC 5957 \cite{rfc5957}
0568 which adds another sorting method which prefers the ``real name'' included in the e-mail addresses instead of using the
0569 raw {\tt foo@example.org} format.  The results of the {\tt SORT} operation are transmitted in a format similar to the
0570 {\tt SEARCH} response.
0571 
0572 \begin{trojitabehavior}
0573 Trojitá includes full support for both of the mentioned RFCs.
0574 \end{trojitabehavior}
0575 
0576 This feature alone is a tremendous improvements over the traditional method where clients would have to download
0577 envelope data for all messages in a mailbox and then sort the messages based on the obtained data.  However, clients
0578 have no way of reusing the sort result when a new message arrives, mandating at least a limited support for client-side
0579 sorting as well.  This limitation is mitigated only by the {\tt CONTEXT} family of extensions which is discussed later
0580 in this chapter.
0581 
0582 \subsection{Threads and Conversations}
0583 
0584 RFC 5256 \cite{rfc5256} also includes support for organizing messages into threads.  The threading algorithm takes a
0585 look at various pieces of message metadata like their subjects or the {\tt Message-Id}, {\tt References} and {\tt
0586 In-Reply-To} headers and builds a tree of messages where children of a particular node represent messages which were
0587 made as responses to the parent one.  This RFC specifies a few threading algorithms from almost useless one (the {\tt
0588 ORDEREDSUBJECT} which groups together messages sharing a similar subject, effectively bundling unrelated items like
0589 generic ``info'', ``inquiry'' etc. messages) to almost perfect ones (the {\tt REFERENCES} which works like the {\tt
0590 ORDEREDSUBJECT}, but also takes the special machine-readable headers into account).  Sadly, even the {\tt REFERENCES}
0591 algorithm only sorts the threads by the time stamp of the thread root and not by the latest message in a thread,
0592 effectively ``hiding'' new responses deep in the mailbox history.  It also still looks at the message subjects,
0593 potentially lumping unrelated messages together.
0594 
0595 Both of these limitations are removed by the {\tt REFS} threading algorithm \cite{draft-ietf-morg-inthread}.  Despite
0596 being still in the draft phase, the Dovecot IMAP server includes full support for it.
0597 
0598 \begin{trojitabehavior}
0599 Trojitá will use it if the {\tt THREAD=REFS} capability is advertised.  In absence of the {\tt REFS} algorithm, Trojitá
0600 degrades to {\tt REFERENCES} and {\tt ORDEREDSUBJECT}, respectively.
0601 \end{trojitabehavior}
0602 
0603 Unfortunately, none of these extensions addresses the need to re-download the whole thread mapping when a new message
0604 arrives; matters are in fact even more complicated than when sorting because a single arriving message could have a wide
0605 ranging effect on the whole threading information.  This issue is addressed by the proposed ``extended {\tt INTHREAD}''
0606 described in \secref{sec:draft-incthread}.
0607 
0608 \subsection{Incremental Sorting and Searching}
0609 
0610 Soon after the original {\tt SORT} command got standardized, it became apparent that having to request a full update of
0611 the sort order whenever a new message arrived would nullify some of the bandwidth saving opportunitites of performing
0612 the server-side sort.  A similar concern existed for server-side searching --- here, too, the client would have to
0613 explicitly check if the new arrivals match the search criteria.  This limitation was addressed by introduction of the
0614 so-called {\em contexts} in RFC 5267 \cite{rfc5267}.
0615 
0616 This RFC defines three extensions, the {\tt ESORT}, {\tt CONTEXT=SEARCH} and {\tt CONTEXT=SORT}.  The first one is
0617 similar to the {\tt ESEARCH} (and in fact reuses the {\tt ESEARCH} response) in that it could reduce the amount of data
0618 transmitted in response to the {\tt SORT} command.  The two {\tt CONTEXT=\ldots} capabilities extend the {\tt SEARCH}
0619 and {\tt SORT} commands by a way to tell the server that it should tell the client whenever the results are updated.  An
0620 efficient way of communicating the changes through the {\tt ADDTO} and {\tt REMOVEFROM} {\tt ESEARCH} return values was
0621 introduced.
0622 
0623 In absence of the search/sort contexts, a newly arriving message would typically result in client repeating the
0624 operation.~\footnote{When speaking about searching, there is a pretty straightforward optimization opportunity where the
0625 {\tt SEARCH} command can be augmented to include an explicit ``and the messages' UID is higher than the
0626 $old\_uidnext$''.  Unfortunately, no such optimization can be performed for the {\tt SORT} command where the sort order
0627 can possibly depend on each and every other message in a mailbox.}  This is turn leads to excess data transfers like in
0628 the following example where a single arrival results in transferring the whole mapping again:
0629 
0630 \begin{minted}{text}
0631   C: x1 UID SORT (SUBJECT) utf-8 ALL
0632   S: * SORT 1 2 10 5 50 20 ... [rest of UIDs goes here]
0633   S: x1 OK sorted
0634   ...time passes...
0635   S: * 1007 EXISTS
0636   C: x2 UID SORT (SUBJECT) utf-8 ALL
0637   S: * SORT 1 2 1111 10 5 50 20 ... [rest of UIDs goes here]
0638   S: x2 OK sorted
0639 \end{minted}
0640 
0641 For brevity purposes, the sort order of the other 1,000 messages has been omitted.  In presence of the {\tt
0642 CONTEXT=SORT} extension, though, the same protocol interaction would look like this one:
0643 
0644 \begin{minted}{text}
0645   C: x1 UID SORT RETURN (ALL UPDATE) (SUBJECT) utf-8 ALL
0646   S: * ESEARCH (TAG "x1") UID ALL 1:2,10,5,50,20,90:1090
0647   S: x1 OK sorted
0648   ...time passes...
0649   S: * 1007 EXISTS
0650   S: * ESEARCH (TAG "x1") UID ADDTO (2 1111)
0651 \end{minted}
0652 
0653 Using the sort contexts therefore leads to dramatic bandwidth savings on ``busy'' mailboxes which keep receiving new
0654 mail over time; the {\tt ESEARCH} response can also occasionally contribute to a reduced amount of transferred data when
0655 the UIDs were assigned in a favorable way.  The biggest contribution is, however, the introduction of the {\tt ADDTO}
0656 {\tt ESEARCH} return response which obliterates the need to transfer sort order of the whole mailbox along with the
0657 single updated item.
0658 
0659 The search and sort contexts also impose certain, albeit abysmal overhead, though --- whenever a message is removed, an
0660 explicit {\tt ESEARCH REMOVEFROM} has to be issued.  This functionality is mandated by the relevant RFC, even though it
0661 doesn't provide any extra functionality --- all clients {\em still} have to listen for {\tt EXPUNGE} or {\tt VANISHED}
0662 untagged responses (and rightly so, obviously), so there is no technical obstacle in requiring them to remove the
0663 freshly removed items from their search/sort result cache.  Etiquette also dictates that clients shall cancel these
0664 updates when they are no longer needed through the {\tt CANCELUPDATE} command.  These drawback are however extremely
0665 small when working with larger mailboxes and absolutely worth the increased benefit of not transferring the whole set of
0666 UIDs over and over again.
0667 
0668 \begin{trojitabehavior}
0669 Trojitá includes full support for both {\tt CONTEXT=SEARCH} and {\tt CONTEXT=SORT}.  The {\tt CONTEXT=SEARCH} has been
0670 tested for interoperability against the Dovecot IMAP server, one of the few implementations which actually offer this
0671 functionality.  Unfortunately, I was not able to locate a single IMAP server supporting {\tt CONTEXT=SORT}, so no
0672 real-world interoperability tests could have been performed.~\footnote{As any other feature of Trojitá, though, the
0673 support for {\tt CONTEXT=SORT} is covered by the automated test suite which was carefully written to minimize the chance
0674 of any unwanted side effects and guard against unintended results when the servers deviate from the expected behavior.}
0675 This is a rather surprising outcome given that the RFC 5267 is not exactly a fresh standard now and that its authors
0676 work from a commercial software vendor offering a pretty advanced IMAP server implementation.
0677 \end{trojitabehavior}
0678 
0679 Sadly, no equivalent of these incremental updates is defined for the {\tt THREAD} command.  I suspect that this is
0680 caused by the fact that a single new arrival can affect each and every message in the previously received thread
0681 mapping.  I have attempted to address this limitation by augmenting the {\tt SEARCH=INTHREAD} draft, see
0682 \secref{sec:draft-incthread} for details about the selected approach.
0683 
0684 \subsection{Advanced Searching}
0685 
0686 Although the basic IMAP specification provides quite a rich set of features aimed at searching the currently selected
0687 mailbox, the specification leaves quite a fertile ground for improvements.
0688 
0689 The biggest problem with IMAP's searching is that it requires a strict substring matching, a requirement which is openly
0690 ignored by at least Google's IMAP implementation \cite{gmail-imap-unsupported-features}.  Google's partial answer to
0691 this problem is at least an ability to issue ``raw'' GMail-like searches through the {\tt X-GM-RAW} SEARCH operator
0692 \cite{gmail-x-gm-raw}.  Others have tried to add a similar feature through the {\tt SEARCH=FUZZY} extension as defined
0693 in RFC 6203 \cite{rfc6203}.
0694 
0695 \begin{trojitabehavior}
0696 Trojitá makes use of the fuzzy searching if available and announced in the capability response.  There were also some
0697 experimental extensions \cite{draft-ietf-imapext-regex} aimed at introducing search based on regular expressions, but
0698 they have not gained much traction.
0699 \end{trojitabehavior}
0700 
0701 A long-missing feature from IMAP is an ability to search multiple mailboxes at once.  A very crude hack is the
0702 (unofficial) {\tt SCAN} extension \cite{crispin-scan} which is said to be private to the University of Washington's {\tt
0703 uw-imapd} daemon.  More recent attempt at tackling down this problem is the {\tt MULTISEARCH} extension \cite{rfc6237}
0704 built on top of the {\tt NOTIFY} \cite{rfc5465}.  As of July 2012, no publicly available IMAP servers have announced
0705 support for this extension.
0706 
0707 \subsection{Obtaining Statistics for Other Mailboxes}
0708 
0709 Many IMAP clients start their session by requesting a {\tt LIST} of all top-level mailboxes.  This command is then
0710 followed by a {\tt STATUS} for each of them in order to obtain information like the number of messages in each mailbox.
0711 The obtained information is typically used in a GUI of some kind to show the mailbox list to the user.
0712 
0713 The basic IMAP specification unfortunately doesn't convey the critical piece of information about whether a mailbox
0714 contains any child mailboxes --- a data point typically required by any GUI to be able to show a proper widget for
0715 opening a list of these child items.  In absence of the {\tt CHILDREN} extensions, as defined by RFC 3348
0716 \cite{rfc3348}, clients have no choice but to issue an explicit {\tt LIST} command for all mailboxes,~\footnote{The only
0717 exception being those marked with the {\tt {\textbackslash}NoInferiors} which is meant to indicate that this mailbox
0718 could {\em never} contain any child mailboxes, perhaps due to technical limitations on the server side --- a very
0719 different case from not containing any child mailboxes at {\em this} time.} trying to list their children.
0720 
0721 The {\tt CHILDREN} is a pretty straightforward extension which shall arguably be supported by any IMAP server worth its
0722 salt; its absence does not improve the situation in any way.
0723 
0724 \begin{trojitabehavior}
0725 Trojitá supports it fully and will gracefully fall back to extra {\tt LIST} requests in case it is not available.
0726 \end{trojitabehavior}
0727 
0728 The initial discovery of mailboxes also mandates a separate {\tt STATUS} command for each mailbox --- behavior which
0729 arguably goes against the spirit behind that command which was intended to {\em not} serve as a generic ``tell me about
0730 updates to other mailboxes'' feature.  This initial idea no longer has its merit, unfortunately --- users simply {\em
0731 expect} being able to see a number of unread messages right next to the mailbox name, and client authors have to deliver
0732 this information to them.  Having to send an extra {\tt STATUS} command for each mailbox during the initial discovery is
0733 not too evil thing per se (the total wasted bandwidth is negligible when compared to mailbox synchronization), but worth
0734 optimizing anyway.  RFC 5819 \cite{rfc5819} adds an option to the {\tt LIST} command to request automatic sending of the
0735 untagged {\tt STATUS} command along.
0736 
0737 \begin{trojitabehavior}
0738 When the IMAP server announces the {\tt LIST-STATUS} capability, Trojitá will automatically make use of this extension.
0739 \end{trojitabehavior}
0740 
0741 \subsection{Push-notification of Other Mailboxes' State}
0742 
0743 A feature most notably absent from the {\tt IDLE} is any support of passively monitoring changes of non-selected
0744 mailboxes.  Over the time, many extensions have appeared in the state of various drafts
0745 \cite{draft-wener-lemonade-clearidle} \cite{draft-gulbrandsen-imap-nostore} \cite{draft-magicaltux-imap4-idleplus},
0746 often simply requesting unsolicited delivery of {\tt STATUS} and {\tt FETCH} responses.  None of these extensions gained
0747 widespread support nor reached the state of a proposed standard, though.
0748 
0749 Said status was reached by the {\tt NOTIFY} extension codified in RFC 5465 \cite{rfc5465}.  It adds an impressive amount
0750 of features; compliant agents can listen for creation and deletion of mailboxes (eliminating the need to redo a
0751 top-to-bottom {\tt LIST} discovery), changes in amount of messages in specified list of mailboxes and even for their
0752 flag changes.  Sadly, support for this extension is scarce among the existing IMAP servers and its author reportedly has
0753 mixed feelings \cite{arnt-good-bad-rfc} about its fate where basically ``noone implements it''.  In early 2012, a
0754 posting on the Dovecot mailing list announced \cite{dovecot-imap-notify} preliminary support for a part of this
0755 extension in Dovecot, one of the most widely deployed open source IMAP daemons.  Unfortunately, this code was not
0756 complete as of July 2012 \cite{dovecot-hg-notify} and the branch I have tried contained regressions which prevented
0757 regular use of other features of the IMAP server altogether.~\footnote{This is not to say that the Dovecot is a bad IMAP
0758 daemon --- not at all.  The version which was used is a development snapshot which is clearly marked as an experimental
0759 version which requires future work.}
0760 
0761 \begin{trojitabehavior}
0762 Due to not being able to verify the {\tt NOTIFY} operation against any available IMAP server implementation, Trojitá
0763 will not try to leverage this extension for the time being.
0764 \end{trojitabehavior}
0765 
0766 \section{Composing and Delivering Mail}
0767 
0768 The baseline versions of the IMAP protocol does not offer any substantial assistance in composing and delivery of new
0769 messages --- the only feature even remotely related to this topic is the {\tt APPEND} command which saves a message
0770 passed by the client into a mailbox.  Over the time, several extensions appeared aiming at improving this area.
0771 
0772 The first extension is the {\tt MULTIAPPEND} command (RFC 3502 \cite{rfc3502}) which allows the client to atomically
0773 upload many messages at once.  Having such a feature could be a terrific boon in clients which support batched import of
0774 data from the existing mail store, but it is not so valuable in a generic client.
0775 
0776 \begin{trojitabehavior}
0777 If Trojitá grows and a support for batched import becomes a wanted feature, the {\tt MULTIAPPEND} command will
0778 doubtlessly contribute to a smoother experience.
0779 \end{trojitabehavior}
0780 
0781 Much more useful is the {\tt CATENATE} extension \cite{rfc4469} which allows clients to build a message from a
0782 combination of uploaded parts and data already available on the IMAP server.  This extension is crucial for implementing
0783 advanced forward-without-download feature.  Suppose a user who is currently on her vacation high above some Nordic
0784 fjord, accessing e-mail over a metered GPRS connection, has just received a huge e-mail consisting of a big binary
0785 attachment.  IMAP already has a feature which allows her to check the accompanying text without downloading the full
0786 message body.  What is missing is some kind of support of forwarding the original message to another recipient.
0787 
0788 This task consists of several steps --- first of all, the body of the resulting message to be sent has to be composed.
0789 The {\tt CATENATE} extension tremendously helps with this task.  Using {\tt CATENATE}, a client can compose a message
0790 consisting of a mixture of data, some of which is coming from the client over the network as raw literals, others being
0791 recycled from server-side data, be it full messages, arbitrary message parts or even byte-sized chunks of these.  After
0792 the message composing is concluded, the message shall be submitted to an MTA~\footnote{Mail Transfer Agent}, typically
0793 over the SMTP protocol \cite{rfc6409}.  Finally, a copy of the message shall be stored in the user's ``sent'' folder for
0794 future reference.
0795 
0796 \begin{trojitabehavior}
0797 Trojitá will make use of the {\tt CATENATE} extension when available.
0798 \end{trojitabehavior}
0799 
0800 It can be seen that in absence of specialized extensions, this an interaction could possibly involve up to three
0801 transfers of the huge binary data, possibly in an inefficient transport encoding, over the unreliable or expensive
0802 network connection.  Clearly, there's a huge room for improvements.  The {\tt CATENATE} extension assists in a
0803 server-side IMAP message assembly, but does not provide a way of improving actual message submission.
0804 
0805 The first possible way of improving relies on a whole family of extensions concerning both SMTP and IMAP.  The SMTP
0806 protocol is extended by the {\tt BURL} command \cite{rfc4468} while the IMAP server has to support the {\tt URLAUTH}
0807 extension \cite{rfc4467} and both daemons have to be properly configured.  Using this protocol combination (which itself
0808 depends on quite a few more extensions, please see the respective RFC documents for details), the IMAP client can
0809 generate a single-use authorization token which --- if used --- enables its holder to access the given message part.
0810 This token is then passed to the SMTP daemon which will combine data obtained directly from the MUA\footnote{Mail User
0811 Agent, i.e. the program which acts on the user's behalf in accessing and submitting the Internet mail} (like the
0812 accompanying text) with the data downloaded from the IMAP server via the passed authorization token, build a MIME
0813 message and take care of its further delivery through the usual means.  As was already mentioned, if the IMAP server
0814 also supports the {\tt CATENATE} extension, the client can build the message on the server at once from the mentioned
0815 fragments (the new accompanying text and the attachment from the original message) and pass this newly-formed message
0816 for submission through the {\tt BURL} SMTP extension.  This has a potential of eliminating the need to transfer the data
0817 to/from the client {\em at all}, leading to a drastic bandwidth reduction.
0818 
0819 \begin{trojitabehavior}
0820 Trojitá includes full support for the {\tt BURL} and {\tt URLAUTH} extensions.  Due to the interoperability troubles
0821 with misconfigured servers which were observed in real world \cite{qmf-fastmail-burl-bug}, making use of {\tt BURL} has
0822 to be explicitly allowed in the settings dialog of the application.
0823 \end{trojitabehavior}
0824 
0825 Unfortunately, such mode of operation comes at a cost.  Support for the required extensions is not
0826 ubiquitous among the deployed servers and even if the code contains all required features, it is often a policy decision
0827 whether an IMAP server should ever allow access to possibly privacy-sensitive data to the outbound MTAs.
0828 
0829 Another possibility presenting slightly different set of features, advantages and disadvantages is implemented by
0830 deferring the actual message submission to the IMAP server as well.  The {\tt CATENATE} extension is still useful
0831 because it shall nonetheless be used to build the MIME message body from existing parts, eliminating the need to upload
0832 the data to the IMAP server.  When the message body is built (no matter how, using {\tt CATENATE} or deferring to legacy
0833 means), the IMAP server can be asked to submit the resulting data for delivery.
0834 
0835 This former approach has been traditionally dismissed by many IMAP proponents, including Mark Crispin, on various
0836 grounds.  The most common complaint is that the SMTP protocol is extremely mature, widely deployed and also complex ---
0837 and that this inherent complexity is {\em required} by various use cases crucial for proper operation of today's
0838 Internet mail.  The critics often argue that covering the whole feature set of the (E)SMTP-based submission would lead
0839 only to an equivalent of tunneling the SMTP session over IMAP \cite{crispin-smtp-tunneling}
0840 \cite{cridland-imap-submission-sendmail-not-enough}, an outcome which is clearly not desirable.  This approach was
0841 also subject to various standardization efforts, often literally tunneling the (E)SMTP conversations \cite[p.
0842 30]{draft-maes-lemonade-p-imap} over an IMAP connection.  Proponents of this submit-over-IMAP approach, however,
0843 counter-argument by stating that optimizing for a common use case has its own merits
0844 \cite{brong-common-sendmail-makes-sense}.  The critics concur that having two ways of obtaining an identical result is
0845 suboptimal and that an easier, yet more limited way would threaten the existence of the older, more flexible solution
0846 \cite{crispin-submission-would-kill-smtp}.
0847 
0848 Finally, a third way of solving the forward-without-download problem was presented in September 2010 through the {\tt
0849 POSTADDRESS} extension \cite{draft-melnikov-imap-postaddress}.  Using this mechanism, a client first obtains a valid
0850 e-mail address serving as a ``delivery address'' for the user's {\em Sent} mailbox.  After getting hold of that
0851 information, the SMTP session then proceeds as usual with one difference --- the obtained address is added as another
0852 recipient of the submitted e-mail message.
0853 
0854 \begin{trojitabehavior}
0855 Besides including full support for the already mentioned ``Lemonade trio'' of extension ({\tt CATENATE}, {\tt URLAUTH}
0856 and {\tt BURL}, Trojitá also includes experimental support for the second approach of forward-without-download, the
0857 submission-over-IMAP variant.
0858 \end{trojitabehavior}
0859 
0860 Mail submission is an important topic, so I have dedicated a full section to a more detailed analysis of various
0861 advantages and disadvantages of competing approaches.  More information is available in section
0862 (\secref{sec:draft-sendmail}) where I present my Internet-Draft documenting a proposed extension in which I've tried to
0863 address many concerns raised during the previous discussion rounds.
0864 
0865 \section{Further Improvements}
0866 
0867 Many additional extensions have been defined over years, covering various areas of the protocol.  This section deals
0868 with those extensions which do not quite fit into any of the previous categories.
0869 
0870 \subsection{Debugging}
0871 
0872 Most of other communication protocols contain a way of letting the other party know what software implementation and in
0873 which version it is talking to.  In the web, this is usually accomplished through the {\tt User-Agent} and {\tt Server}
0874 headers, e-mail messages often contain either an {\tt X-Mailer} or {\tt User-Agent} field in theirs RFC 2822 headers,
0875 etc.  IMAP adds a similar feature through the {\tt ID} extension defined in RFC 2971 \cite{rfc2971}.
0876 
0877 This RFC is pretty clear on that implementations are explicitly {\em forbidden} from using {\em any} knowledge obtained
0878 through the {\tt ID} extension to alter their behavior.  This is a reasonable decision intended to prevent clients
0879 implementing blacklists and whitelists of ``known'' servers.  All IMAP protocol speakers are intended to only use the
0880 {\tt CAPABILITY} responses (and the {\tt ENABLE} extension, if present) to change their behavior.
0881 
0882 \begin{trojitabehavior}
0883 Trojitá is fully compliant with these requirements.
0884 \end{trojitabehavior}
0885 
0886 \subsection{Internationalization}
0887 
0888 The ``internationalization'' RFC (RFC 5255 \cite{rfc5255}) is focused on server implementations, mainly specifying how
0889 to perform search/sort collation under various circumstances.  That said, it also presents two commands to the IMAP
0890 clients.  The first of them is the {\tt LANGUAGE} command suitable for changing the language in which various error and
0891 notifying messages are generated and sent by the server.
0892 
0893 \begin{trojitabehavior}
0894 Trojitá tries hard to rely on machine-readable response codes (RFC 5530 \cite{rfc5530}) instead.
0895 \end{trojitabehavior}
0896 
0897 The second command is the {\tt COMPARATOR}, a feature intended to let clients
0898 specify which comparators and collators to use when performing search or sort operations (these comparators are defined
0899 in RFC 4790 \cite{rfc4790}).  By default, servers supporting at least the {\tt I18NLEVEL=1} extension are required to
0900 perform collations using the {\tt i;unicode-casemap} comparator \cite{rfc5051} --- a feature which is very useful (and
0901 often sufficient) in countries using the Latin alphabet.  Those servers which support {\tt I18NLEVEL=2} also accept
0902 client-specified preference about how to perform these operations.
0903 
0904 \begin{trojitabehavior}
0905 Adding support for this higher level would be trivial on a technical front (the {\tt LANGUAGE} and {\tt COMPARATOR}
0906 commands are very simple with much more demanding requirements on servers), but no requests for such a feature in
0907 Trojitá were received yet --- suggesting that the {\tt i;unicode-casemap} comparator works well for most users at this
0908 point.
0909 \end{trojitabehavior}
0910 
0911 There is also the experimental ``UTF-8'' RFC \cite{rfc5738} whose aim is to get rid of any non-UTF8 data being
0912 transferred over IMAP.  Unfortunately, as designed, this document presents backward-incompatible changes to the IMAP
0913 protocol and is hence not widely supported by the common server implementations.  The client authors would very much
0914 prefer to stop dealing with various Unicode encoding schemes, but this RFC does not completely address all of the
0915 issues.  An ongoing discussion is nevertheless taking place on official IETF's channels; it will be promising to watch
0916 its future and especially the fate of the ``5738bis'' Internet Draft \cite{draft-ietf-eai-5738bis}.
0917 
0918 \begin{trojitabehavior}
0919 It shall be noted that Trojitá's source is completely ready for internationalization and localisation of the
0920 application.~\footnote{This support does not come at no cost, unfortunately.  Qt's {\tt QDateTime} class which is used
0921 for keeping track of the date and time information in all Qt-using projects unfortunately does not support tracking of
0922 timezone information \cite{qt-qdatetime-tz}.  Trojitá works around this limitation of the public API by manual hack in
0923 {\tt Imap::Mailbox::formatDateTimeWithTimeZoneAtEnd()} method.}
0924 \end{trojitabehavior}
0925 
0926 \subsection{Other Supported RFCs}
0927 
0928 Trojitá is fully conforming to the description of the ``Distributed Electronic Mail Models in IMAP4'', as defined in RFC
0929 1733 \cite{rfc1733}.  It also respect the recommendations about concurrent access to mailboxes from RFC 2180
0930 \cite{rfc2180}, generic suggestions to the IMAP implementors (RFC 2683 \cite{rfc2683}), Mark Crispin's famous ``Ten
0931 Commandments of How to Write an IMAP client'' \cite{crispin-ten-commandments} and Timo Sirainen's suggestions for client
0932 authors \cite{tss-client-coding-howto} \cite{imapwiki-client-best-practices}.
0933 
0934 It will make use of the {\tt UNSELECT} command for internal technical reasons (RFC 3691 \cite{rfc3691}), if available;
0935 if it isn't present, it will gracefully revert to using fabricated mailbox names with the {\tt EXAMINE} command from the
0936 baseline IMAP specification.  This failover is thoroughly verified by a suite of automated unit tests.
0937 
0938 Trojitá is capable of recording responses from the {\tt UIDPLUS} extension (RFC 4315 \cite{rfc4315}); the author have
0939 also contributed \cite{jkt-move-uidplus} to the discussion related to the {\tt COPYUID} equivalent for the proposed {\tt
0940 UID MOVE} command.
0941 
0942 The code also includes full support for recognizing various extensions to the IMAP's grammar (RFC 4466 \cite{rfc4466}),
0943 response codes (RFC 5530 \cite{rfc5530}) and the reserved set of keywords (RFC 5788 \cite{rfc5788}).
0944 
0945 RFC 5258 \cite{rfc5258} is used when available to explicitly encourage the IMAP server to send additional metadata in
0946 {\tt LIST} responses --- the biggest benefit of this extension is eliminating the need of sending explicit {\tt LSUB}
0947 requests to discover mailbox subscriptions.
0948 
0949 Finally, the Lemonade extension (RFC 5550 \cite{rfc5550} and the obsolete RFC 4550 \cite{rfc4550}) has compiled a set of
0950 requirements crucial to the mobile IMAP e-mail clients.  Comparison of the proposed set of extensions with the Lemonade
0951 profile is presented in a dedicated section of this thesis on page \pageref{sec:lemonade-comparison}.
0952 
0953 \subsection{Out-of-scope Features}
0954 
0955 The extensions presented so far all have a certain affinity towards the ``mobile IMAP''.  Many other extensions have
0956 been introduced, though, often solving a real problem.
0957 
0958 The first family of extensions with debatable merit are extensions providing support for so-called referrals.  The RFC
0959 2221 \cite{rfc2221} adds a mechanism for servers to redirect clients based on their identity, a feature which was
0960 originally supposed to come handy in large corporate environment.  Similar to that, the RFC 2193 \cite{rfc2193} adds
0961 mailbox referrals, a feature where a subset of user's mailboxes might be stored on a remote server.  As it happens,
0962 these features have not attained a big market share among client developers \cite{thunderbird-referrals} and the servers
0963 which supports that are generally willing to act as a transparent proxy for their clients anyway
0964 \cite{cyrus-referral-proxy}.
0965 
0966 Extensions which are useful in a general-purpose e-mail client are the {\tt NAMESPACE} extension (RFC 2342
0967 \cite{rfc2342}) which would allow compliant clients to automatically discover where e.g. other users' mailboxes are
0968 located, support for managing access-control lists (ACLs) on the server (RFC 4314 \cite{rfc4314} and its obsolete form
0969 given in RFC 2086 \cite{rfc2086}) and finally support for reporting and managing storage quotas (RFC 2087
0970 \cite{rfc2087}).
0971 
0972 \begin{trojitabehavior}
0973 These have not been implemented in Trojitá yet.
0974 \end{trojitabehavior}
0975 
0976 A mechanism for increasing interoperability with organizations which have invested in a single-sign-on infrastructure
0977 like Kerberos could be improved through better support for SASL (RFC 1731 \cite{rfc1731}, RFC4959 \cite{rfc4959}).
0978 
0979 \begin{trojitabehavior}
0980 A request from users which would very much prefer to have a GSSAPI-enabled Trojitá was already received, but
0981 unfortunately this feature remains unimplemented due to time constraints.
0982 \end{trojitabehavior}
0983 
0984 A few extensions might improve the general comfort of users setting up their e-mail clients for the first time.  Without
0985 any doubt, autoconfiguration through the DNS SRV records (RFC 6186 \cite{rfc6186}) falls into this category.
0986 
0987 There are also certain features which might add a whole new level of functionality to working with e-mail -- examples
0988 are the {\tt ANNOTATE} extension (RFC 5257 \cite{rfc5257}) for adding arbitrary annotations to individual messages or
0989 even their parts, which is still marked as experimental, or the similar {\tt METADATA} feature (RFC 5464 \cite{rfc5464})
0990 adding the same functionality on a server or mailbox level.  Needless to say, support for these extensions is scarce
0991 among the IMAP clients.
0992 
0993 Other extensions try to fill a certain niche.  Examples are the {\tt WITHIN} extension (RFC 5032 \cite{rfc5032}) which
0994 allows clients to search among messages of a certain age or the {\tt SEARCHRES} (RFC 5182 \cite{rfc5182}) adding a
0995 low-level pipelining optimization which would allow the client to re-use the previous search result in the subsequent
0996 commands.  RFC 5466 \cite{rfc5466} adds support for persistent storage of search criteria on the server through the
0997 already mentioned {\tt METADATA} extension.
0998 
0999 \begin{trojitabehavior}
1000 I have not found a use case for having these optional extensions utilized from Trojitá in any place.
1001 \end{trojitabehavior}
1002 
1003 The RFC 3503 \cite{rfc3503} deals with how to generate the message delivery notifications (MDNs) in IMAP.
1004 
1005 \begin{trojitabehavior}
1006 This document clearly does not apply to clients which on purpose do not create MDNs for privacy reasons, such as
1007 Trojitá.
1008 \end{trojitabehavior}
1009 
1010 Finally, certain extensions improve the user experience in specialized environments.  One of them is RFC 5616
1011 \cite{rfc5616}, an extension aimed at ``Streaming Internet Messaging Attachments''.  One could imagine a use case where
1012 a carrier-level voice mailbox was implemented over IMAP; in similar situations, such a solution would have its merit.
1013 At the same time, this specific extension has so special requirements on the network architecture that it is clearly
1014 out-of-scope for a general-purpose e-mail client merely running on a cell phone.
1015 
1016 \section{Obsolete Extensions}
1017 
1018 IMAP is a rather old protocol (its history is slightly older than the author of this thesis, for that matter).  Certain
1019 features have been therefore deprecated over time and it took years to grow to the current IMAP4rev1 version from the
1020 old standards of IMAP2 \cite{rfc1064} \cite{rfc1176}, IMAP3 \cite{rfc1203} and IMAP4 \cite{rfc1730}.  Attention has been
1021 paid to make this transition as smooth as possible through various compatibility recommendations \cite{rfc1732}
1022 \cite{rfc2060} \cite{rfc2061} \cite{rfc2062}.
1023 
1024 \begin{trojitabehavior}
1025 Trojitá requires the server to at least announce the {\tt IMAP4rev1} capability.  This protocol revision is currently
1026 defined by RFC 3501 \cite{rfc3501} from March 2003; however, changes since the previous version from December 1996
1027 (\cite{rfc2060}) are mostly backward compatible --- and in practice, no report of Trojitá not being able to work against
1028 any IMAP server implementation out there were received.
1029 \end{trojitabehavior}
1030 
1031 The {\tt UIDPLUS} extension got redefined from its former shape \cite{rfc2359} to the current revision \cite{rfc4315};
1032 the new document states that the reason for this revision was to prevent sending of bogus UID replies when the target
1033 mailbox did not support persistent UIDs.
1034 
1035 \begin{trojitabehavior}
1036 As such, Trojitá can deal with both revision of the {\tt UIDPLUS} document.
1037 \end{trojitabehavior}
1038 
1039 \end{document}