Ϫf!dZddlmZddlZddlZddlZddlZddlZddlZddl m Z ddl m Z ddl mZddlmZmZddlmZdd lmZdd lmZmZdd lmZdd lmZmZmZdd lm Z ddl!m"Z"m#Z#ddl$m%Z%m&Z&m'Z'm(Z(ddl)m*Z*ddl+m,Z,ddl-m.Z.m/Z/ddl0m1Z1ddl2m3Z3ddl4m5Z5m6Z6m7Z7ddl8m9Z9ddl:m;Z;mm?Z?m@Z@mAZAddlBmCZCmDZD ddlEmFZFmGZGdZIGddeDZJGddZKGd d!eCZLGd"d#eCZMGd$d%eDZNee1je1je1jGd&d'ZRee1je1jGd(d)ZSGd*d+e1jZUGd,d-eUe1jZWGd.d/e1jZYGd0d1e1jZ[Gd2d3Z\Gd4d5e\eDZ]Gd6d7eCZ^Gd8d9e\eDZ_ee"Gd:d;Z`Gd<d=ZaGd>d?e\eDZbGd@dAeDZcGdBdCe\eDZdGdDdEeDZeGdFdGe1jZfGdHdIe\eDZgGdJdKZhGdLdMehZiGdNdOeieCZjGdPdQeieCZkGdRdSeheCZlGdTdUeheCZmGdVdWeheCZnGdXdYeheDZoGdZd[eheCZpGd\d]eheCZqGd^d_e1jZree1jGd`dae=jZuGdbdceDe\ZvGdddeeDZwGdfdgeDe\ZxGdhdie\eDZyee1jGdjdkeDe\Z{GdldmZ|ee1jGdndoZ~ee1jGdpdqZGdrdseDZeeF dtee'je(d duGdvdwe\eDZGdxdyeRZGdzd{e\eDZGd|d}eDZGd~dZGddeDZGddeDZGddZGddeeCZGddeeDZGddeCZy#eH$rdZFdZGYwxYw)z" Test case for twisted.mail.imap4 ) annotationsN) OrderedDictBytesIO)chain)OptionalType)skipIf) implementer) verifyClass verifyObject)'InMemoryUsernamePasswordDatabaseDontUse)CramMD5CredentialsIUsernameHashedPasswordIUsernamePasswordUnauthorizedLogin)IRealmPortal)defererror interfacesreactor)Deferred)Clock)StringTransport StringTransportWithDisconnection)imap4) MessageSet)IChallengeResponseIClientAuthenticationICloseableMailboxIMAP)loopback)failurelogutil) iterbytes nativeString networkString)SynchronousTestCaseTestCase)ClientTLSContextServerTLSContextc |fdS)Nc|SN)resultfs =/usr/lib/python3/dist-packages/twisted/mail/test/test_imap.pyzstrip..:sqsr1)r3s r4stripr79s  ""r6cdeZdZddgddgddgddgd d ggZd Zd Zd ZdZdZdZ dZ dZ dZ y)IMAP4UTF7Tests Hello world Hello worldz Hello & worldsHello &- world HelloÿworldHello&AP8-worlduÿþýüs &AP8A,gD9APw-u~peter/mail/日本語/台北s~peter/mail/&ZeVnLIqe-/&U,BTFw-cjd}|j|jdd|jdy)z Specifying an error policy to C{unicode.encode} with the I{imap4-utf-7} codec should produce the same result as not specifying the error policy. r: imap4-utf-7strictN assertEqualencodeselftexts r4test_encodeWithErrorsz$IMAP4UTF7Tests.test_encodeWithErrorsIs0   KK x 0$++m2L r6cjd}|j|jdd|jdy)zO Similar to L{test_encodeWithErrors}, but for C{bytes.decode}. r;r?r@NrBdecoderEbytess r4test_decodeWithErrorsz$IMAP4UTF7Tests.test_decodeWithErrorsTs0  LL 15<< 3N r6cJd}|j|jddy)z Unicode strings that contain an ampersand (C{&}) can be encoded to bytes with the I{imap4-utf-7} codec. u &Hello&½&r?s&-Hello&-&AL0-&-NrArDs r4test_encodeAmpersandz#IMAP4UTF7Tests.test_encodeAmpersand]s& 6  KK &  r6cF|jdjddy)z An I{imap4-utf-7} encoded string that does not shift back to ASCII (i.e., it lacks a final C{-}) can be decoded. s&AL0r?½NrIrEs r4!test_decodeWithoutFinalASCIIShiftz0IMAP4UTF7Tests.test_decodeWithoutFinalASCIIShifths!  NN= ) * r6ctjdtd}|j|j dy)zl C{codecs.getreader('imap4-utf-7')} returns the I{imap4-utf-7} stream reader class. r?r=r<N)codecs getreaderrrBread)rEreaders r4test_getreaderzIMAP4UTF7Tests.test_getreaderrs8 1!!-09K1LM (89r6ct}tjd|}|jd|j |j dy)zl C{codecs.getwriter('imap4-utf-7')} returns the I{imap4-utf-7} stream writer class. r?r<r=N)rrU getwriterwriterBgetvalue)rEoutputwriters r4test_getwriterzIMAP4UTF7Tests.test_getwriterzsG 0!!-08 %& *,>?r6cn|jD]&\}}|j|jd|(y)z The I{imap4-utf-7} can be used to encode a unicode string into a byte string according to the IMAP4 modified UTF-7 encoding rules. r?N)testsrBrCrEinputr^s r4 test_encodezIMAP4UTF7Tests.test_encodes6 "ZZ BME6   U\\-8& A Br6cn|jD]&\}}|j||jd(y)z The I{imap4-utf-7} can be used to decode a byte string into a unicode string according to the IMAP4 modified UTF-7 encoding rules. r?N)rbrBrJrcs r4 test_decodezIMAP4UTF7Tests.test_decodes6 "ZZ BME6   UFMM-$@ A Br6cttddtddD]o}t|j}|j |t|jd|j t||j dq|j djdd|j dj ddy) z The IMAP4 modified UTF-7 implementation encodes all printable characters which are in ASCII using the corresponding ASCII byte. &'r?&s&-N)rrangechrrCrBrJ)rEocharbytes r4test_printableSingletonsz'IMAP4UTF7Tests.test_printableSingletonss uT4(%d*;< EA1v}}H   Xs1v}}]'C D   SVX__]%C D E M2E: m4c:r6N) __name__ __module__ __qualname__rbrGrMrOrSrYr`rergrrr1r6r4r9r9=sg ' +, -. -. 9 . E      :@BB ;r6r9c$eZdZdZdZdZdZy)BufferingConsumercg|_yr0)bufferrRs r4__init__zBufferingConsumer.__init__s  r6c|jj||jr|jjyyr0)ryappendconsumerresumeProducingrKs r4r\zBufferingConsumer.writes0 5! == MM ) ) + r6cF||_|jjyr0)r}r~)rEr} streamings r4registerProducerz"BufferingConsumer.registerProducers   %%'r6cd|_yr0)r}rRs r4unregisterProducerz$BufferingConsumer.unregisterProducers  r6N)rsrtrurzr\rrr1r6r4rwrws, (r6rwc*eZdZdZdZdZdZdZy)MessageProducerTestscdt}d|d<d|d<d|d<d|d <t|d dd d}ttj|j }fd }|j |S) NsThis is body text. Rar. sender@hostfromrecipient@domaintobooga booga boosubject text/plain content-typer1{cj|jdjjdzy)Nr6sf{119} From: sender@host To: recipient@domain Subject: booga booga boo Content-Type: text/plain )assertIdenticalrBjoinry)r2bodycprEs r4 cbProducedz7MessageProducerTests.testSinglePart..cbProduceds@   +   "   r6r FakeyMessagerwrMessageProducerbeginProducing addCallback)rEheadersmsgdrrrrs` @@@r4testSinglePartz#MessageProducerTests.testSingleParts*-'* . ".7BdC>    ! !# &  Q  }}Z((r6cF d}dt}d|d<d|d<d|d<d |d <t}d |d<d |d <t|d d|dt|d dddg}ttj| j } fd}|j |S)Nr6&Contained body message text. Squarge.rrrrrr%multipart/alternative; boundary="xyz"rthis is subject textrr1rcj|jdjjdzdzy)Nr6s{239} From: sender@host To: recipient@domain Subject: booga booga boo Content-Type: multipart/alternative; boundary="xyz" --xyz Subject: this is subject text Content-Type: text/plain --xyz-- failUnlessIdenticalrBrryr2r innerBodyrrEs r4rz.cbProducedsJ  $ $VQ /   " $ $'9 9 r6r rE outerBodyr innerHeadersrrrrrrs ` @@@r4testSingleMultiPartz(MessageProducerTests.testSingleMultiParts = -'* . "I"} "8 Y'3 ^$      ,D)T4 H I      ! !# &  Q  $}}Z((r6c d}d d t}d|d<d|d<d|d <d |d <t}d |d <d |d <t}d|d <d|d <t|dd|dt|dd ddt|dd ddg}ttj| j } fd}|j |S)Nr6r.Secondary message text of squarge body.rrrrrrrrrrthis is subject text/htmlr1rcj|jdjjdzdzzdzy)Nr6s{354} From: sender@host To: recipient@domain Subject: booga booga boo Content-Type: multipart/alternative; boundary="xyz" --xyz Subject: this is subject text Content-Type: text/plain sE --xyz Subject: this is subject Content-Type: text/html rr)r2r innerBody1 innerBody2rrEs r4rz>MessageProducerTests.testMultipleMultiPart..cbProduceds^  $ $VQ /   " % %( % %(: : r6r) rErrr innerHeaders2rrrrrrrs ` @@@@r4testMultipleMultiPartz*MessageProducerTests.testMultipleMultiParts > F -'* . "I"} "8 Y'3 ^$# #; i (3 n%     \2tZtL]Bj$M       ! !# &  Q   *}}Z((r6cV d}dt}d|d<d|d<d|d<d |d <t}d |d<d |d <t|d d|dt|d dddg}ttj| d _ j } fd}|j|S)z> A boundary is generated if none is provided. r6rrrrrrrmultipart/alternativerrrr1Nrc,tjdS)Nz$aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa)uuidUUIDr1r6r4r5z?MessageProducerTests.test_multiPartNoBoundary..Ms499%KLr6cj|jdjjdzdzy)Nr6s {341} From: sender@host To: recipient@domain Subject: booga booga boo Content-Type: multipart/alternative; boundary="----=aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa" ------=aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa Subject: this is subject text Content-Type: text/plain s- ------=aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa-- rrs r4rzAMessageProducerTests.test_multiPartNoBoundary..cbProducedQsL  $ $VQ /   "  GG r6)rrrwrr_uuid4rrrs ` @@@r4test_multiPartNoBoundaryz-MessageProducerTests.test_multiPartNoBoundary3s = -'* . "9"} "8 Y'3 ^$      ,D)T4 H I      ! !# &L  Q  *}}Z((r6cF d}dt}d|d<d|d<d|d<d |d <t}d |d<d |d <t|d d|dt|d dddg}ttj| j } fd}|j |S)z> A boundary without does not have them added. r6rrrrrrrz#multipart/alternative; boundary=xyzrrrr1Nrcj|jdjjdzdzy)Nr6s{237} From: sender@host To: recipient@domain Subject: booga booga boo Content-Type: multipart/alternative; boundary=xyz --xyz Subject: this is subject text Content-Type: text/plain rrrs r4rz?MessageProducerTests.test_multiPartNoQuotes..cbProducedsJ  $ $VQ /   " $ $'9 9 r6rrs ` @@@r4test_multiPartNoQuotesz+MessageProducerTests.test_multiPartNoQuoteshs = -'* . "G"} "8 Y'3 ^$      ,D)T4 H I      ! !# &  Q  &}}Z((r6N)rsrtrurrrrrr1r6r4rrs)8+)Z4)l3)j/)r6rc|eZdZdZdZdZdZdZdZdZ dZ d Z d Z d Z d Zd ZdZdZdZdZdZdZy)MessageSetTestsz" Tests for L{MessageSet}. ct}t}|j|||j|d|dz}|jt|d|jt |dg|dz}|jt|d|jt |gd|dz}|j|||jt ||zgd|j d|jt|d|jt |gd|j|||j d d |jt|d |jt |gd y )a4 Test the following properties of L{MessageSet} addition and equality: 1. Two empty L{MessageSet}s are equal to each other; 2. A L{MessageSet} is not equal to any other object; 2. Adding a L{MessageSet} and another L{MessageSet} or an L{int} representing a single message or a sequence of L{int}s representing a sequence of message numbers produces a new L{MessageSet} that: 3. Has a length equal to the number of messages within each sequence of message numbers; 4. Yields each message number in ascending order when iterated over; 6. L{MessageSet.add} with a single message or a start and end message satisfies 3 and 4 above. r1rrrr)rrrr)rrrrrrrN)rrBassertNotEquallenlistadd)rEm1m2s r4!test_equalityIterationAndAdditionz1MessageSetTests.test_equalityIterationAndAdditions@.\ \ R  B# !V R!$ bA3' &[ R!$ b9- &[ R  b2g 2 q  R!$ b<0 B# q!  R!$ b#89r6cN|jtttddy)z A L{MessageSet} that has a range that ends with L{None} raises a L{TypeError} when its length is requested. rN) assertRaises TypeErrorrrrRs r4test_lengthWithWildcardRangez,MessageSetTests.test_lengthWithWildcardRanges )S*Q*=>r6c.ttddy)zD L{MessageSet.__repr__} does not raise an exception rrN)reprrrRs r4test_reprSanityzMessageSetTests.test_reprSanitys Z1 r6ctjdtjdtjddtjddg}gd}t||D] \}}|jt ||"y)z In a L{MessageSet}, in the presence of wildcards, if the highest message id is known, the wildcard should get replaced by that high value. *1:*s3:*rs*:2)*1:*z3:6z2:6Nr parseIdListziprBstrrEinputsoutputsirps r4&test_stringRepresentationWithWildcardsz6MessageSetTests.test_stringRepresentationWithWildcardss~   d #   f %   fa (   fa (   ( (DAq   SVQ ' (r6ctjdtjdg}ddg}t||D] \}}|jt ||"y)z In a L{MessageSet}, inverting the high and low numbers in a range doesn't affect the meaning of the range. For example, 3:2 displays just like 2:3, because according to the RFC they have the same meaning. 2:3s3:22:3Nrrs r4&test_stringRepresentationWithInversionz6MessageSetTests.test_stringRepresentationWithInversionsf   f %   f %     ( (DAq   SVQ ' (r6ctd}|jt|d|jt|d|jt |dgy)z Creating a L{MessageSet} with a single message number adds only that message to the L{MessageSet}; its serialized form includes only that message number, its length is one, and it yields only that message number. r1NrrBrrrrEms r4"test_createWithSingleMessageNumberz2MessageSetTests.test_createWithSingleMessageNumber sK qM Q% Q# a1#&r6ctdd}|jt|d|jt|d|jt |gdy)a? Creating a L{MessageSet} with both a start and end message number adds the sequence between to the L{MessageSet}; its serialized form consists that range, its length is the length of the sequence, and it yields the message numbers inclusively between the start and end. r z1:10) rrrrrrrr rNrrs r4test_createWithSequencez'MessageSetTests.test_createWithSequencesM q"  Q( Q$ a"ABr6ctd}|jt|d|jt|d|j t t |y)z Creating a L{MessageSet} with a single L{None}, representing C{*}, adds C{*} to the range; its serialized form includes only C{*}, its length is one, but it cannot be iterated over because its endpoint is unknown. Nrr)rrBrrrrrrs r4test_createWithSingleWildcardz-MessageSetTests.test_createWithSingleWildcard#sH t  Q% Q# )T1-r6ctd}d|_|jt|dgtdd}d|_|jt|gdy)z Setting L{MessageSet.last} replaces L{None}, representing C{*}, with that number, making that L{MessageSet} iterable. Nrrrr)rlastrBr)rEsingleMessageReplaced rangeReplaceds r4test_setLastSingleWildcardz*MessageSetTests.test_setLastSingleWildcard/sY !+4 0%'" 34rd;"1d+   m,i8r6ctdd}|jddd|_|jt |gdy)zL Setting L{MessageSet.last} replaces L{None} in all ranges. rNrrrrrrr)rrrrBrrs r4test_setLastWithWildcardRangez-MessageSetTests.test_setLastWithWildcardRange<s8 q$  a a/2r6ctdd}d|_|jt5d|_dddy#1swYyxYw)z9 L{MessageSet.last} cannot be set twice. rNrr)rrr ValueErrorrs r4test_setLastTwiceFailsz&MessageSetTests.test_setLastTwiceFailsEsA q$    z * AF   s :Ac"td}d|_|jd|jt |ddg|jt |dzgd|jdd|jt |gdy)a Adding a L{None}, representing C{*}, or a sequence that includes L{None} to a L{MessageSet} whose L{last} property has been set replaces all occurrences of L{None} with the value of L{last}. rrN)Nr)rrrr)rrr)rrrrBr)rEhasLasts r4test_lastOverridesNoneInAddz+MessageSetTests.test_lastOverridesNoneInAddNstQ-  D gA/ g 12I> At g 2r6cbtdd}d|_|j|jdy)zF Accessing L{MessageSet.last} returns the last value. rNr)rrrBrs r4 test_getLastzMessageSetTests.test_getLastas+ q$  #r6c>t}|jd|jt|dgt}|jd|jt |dt}|jd|jt|gdt}|jd|jt |dt}|jtdd|jt|gdy)z L{MessageSet.extend} accepts as its arugment an L{int} or L{None}, or a sequence L{int}s or L{None}s of length two, or another L{MessageSet}, combining its argument with its instance's existing ranges. rNrrrNNr)rextendrBrr)rE extendWithIntextendWithNoneextendWithSequenceOfIntsextendWithSequenceOfNonesextendWithMessageSets r4 test_extendzMessageSetTests.test_extendis# Q m,qc2#d# ^,c2#-<  ''/ 67C$.L!!((6 67=)|##Jq!$45 23Y?r6ctdd}tddtddz}|jd||jd||dz}|jt5d|vddd|dz}|j dd|jt5d|vdddy#1swYCxYw#1swYyxYw) z A L{MessageSet} contains a number if the number falls within one of its ranges, and raises L{TypeError} if any range contains L{None}. rrrrrN)r r)rassertIn assertNotInrrr)rEhasFivedoesNotHaveFivehasFiveButHasNonehasFiveButHasNoneInSequences r4 test_containszMessageSetTests.test_containss Q"$Q*Z1-== a! O,#dN   y ) # " " #'.&8##''40   y ) - , , - -  # #  - -s$B+B7+B47Cctdd}tdd}||z}|tddz}|jt|dzgd|jt|d zgd |jt|d zgd |jt|d zgd|jt|d zgd|jt|tdzgdy)z Adding a sequence of message numbers to a L{MessageSet} that begins or ends immediately before or after an existing sequence in that L{MessageSet}, or overlaps one, merges the two. rrrrrr)rr)rrrr)rrr)rr)rrrr)rr)rrrrr)rrrrrrrrr)rrrrrrrN)rrBr)rE mergeAfter mergeBeforemergeBetweenSequencemergeBetweenNumbers r4test_rangesMergedz!MessageSetTests.test_rangesMergeds 1%  A& )K7'*Q*:: j612LA j612OD kF23\B kF23_E 2V;<>VW  #jm3 46K r6c|jtddtdd|jttddgdtdd}d|_|jt|ddgy)a Test the C{seq-range} examples from Section 9, "Formal Syntax" of RFC 3501:: Example: 2:4 and 4:2 are equivalent and indicate values 2, 3, and 4. Example: a unique identifier sequence range of 3291:* includes the UID of the last message in the mailbox, even if that value is less than 3291. @see: U{http://tools.ietf.org/html/rfc3501#section-9} rrrrri Ni )rBrrrrs r4test_seq_rangeExamplesz&MessageSetTests.test_seq_rangeExamplessi Aq):a+;< jA./; tT " a4,/r6cTtdtddztdztddz}d|_|jdjd |Dd tddtd dz}d |_|jdjd |Ddy)a Test the C{sequence-set} examples from Section 9, "Formal Syntax" of RFC 3501. In particular, L{MessageSet} reorders and coalesces overlaps:: Example: a message sequence number set of 2,4:7,9,12:* for a mailbox with 15 messages is equivalent to 2,4,5,6,7,9,12,13,14,15 Example: a message sequence number set of *:4,5:7 for a mailbox with 10 messages is equivalent to 10,9,8,7,6,5,4,5,6,7 and MAY be reordered and overlap coalesced to be 4,5,6,7,8,9,10. @see: U{http://tools.ietf.org/html/rfc3501#section-9} rrrrrN,c32K|]}t|ywr0r.0rs r4 z.s9SV9z2,4,5,6,7,9,12,13,14,15rrc32K|]}t|ywr0r*r+s r4r-z.s!BQ#a&!Br.z4,5,6,7,8,9,10)rrrBr)rEfromFifteenMessagesfromTenMessagess r4test_sequence_setExamplesz)MessageSetTests.test_sequence_setExampless$ qMJq!, ,z!} .cbProducedsB  $ $VQ /   ]c!fa[8#((188:L MMr6c(j|Sr0)r~)r2rs r4cbResumez4IMAP4HelperTests.test_fileProducer..cbResumes    Mr6)rwrr FileProducerrr)rEr3rrr>r<rrs` @@@r4test_fileProducerz"IMAP4HelperTests.test_fileProducersn 7   AJ   q !  Q     j! h}}Z((r6cdgdddggdgdgdgdgd gd gg}|D]j\}}}tj|d }|D]"}|j|j|$|D]"}|j |j|$ly) N foo/%gum/barzfoo/barzoo/lalagum/barz foo/gumx/barz foo/gum/baz foo/xgum/bar foo/gum/bar foo/x%x/barfoobarz fuz fuz fuzz foo/*/bar foo/xyz/barz foo/xx/baz) foo/xyx/bar foo/xx/barfoo/xxxxxxxxxxxxxx/barfoo/xyz*abc/barrJz foo/abc/barzfoo/xyzab/cbarzfoo/xyza/bcbarzfoo/xyzabc/barzfoo/xyz/abc/barzfoo/xyz/123/abc/bar/rwildcardToRegexp assertFalsematch assertTruerEcaseswildcardfailsucceedxs r4 test_wildcardzIMAP4HelperTests.test_wildcardsL/  WG  "RL  $(- 3 #HdG--h.checks%,,T2F   VhZ 0r6s8(BODY.PEEK[HEADER.FIELDS.NOT (subject bcc cc)] {%d} %b) BODY.PEEKsHEADER.FIELDS.NOT)ssubjectsbccsccs(FLAGS (\Seen) INTERNALDATE "17-Jul-1996 02:44:25 -0700" RFC822.SIZE 4286 ENVELOPE ("Wed, 17 Jul 1996 02:23:25 -0700 (PDT)" "IMAP4rev1 WG mtg summary and minutes" (("Terry Gray" NIL gray cac.washington.edu)) (("Terry Gray" NIL gray cac.washington.edu)) (("Terry Gray" NIL gray cac.washington.edu)) ((NIL NIL imap cac.washington.edu)) ((NIL NIL minutes CNRI.Reston.VA.US) ("John Klensin" NIL KLENSIN INFOODS.MIT.EDU)) NIL NIL ) BODY (TEXT PLAIN (CHARSET US-ASCII) NIL NIL 7BIT 3028 92))FLAGSs\Seens INTERNALDATEs17-Jul-1996 02:44:25 -0700s RFC822.SIZEs4286sENVELOPEs%Wed, 17 Jul 1996 02:23:25 -0700 (PDT)s$IMAP4rev1 WG mtg summary and minutes)s Terry GrayNsgraycac.washington.edu)NNsimapr)NNsminutessCNRI.Reston.VA.US)s John KlensinNsKLENSINsINFOODS.MIT.EDUs#BODYsTEXTPLAINCHARSETsUS-ASCIIs7BITs3028s92s("oo \"oo\" oo")rvs ("oo \\ oo")soo \\ oos ("oo \ oo")soo \ oos ("oo \o")soo \os(oo \o)rurw)rr)rEr|rs` r4test_parenParserz!IMAP4HelperTests.test_parenParsers5 LL%1 % 1  ISQRVUVK W 02MNPQ R   J -<;JKJKJKABFO:- 1" 0 d #m_5 -1 o }- mi[) mi[) kE6?+ kE6?+r6c gdgdgdgdgdgdgdgdgd g }|D]\}}}|jd }tj}|j||j t |j d |jt|j d t|||j t|j d |y) N)ENVELOPEEnvelopeenvelope)FLAGSFlagsflags) INTERNALDATE InternalDate internaldate) RFC822.HEADER RFC822Headerz rfc822.header) RFC822.SIZE RFC822Sizez rfc822.size) RFC822.TEXT RFC822Textz rfc822.text)RFC822rrfc822)UIDruid) BODYSTRUCTURE BodyStructure bodystructureasciirr) rCr _FetchParser parseStringrBrr2rV isinstancegetattrr)rErXinpoutpasStringrs r4test_fetchParserSimplez'IMAP4HelperTests.test_fetchParserSimples 0 ' < > 8 8 * ! ?  $) 9 Cx**W%C""$A MM#    S]A . OOJqxx{GAt4DE F   S!-x 8  9r6cddgdfgddgdfgddgd fgg}|D]\}}tj}|j||jt |j |d |j Dcgc]*}t |jjd ,}}|j|d j|j||d ycc}w) NsALLr)flags internaldate rfc822.sizeenvelopesFULLr)rrrrsbodysFASTr)rrrrrr) rrrrBrr2rlowerrCsort)rErXrrrtokenexpectedResults r4test_fetchParserMacrosz'IMAP4HelperTests.test_fetchParserMacross aQR SUV qEF G   6IC""$A MM#    S]DG 4NOhhWUc%j..077@WNW    ! GLLN   ^T!W 5 6Xs;/C'cZtj}|}|jd|jt |j d|j t|j d|j|j|j djd|j|j djd|jt|j dd|}|jd|jt |j d|j t|j d|j|j|j djd|jt|j dd|}|jd|jt |j d|j t|j d|j|j|j djd|jt|j dd |}|jd |jt |j d|j t|j d|j|j|j djd|j t|j dj|j|j|j djjd|j|j djjd |j|j djd|jt|j dd |}|jd |jt |j d|j t|j d|j|j|j djd|j t|j dj|j|j|j djjd|j|j djjd |j|j djd|jt|j dd |}|jd|jt |j d|j t|j d|j|j|j djd|j t|j dj|j|j|j djjd|j|j djjgd|j|j djd|jt!|j dd|}|jd|jt |j d|j t|j d|j|j|j djd|j t|j dj|j|j|j djjd|j|j djjgd|j|j djd|jt!|j dd|}|jd|jt |j d|j t|j d|j|j|j djd|j t|j dj|j|j|j djjd|j|j djjgd|j|j djd|jt!|j dd|}|jd|jt |j d|j t|j d|j|j|j djd|j t|j dj"|j$|j|j dj&d|j|j dj(d|j|j dj*d|j|j djd|jt!|j dd|}|jd|jt |j d|j t|j d|j|j|j djd|j t|j dj|j|j|j dj&d|j|j djjddg|j|j dj(d|j|j dj*d|j|j djd|jt!|j ddy)NrrrFBODYrTsBODY[]zBODY[]s BODY[HEADER]r1z BODY[HEADER]sBODY.PEEK[HEADER]s+BODY[HEADER.FIELDS (Subject Cc Message-Id)])sSUBJECTsCC MESSAGE-IDs0BODY.PEEK[HEADER.FIELDS (Subject Cc Message-Id)]s4BODY.PEEK[HEADER.FIELDS.NOT (Subject Cc Message-Id)]s/BODY[HEADER.FIELDS.NOT (Subject Cc Message-Id)]sBODY[1.MIME]<10.50>rr2s?BODY.PEEK[1.3.9.11.HEADER.FIELDS.NOT (Message-Id Date)]<103.69>)rrrrrsDATEgEs:BODY[1.3.9.11.HEADER.FIELDS.NOT (Message-Id Date)]<103.69>)rrrrBrr2rVrBodypeekheaderremptyHeadernegatefieldsrLmimeMIMEpart partialBegin partialLength)rEPrs r4test_fetchParserBodyz%IMAP4HelperTests.test_fetchParserBodys    C g QXX*  188A;78 !))51 !++T2 QXXa[)62 C l# QXX*  188A;78 !))40 QXXa[)62 C i  QXX*  188A;78 !**D1 QXXa[)84 C o& QXX*  188A;78 !))51  188A;#5#5qxx@A !++22D9 !++22B7 !**E2 QXXa[)>: C *+ QXX*  188A;78 !))40  188A;#5#5qxx@A !++22D9 !++22B7 !**E2 QXXa[)>: C DE QXX*  188A;78 !))51  188A;#5#5qxx@A !++22E: !++224VW !**E2  !((1+  N  C IJ QXX*  188A;78 !))40  188A;#5#5qxx@A !++22E: !++224VW !**E2  !((1+  N  C MN QXX*  188A;78 !))40  188A;#5#5qxx@A !++22D9 !++224VW !**E2  !((1+  R  C ,- QXX*  188A;78 !))51  188A;#3#3QVV<= !))40 !1126 !22B7 !**E2 qxx{+-CD C N  QXX*  188A;78 !))40  188A;#5#5qxx@A !))=9 !++22]G4LM !1137 !22B7 !**E2  !((1+  I r6ctj}|jd|jt |j d|j|j dj d|j|j d|j|j|j dj|j|jt|j ddy)z Parsing a C{BODY} whose C{HEADER} values require quoting results in a object that perserves that quoting when serialized. sBODY[HEADER.FIELDS ((Quoted)]rrFsBODY[HEADER.FIELDS ("(Quoted")]N) rrrrBrr2rassertIsInstancerrrrLrErs r4test_fetchParserQuotedHeaderz-IMAP4HelperTests.test_fetchParserQuotedHeaders     67 QXX* !))51 ahhqk1662 ahhqk00!((; qxx{+-OPr6ctj}|jd|jt |j y)z= Parsing an empty string results in no data. r6N)rrrrTrr2rs r4test_fetchParserEmptyStringz,IMAP4HelperTests.test_fetchParserEmptyStrings4     c QXX'r6cntj}|jt|jdy)z\ Parsing a string with an unknown attribute raises an L{Exception}. sUNKNOWNNrrr Exceptionrrs r4 test_fetchParserUnknownAttributez1IMAP4HelperTests.test_fetchParserUnknownAttributes(     )Q]]J?r6cntj}|jt|jdy)zf Parsing a string that prematurely ends in whitespace raises an L{Exception}. sBODY[HEADER.FIELDS Nrrs r40test_fetchParserIncompleteStringEndsInWhitespacezAIMAP4HelperTests.test_fetchParserIncompleteStringEndsInWhitespace)     )Q]]4KLr6cntj}|jt|jdy)z Parsing a string that contains an unexpected character rather than whitespace raises an L{Exception}. sBODY[HEADER.FIELDS!]Nrrs r4"test_fetchParserExpectedWhitespacez3IMAP4HelperTests.test_fetchParserExpectedWhitespacerr6ctj}|jd|jt |j d|j |j d|j|j|j djd|j |j dj|j|jt|j ddy)z: A C{BODY} can contain a C{TEXT} section. s BODY[TEXT]rrFN) rrrrBrr2rrrrFTextrLrs r4test_fetchParserTextSectionz,IMAP4HelperTests.test_fetchParserTextSections     m$ QXX* ahhqk1662 !))51 ahhqk..7 qxx{+];r6cntj}|jt|jdy)z[ Parsing a C{BODY} with an unknown section raises an L{Exception}. s BODY[UNKNOWN]Nrrs r4test_fetchParserUnknownSectionz/IMAP4HelperTests.test_fetchParserUnknownSections)     )Q]]4DEr6ctj}|jt|jdtj}|jt|jdy)ze Parsing a C{BODY} with an unterminated section list raises an L{Exception}. s BODY[HEADERsBODY[HEADER.FIELDS (SUBJECT)Nrrs r4#test_fetchParserMissingSectionClosez4IMAP4HelperTests.test_fetchParserMissingSectionClosesM     )Q]]NC     )Q]]4STr6ctj}|jt|jdtj}|jt|jdy)z Parsing a C{BODY} whose C{HEADER.FIELDS} list does not begin with an open parenthesis (C{(}) or end with a close parenthesis (C{)}) raises an L{Exception}. sBODY[HEADER.FIELDS Missing)]sBODY[HEADER.FIELDS (Missing]Nrrs r4(test_fetchParserHeaderMissingParenthesesz9IMAP4HelperTests.test_fetchParserHeaderMissingParenthesessN     )Q]]4ST     )Q]]4STr6cntj}|jt|jdy)zk Parsing a C{BODY} with a range that lacks a period (C{.}) raises an L{Exception}. sBODY<01>Nrrs r4test_fetchParserDotlessPartialz/IMAP4HelperTests.test_fetchParserDotlessPartials(     )Q]]K@r6cntj}|jt|jdy)z Parsing a C{BODY} with a partial range that's missing its closing greater than sign (C{>}) raises an L{EXCEPTION}. sBODY<0Nrrs r4test_fetchParserUnclosedPartialz0IMAP4HelperTests.test_fetchParserUnclosedPartials(     )Q]]I>r6ctdddtdddg}d}|jtj||y)NrHrIbazthis is a file buzbizs4"foo" "bar" "baz" {16} this is a file "buz" "biz")rrBrcollapseNestedLists)rEinputStructurer^s r4 test_fileszIMAP4HelperTests.test_filessD    ) *    M 22>BFKr6cdtjddtddtjddg}d}|jtj||y) Nrqrrsbazrsthis is quotedsbuzr6sC"foo" bar "baz" {16} this is a file {15} this is quoted buz "")r DontQuoteMerrBrrcs r4test_quoteAvoiderz"IMAP4HelperTests.test_quoteAvoidersa    f %  ) *   f %     22596Br6cpddggfg}|D]*\}}|jtj||,y)Ns({10} 0123456789)s 0123456789)rBrr)rErXr}rhs r4 test_literalszIMAP4HelperTests.test_literalssH $ &7 8 $ FND(   U44T:H E Fr6ctjdtjdddtjtjdtjdtjdtjtjdtjdtjdtjtjtjtjdd d tjdd d tjddddtjtjdtjtjdg}gd}t ||D]\}}|j ||y)Nr)flagged)rf unflaggeddeleted)rtoday)before)unseen)new yesterdayi)rfsincesmallertuesdayi')rfrlarger)rfrrrspam)rz1:5r)FLAGGEDz(DELETED UNFLAGGED)z(OR FLAGGED DELETED)z(BEFORE "today")z(OR DELETED (OR UNSEEN NEW))z(OR (NOT (OR (SINCE "yesterday" SMALLER 1000) (OR (BEFORE "tuesday" LARGER 10000) (OR (BEFORE "today" DELETED UNSEEN) (NOT (SUBJECT "spam")))))) (NOT (UID 1:5))))rQueryOrNotrrB)rErrqueryrhs r4test_queryBuilderz"IMAP4HelperTests.test_queryBuilders2 KK " KKqAq 9 HHU[[+U[[-C D KKw ' HHU[[+U[[-BEKKTUDV W HH HH 1KN 1YuM 1Q'R %++f"=>  %++%01   &   #673 .OE8   UH - .r6cTtjd}|jd|y)z When passed the C{keyword} argument, L{imap4.Query} returns an unquoted string. @see: U{http://tools.ietf.org/html/rfc3501#section-9} @see: U{http://tools.ietf.org/html/rfc3501#section-6.4.4} twisted)keywordz(KEYWORD twisted)NrrrBrErs r4test_queryKeywordFlagWithQuotesz0IMAP4HelperTests.test_queryKeywordFlagWithQuotes@s# I. ,e4r6cTtjd}|jd|y)z When passed the C{unkeyword} argument, L{imap4.Query} returns an unquoted string. @see: U{http://tools.ietf.org/html/rfc3501#section-9} @see: U{http://tools.ietf.org/html/rfc3501#section-6.4.4} r) unkeywordz(UNKEYWORD twisted)Nrrs r4!test_queryUnkeywordFlagWithQuotesz2IMAP4HelperTests.test_queryUnkeywordFlagWithQuotesKs# i0 .6r6c|tjtjdd}|j|dy)z When passed a L{MessageSet}, L{imap4.Query} returns a query containing a quoted string representing the ID sequence. rNmessagesz(MESSAGES "1:*"))rrrrBrs r4test_queryWithMesssageSetz*IMAP4HelperTests.test_queryWithMesssageSetVs0  U%5%5a%>?  23r6cTtjd}|j|dy)zl When passed an L{int}, L{imap4.Query} returns a query containing a quoted integer. rrz(MESSAGES "1")Nrrs r4test_queryWithIntegerz&IMAP4HelperTests.test_queryWithInteger^s#  Q'  01r6c|jtjtjtjdy)zq An L{imap4.Or} query with less than two arguments raises an L{imap4.IllegalQueryError}. rrN)rrIllegalQueryErrorrrrRs r4test_queryOrIllegalQueryz)IMAP4HelperTests.test_queryOrIllegalQueryfs* %11588U[[RS=TUr6c.|jd|jdtjd i|di|jd|jdtjd i|ddj dt dDdiy ) z Helper to implement tests for value filtering of KEYWORD and UNKEYWORD queries. @param keyword: A native string giving the name of the L{imap4.Query} keyword argument to test. (z twistedrocks)ztwisted (){%*"\] rocksztwisted c32K|]}t|ywr0)ro)r,chs r4r-z9IMAP4HelperTests._keywordFilteringTest..s;2s2w;r.!z rocksNr1)rBupperrrrrn)rErs r4_keywordFilteringTestz&IMAP4HelperTests._keywordFilteringTestms    / KK ?7$=> ?    / KK ww;r;;>  r6c&|jdy)a When passed the C{keyword} argument, L{imap4.Query} returns an C{atom} that consists of one or more non-special characters. List of the invalid characters: ( ) { % * " \ ] CTL SP @see: U{ABNF definition of CTL and SP} @see: U{IMAP4 grammar} @see: U{IMAP4 SEARCH specification} rNr-rRs r4test_queryKeywordFlagz&IMAP4HelperTests.test_queryKeywordFlags ""9-r6c&|jdy)a When passed the C{unkeyword} argument, L{imap4.Query} returns an C{atom} that consists of one or more non-special characters. List of the invalid characters: ( ) { % * " \ ] CTL SP @see: U{ABNF definition of CTL and SP} @see: U{IMAP4 grammar} @see: U{IMAP4 SEARCH specification} rNr/rRs r4test_queryUnkeywordFlagz(IMAP4HelperTests.test_queryUnkeywordFlags "";/r6czgd}|D]2}|jtjtj|d4y)z| Trying to parse an invalid representation of a sequence range raises an L{IllegalIdentifierError}. )s*:*rqs4:sbar:590NrrIllegalIdentifierErrorrrErrds r4test_invalidIdListParserz)IMAP4HelperTests.test_invalidIdListParsers; 3 E   ,,e.?.?  r6czgd}|D]2}|jtjtj|d4y)z Zeroes and negative values are not accepted in id range expressions. RFC 3501 states that sequence numbers and sequence ranges consist of non-negative numbers (RFC 3501 section 9, the seq-number grammar item). )s0:5s0:0s*:00s-3:5s1:-2s-1r4Nr5r7s r4#test_invalidIdListParserNonPositivez4IMAP4HelperTests.test_invalidIdListParserNonPositives< I E   ,,e.?.?  r6cgd}tddtddtddtddztddtdtddtdtdztdztddtddtddtdd ztdtddztdtddztd d ztddtd ztd d ztdd g}gd }t||D]*\}}|jtj||,t||D]p\}}|/|j t ttj|7ttj|}|j||d|d|d|ry)zi The function to parse sequence ranges yields appropriate L{MessageSet} objects. )rs5:*s1:2,5:*r1s1,2s1,3,5s1:10s1:10,11s 1:5,10:20s1,5:10s 1,5:10,15:20s 1:10,15,20:254:2rNrrrr r'r)NNNrrrrrr?r rzlen(z) = z != )rrrBrrrrr)rErrlengthsrdrhLs r4test_parseIdListz!IMAP4HelperTests.test_parseIdLists  $ q$  q$  q$ *Q"2 2 tT " qM q!  qMJqM )JqM 9 q"  q"  q! z"b1 1 qMJq"- - qMJq"- - 2r0B B q"  2 .B1C C q!  "K"673 AOE8   U..u5x @ A #673 YOE8!!)S%2C2CE2JK))%01  HUIT!d8,.WX  Yr6cN|jttjdy)zu L{imap4.parseTime} raises L{ValueError} when given a a time string whose format is invalid. invalidNrrr parseTimerRs r4test_parseTimeInvalidFormatz,IMAP4HelperTests.test_parseTimeInvalidFormats *eooyAr6cdgd}|D]'}|jttj|)y)zv L{imap4.parseTime} raises L{ValueError} when given a time string composed of invalid values. )zinvalid-July-2017z2-invalid-2017z2-July-invalidNrJ)rEinvalidStringsrIs r4test_parseTimeInvalidValuesz,IMAP4HelperTests.test_parseTimeInvalidValuess2   & DG   j%//7 C Dr6c t}|j|j|j|j |j d}t j||j}|j||y)z L{imap4.statusRequestHelper} builds a L{dict} mapping the requested status names to values extracted from the provided L{IMailboxIMAP}'s. )MESSAGESRECENTUIDNEXT UIDVALIDITYUNSEENN) SimpleMailboxgetMessageCountgetRecentCount getUIDNextgetUIDValiditygetUnseenCountrstatusRequestHelperkeysrB)rEmboxrhr2s r4test_statusRequestHelperz)IMAP4HelperTests.test_statusRequestHelpersx ,,.))+(..0))+  **4A 6*r6N),rsrtrur3r9r@r]r_rir~rrrrrrrrrrrrrrrrrrrrrrr r"r%r-r0r2r8r;rGrLrOr_r1r6r4r5r5s> )03464&8@tD0M,^9*6&r h Q(@MM <FU UA? LC(F!.F 5 742V 2 . 0  1YfB D+r6r5ceZdZUdZgZded<dZdZdZdZ dZ d Z d Z d Z d Zd ZdZdZdZdZddZdZdZdZdZdZy)rVz\Flag1Flag2z\AnotherSysFlagLastFlag+list[tuple[bytes, list[bytes], bytes, int]]rrrFc~g|_|jj|_|jj|_yr0 listenersr| addListenerremoveremoveListenerrRs r4rzzSimpleMailbox.__init__!->>00"nn33r6c|jSr0rrRs r4getFlagszSimpleMailbox.getFlags& zzr6cy)N*r1rRs r4rZzSimpleMailbox.getUIDValidity)sr6c2t|jdzSNrrrrRs r4rYzSimpleMailbox.getUIDNext,s4==!A%%r6cy)Nrr1rRs r4rWzSimpleMailbox.getMessageCount/r6cy)Nrr1rRs r4rXzSimpleMailbox.getRecentCount2rvr6cy)Nrr1rRs r4r[zSimpleMailbox.getUnseenCount5rvr6c|jSr0rwrRs r4 isWriteablezSimpleMailbox.isWriteable8s wwr6cyr0r1rRs r4destroyzSimpleMailbox.destroy; r6cy)NrQr1rRs r4getHierarchicalDelimiterz&SimpleMailbox.getHierarchicalDelimiter>sr6ci}d|vr|j|d<d|vr|j|d<d|vr|jdz|d<d|vr|j|d<d|vr|j|d<t j |S)NrQrRrSrrTrUrWrXgetUIDr[rr[rEnamesrs r4 requestStatuszSimpleMailbox.requestStatusAs    002AjM u --/AhK  //1A5AiL E !#{{}Am  u --/AhK}}Qr6Nc|jj||||jf|xjdz c_tjdSrsrr|mUIDrr[rEmessagerdates r4 addMessagezSimpleMailbox.addMessageOs= gudDII>? Q }}T""r6cg}|jD]}d|dvs |j||D]}|jj||Dcgc]}|d c}Scc}w)N\Deletedrrrr|rirEdeleters r4expungezSimpleMailbox.expungeTsm !Aad" a  ! $A MM  # $$%!%%% A"cd|_yNT)closedrRs r4closezSimpleMailbox.close]s  r6cyr0r1rErrs r4fetchzSimpleMailbox.fetch` r6cyr0r1rErs r4rzSimpleMailbox.getUIDdrr6cyr0r1rErrmoders r4storezSimpleMailbox.storehrr6r0)rsrtrurr__annotations__rr{rrzrnrZrYrWrXr[r|r~rrrrrrrrr1r6r4rVrVsv @E<>H9> D B F4 &   # &   r6rVceZdZUdZdZgZded<dZdZdZ dZ d Z d Z d Z d Zd ZdZdZdZdZdZddZdZdZdZdZy)UncloseableMailboxz* A mailbox that cannot be closed. rardrrrFc~g|_|jj|_|jj|_yr0rfrRs r4rzzUncloseableMailbox.__init__yrkr6c|jS)zB The flags @return: A sequence of flags. rmrRs r4rnzUncloseableMailbox.getFlags~s zzr6cy)zF The UID validity value. @return: The value. rqr1rRs r4rZz!UncloseableMailbox.getUIDValiditys r6c2t|jdzS)z: The next UID. @return: The UID. rrtrRs r4rYzUncloseableMailbox.getUIDNexts 4==!A%%r6cy)zG The number of messages. @return: The number. rr1rRs r4rWz"UncloseableMailbox.getMessageCount r6cy)D The recent messages. @return: The number. rr1rRs r4rXz!UncloseableMailbox.getRecentCountrr6cy)rrr1rRs r4r[z!UncloseableMailbox.getUnseenCountrr6c|jS)z` The recent messages. @return: Whether or not the mailbox is writable. rzrRs r4r|zUncloseableMailbox.isWriteables wwr6cy)z' Destroy this mailbox. Nr1rRs r4r~zUncloseableMailbox.destroys r6cy)zU Return the hierarchical delimiter. @return: The delimiter. rQr1rRs r4rz+UncloseableMailbox.getHierarchicalDelimiters r6ci}d|vr|j|d<d|vr|j|d<d|vr|jdz|d<d|vr|j|d<d|vr|j|d<t j |S)z Return the mailbox's status. @param names: The status items to include. @return: A L{dict} of status data. rQrRrSrrTrUrrs r4rz UncloseableMailbox.requestStatuss    002AjM u --/AhK  //1A5AiL E !#{{}Am  u --/AhK}}Qr6Nc|jj||||jf|xjdz c_tjdS)a Add a message to the mailbox. @param message: The message body. @param flags: The message flags. @param date: The message date. @return: A L{Deferred} that fires when the message has been added. rNrrs r4rzUncloseableMailbox.addMessages? gudDII>? Q }}T""r6cg}|jD]}d|dvs |j||D]}|jj||Dcgc]}|d c}Scc}w)zj Delete messages marked for deletion. @return: A L{list} of deleted message IDs. rrrrrs r4rzUncloseableMailbox.expungeso  !Aad" a  ! $A MM  # $$%!%%%rcyr0r1rs r4rzUncloseableMailbox.fetchrr6cyr0r1rs r4rzUncloseableMailbox.getUIDrr6cyr0r1rs r4rzUncloseableMailbox.storerr6r0)rsrtrur3rrrrr{rrzrnrZrYrWrXr[r|r~rrrrrrrr1r6r4rrmsy AE<>H9> D B F4 &  *#" &   r6rc"eZdZdZeZdZddZy)AccountWithoutNamespaceszL An in-memory account that does not provide L{INamespacePresenter}. c"|jSr0)mailboxFactory)rEnameids r4 _emptyMailboxz&AccountWithoutNamespaces._emptyMailbox s""$$r6cXtjj||}|||_|Sr0)r MemoryAccountselectr{)rErr{r^s r4rzAccountWithoutNamespaces.selects,""))$5  DG r6Nr)rsrtrur3rVrrrr1r6r4rrs#N%r6rceZdZdZy)AccountzD An in-memory account that provides L{INamespacePresenter}. Nrsrtrur3r1r6r4rrsr6rc(eZdZedZdZdZy) SimpleServertestuserctjj|g|i|t|}t |}t }|j dd||_||_|j|d|_ y)N accountHolderr password-testF) r IMAP4Serverrz TestRealmrraddUsercheckerportalregisterChecker timeoutTest)rEargskwrealmrrs r4rzzSimpleServer.__init__sn ""45$5"5- 3 5 +/0  q! r6c^|jrytjj||yr0)rrr lineReceivedrElines r4rzSimpleServer.lineReceived*s$     &&tT2r6N)rsrtrur theAccountrzrr1r6r4rrs%J !3r6rc,eZdZddZdZdZdZdZy) SimpleClientNc`tjj||||_g|_yr0)r IMAP4Clientrzdeferredevents)rErcontextFactorys r4rzzSimpleClient.__init__3s& ""48   r6c:|jjdyr0)rcallback)rEcapss r4serverGreetingzSimpleClient.serverGreeting8s t$r6cr|jjd|g|jjy)N modeChangedrr| transportloseConnection)rE writeables r4rzSimpleClient.modeChanged;s) M956 %%'r6cr|jjd|g|jjy)N flagsChangedrrEnewFlagss r4rzSimpleClient.flagsChanged?s) NH56 %%'r6ct|jjd||g|jjy)N newMessagesr)rEexistsrecents r4rzSimpleClient.newMessagesCs+ M66:; %%'r6r0)rsrtrurzrrrrr1r6r4rr2s %(((r6rcNeZdZUdZded<dZded<dZdZdZd Z d Z d Z y) IMAP4HelperMixinNzOptional[ServerTLSContext] serverCTXzOptional[ClientTLSContext] clientCTXctj}t|j|_t ||j |_||_gt_ td}t|_ |t_ y)Nrr)rrrrserverrrclient connectedrVrrmboxTyper)rErrs r4setUpzIMAP4HelperMixin.setUpLsY NN "$..A "1T^^D !# [) + ", r6c|`|`|`yr0)rrrrRs r4tearDownzIMAP4HelperMixin.tearDownWs K K Nr6cL|jjjyr0)rrr)rEignores r4 _cbStopClientzIMAP4HelperMixin._cbStopClient\s ,,.r6c|jjj|jjjt j |dt |zy)N Problem with )rrrrr%errr)rEr$s r4 _ebGeneralzIMAP4HelperMixin._ebGeneral_sE ,,. ,,. 3t945r6cVtj|j|jSr0)r# loopbackAsyncrrrRs r4r#zIMAP4HelperMixin.loopbackds%%dkk4;;??r6c|jtjt|j}t |}|j ||y)a. Assert that the provided failure is an L{IMAP4Exception} with the given message. @param failure: A failure whose value L{IMAP4Exception} @type failure: L{failure.Failure} @param expected: The expected failure message. @type expected: L{bytes} N)traprIMAP4ExceptionrvaluerrB)rEr$rhrs r4assertClientFailureMessagez+IMAP4HelperMixin.assertClientFailureMessagegs?  U))*gmm$> (+r6) rsrtrurrrrrrr r#rr1r6r4rrHs7,0I)0,0I)0 - /6 @,r6rc>eZdZdZdZdZdZdZdZdZ dZ d Z d Z d Z d Zd ZdZdZdZdZdZdZdZdZdZdZdZdZdZdZdZdZdZ dZ!d Z"d!Z#d"Z$d#Z%d$Z&d%Z'd&Z(d'Z)d(Z*d)Z+d*Z,d+Z-d,Z.d-Z/d.Z0d/Z1d0Z2d1Z3d2Z4d3Z5y4)5IMAP4ServerTestscifd}jjt|jj}t j j|g}dddd|jfdS)Ncbfd}jjj|S)Ncpj|jjjyr0updaterrrrrrEs r4gotCapszAIMAP4ServerTests.testCapability..getCaps..gotCaps~$ A %%446r6rgetCapabilitiesrrrrEs r4getCapsz0IMAP4ServerTests.testCapability..getCaps}( 7;;..0<.st'7'7$'Gr6)rrr7 addErrbackr r gatherResultsr#)rErd1rrrhs` @@r4testCapabilityzIMAP4ServerTests.testCapabilityzsn F^^ ' 'g 7 B B4?? S   " 5 6"&dTJ}}GHHr6cRitjjd<fd}jj t |j j}tjj|g}ddddgd|j fdS)NCRAM-MD5cbfd}jjj|S)Ncpj|jjjyr0rrs r4rzIIMAP4ServerTests.testCapabilityWithAuth..getCaps..gotCapsrr6rrs r4rz8IMAP4ServerTests.testCapabilityWithAuth..getCapsr r6)r!r"r#AUTHc(jSr0r%)r&rexpCaprEs r4r5z9IMAP4ServerTests.testCapabilityWithAuth..st'7'7'Er6) rr challengersrrr7r'r rr(r#)rErr)rrr1s` @@r4testCapabilityWithAuthz'IMAP4ServerTests.testCapabilityWithAuths/A  , F^^ ' 'g 7 B B4?? S   " 5 6!]  }}EFFr6cd_fd}jjt|j j j }|jfdS)Nrctfd}jjjt|y)Ncd_yrs) loggedOutrRsr4 setLoggedOutzAIMAP4ServerTests.testLogout..logout..setLoggedOuts !"r6)rlogoutrr7)r8rEs r4r9z+IMAP4ServerTests.testLogout..logouts* # KK   , ,U<-@ Ar6c<jjdSrs)rBr7r&rEs r4r5z-IMAP4ServerTests.testLogout..st'7'7'Jr6)r7rrr7r'r r#)rEr9rs` r4 testLogoutzIMAP4ServerTests.testLogoutsR B ""5=1<.noop..setResponsess !* %%446r6)rnoopr)rArEs r4rBz'IMAP4ServerTests.testNoop..noops% 7 KK    * *< 8r6c<jjgSr0)rBr@r;s r4r5z+IMAP4ServerTests.testNoop..st'7'7'Kr6)r@rrr7r'r r#)rErBrs` r4testNoopzIMAP4ServerTests.testNoopsQ 9 ""5;/::4??K MMO}}KLLr6cfd}jjt|jj}t j |jg}|jjS)Nctjjdd}|jjyNrr)rloginrrrrEs r4rHz)IMAP4ServerTests.testLogin..logins, !!+/?@A MM$,, -r6) rrr7r'r rr(r# _cbTestLoginrErHr)rs` r4 testLoginzIMAP4ServerTests.testLoginsa .^^ ' 'e 5 @ @ Q   T]]_ 5 6}}T..//r6c|j|jjtj|j|jj dyNauthrBraccountrrstaterEignoreds r4rJzIMAP4ServerTests._cbTestLogin< ,,l.E.EF **F3r6c fd}jjt|jj}j }t j||g}|jjS)Nctjjdd}|jjyNrswrong-passwordrrHaddBothrrIs r4rHz/IMAP4ServerTests.testFailedLogin..login, !!+/@AA IId(( )r6) rrr7r'r r#rr(_cbTestFailedLoginrErHr)d2rs` r4testFailedLoginz IMAP4ServerTests.testFailedLoginse *^^ ' 'e 5 @ @ Q ]]_   R )}}T4455r6c|j|jjd|j|jjdy)Nunauth)rBrrQrRrSs r4r\z#IMAP4ServerTests._cbTestFailedLogins6 ,,d3 **H5r6c.dj_fd}jjt |j j }j}tj||g}|jjS)zj Attempting to log into a server that has no L{Portal} results in a failed login. Nctjjdd}|jjyrXrYrIs r4rHz7IMAP4ServerTests.test_loginWithoutPortal..loginr[r6) rrrrr7r'r r#rr(r\r]s` r4test_loginWithoutPortalz(IMAP4ServerTests.test_loginWithoutPortalss "  *^^ ' 'e 5 @ @ Q ]]_   R )}}T4455r6c\d}|jjj_fd}jj t |jj}j}tj||g}|j jS)z The server responds with a C{BAD} response when its portal attempts to log a user in with checker that claims to support L{IAccount} but returns an an avatar interface that is not L{IAccount}. cdddfS)Nz Not IAccountzNot an accountcyr0r1r1r6r4r5zVIMAP4ServerTests.test_nonIAccountAvatar..brokenRequestAvatar..r6r1)r&__s r4brokenRequestAvatarzDIMAP4ServerTests.test_nonIAccountAvatar..brokenRequestAvatars"$4lC Cr6ctjjdd}|jjyrGrYrIs r4rHz6IMAP4ServerTests.test_nonIAccountAvatar..logins, !!+/?@A IId(( )r6) rrr requestAvatarrrr7r'r r#rr(r\)rErjrHr)r^rs` r4test_nonIAccountAvatarz'IMAP4ServerTests.test_nonIAccountAvatars D2E   . *^^ ' 'e 5 @ @ Q ]]_   R )}}T4455r6cGddtfd}|j_fd}jj t |}|j jd|jfd}|j j|jjj}tj||g}|j jS)z Any exception raised by L{IMAP4Server.authenticateLogin} that is not L{UnauthorizedLogin} is logged results in a C{BAD} response. ceZdZdZy)AIMAP4ServerTests.test_loginException..UnexpectedException2 An unexpected exception. Nrr1r6r4UnexpectedExceptionrp r6rrcd)NWhoopsr1)userpasswdrrs r4raisesUnexpectedExceptionzGIMAP4ServerTests.test_loginException..raisesUnexpectedExceptions%h/ /r6c<jjddSrGrrHrRsr4rHz3IMAP4ServerTests.test_loginException..login ;;$$[2BC Cr6sServer error: WhoopscFjjyr0rVflushLoggedErrors)r&rrrEs r4assertErrorLoggedz?IMAP4ServerTests.test_loginException..assertErrorLoggeds OOD223FG Hr6)rrauthenticateLoginrrr7r'rr rZrr#rr(r\)rErxrHr)rr^rrrs` @r4test_loginExceptionz$IMAP4ServerTests.test_loginExceptions )   0)B % D^^ ' 'e 5 d557NO  I  I doo& 4%%& ]]_   R )}}T4455r6cBddijj_fd}jj t |j j}tjj|g}|j jS)N {test}user{test}passwordcjjdd}|jtjdt z|j jy)Nrrr)rrHr'r%r rrrrIs r4rHz9IMAP4ServerTests.testLoginRequiringQuoting..login"sG !!-1BCA LL/CI"= > MM$,, -r6) rrusersrrr7r'r rr(r#_cbTestLoginRequiringQuotingrKs` r4testLoginRequiringQuotingz*IMAP4ServerTests.testLoginRequiringQuotingsy%24E$F ! . ^^ ' 'e 5 @ @ Q   " 5 6}}T>>??r6c|j|jjtj|j|jj dyrNrPrSs r4rz-IMAP4ServerTests._cbTestLoginRequiringQuoting+rUr6cd_fd}fd}jjt|}|jt||j j j }tj||g}|jfd}|jjddggggg|S)Nc<jjddSrGrzrRsr4rHz-IMAP4ServerTests.testNamespace..login2r{r6c`fd}jjj|S)Nc6|_jdyr0 namespaceArgsrrrEs r4 gotNamespacezGIMAP4ServerTests.testNamespace..namespace..gotNamespace6%)"""4(r6r namespacerrrEs r4rz1IMAP4ServerTests.testNamespace..namespace5( );;((*66|D Dr6cjD]&}|D]}|D]}j|t!(jSr0)rrr)rT namespacespairrrEs r4assertAllPairsNativeStringszCIMAP4ServerTests.testNamespace..assertAllPairsNativeStringsBsT"00 : &:D!%:--eS9:: :%% %r6r(rQ) rrrr7r'r r#rr(rB)rErHrr)r^rrs` r4 testNamespacezIMAP4ServerTests.testNamespace/s! D E^^ ' 'e 5 uY'( doo& ]]_   R )  &  & d&&2s)b"(=>r6ctdj_d_fd}fd}jj t |}|j t ||jjj}tj||g}|j fd|j jgggg|S)z A mailbox that does not provide L{INamespacePresenter} returns empty L{list}s for its personal, shared, and user namespaces. rNc<jjddSrGrzrRsr4rHz.loginUr{r6c`fd}jjj|S)Nc6|_jdyr0rrs r4rzVIMAP4ServerTests.test_mailboxWithoutNamespace..namespace..gotNamespaceYrr6rrs r4rz@IMAP4ServerTests.test_mailboxWithoutNamespace..namespaceXrr6cjSr0)rr;s r4r5z?IMAP4ServerTests.test_mailboxWithoutNamespace..ds  2 2r6) rrrrrrr7r'r r#rr(rB)rErHrr)r^rs` r4test_mailboxWithoutNamespacez-IMAP4ServerTests.test_mailboxWithoutNamespaceMs ":+!F ! D E^^ ' 'e 5 uY'( doo& ]]_   R ) 23 d&&R 5r6ctjjdd_fd}fd}jj t |}|j t ||jjj}tj||gj jS)N test-mailboxc<jjddSrGrzrRsr4rHz*IMAP4ServerTests.testSelect..loginlr{r6cjfd}jjd}|j||S)Nc6|_jdyr0) selectedArgsrrs r4selectedz=IMAP4ServerTests.testSelect..select..selectedp$(!""4(r6r)rrr)rrrEs r4rz+IMAP4ServerTests.testSelect..selectos/ ) "">2A MM( #Hr6) rr addMailboxrrrr7r'r r#rr( _cbTestSelect)rErHrr)r^s` r4 testSelectzIMAP4ServerTests.testSelecths**>:  D ^^ ' 'e 5 uV}% doo& ]]_""B8,889K9KLLr6cfd}fd}jjt|jjt|jjjdjjj jjj tjjjg}|jfd}|S)zh A client that selects a mailbox that does not exist receives a C{NO} response. c<jjddSrGrzrRsr4rHz9IMAP4ServerTests.test_selectWithoutMailbox..loginr{r6c:jjdS)NrrrrRsr4rz:IMAP4ServerTests.test_selectWithoutMailbox..select;;%%n5 5r6No such mailboxcPjjjyr0) assertIsNonerr^r;s r4assertNoMailboxSelectedzKIMAP4ServerTests.test_selectWithoutMailbox..assertNoMailboxSelecteds   dkk.. /r6) rrr7r'rrr rr(r#)rErHrconnectionCompleters` r4test_selectWithoutMailboxz*IMAP4ServerTests.test_selectWithoutMailbox~s  D 6 ""5<0 ""5=1 !!$"A"ACUV ""4#5#56 !!$//2"00$..$--/1RS  ' ' 0 ( 0"!r6c tjjd}|j|jj ||j|j ddddddy)N TEST-MAILBOXrrrqraTEXISTSrRrTr READ-WRITE)rr mailboxesrBrr^rrErTr^s r4rzIMAP4ServerTests._cbTestSelects]&&00@ ))40    !M"   r6ctjjdd_fd}fd}jj t |}|j t ||jjj}tj||g}|j jS)a L{IMAP4Client.examine} issues an I{EXAMINE} command to the server and returns a L{Deferred} which fires with a C{dict} with as many of the following keys as the server includes in its response: C{'FLAGS'}, C{'EXISTS'}, C{'RECENT'}, C{'UNSEEN'}, C{'READ-WRITE'}, C{'READ-ONLY'}, C{'UIDVALIDITY'}, and C{'PERMANENTFLAGS'}. Unfortunately the server doesn't generate all of these so it's hard to test the client's handling of them here. See L{IMAP4ClientExamineTests} below. See U{RFC 3501}, section 6.3.2, for details. rNc<jjddSrGrzrRsr4rHz,IMAP4ServerTests.test_examine..loginr{r6cjfd}jjd}|j||S)Nc6|_jdyr0) examinedArgsrrs r4examinedz@IMAP4ServerTests.test_examine..examine..examinedrr6r)rexaminer)rrrEs r4rz.IMAP4ServerTests.test_examine..examines/ ) ##N3A MM( #Hr6) rrrrrrr7r'r r#rr(_cbTestExamine)rErHrr)r^rs` r4 test_examinezIMAP4ServerTests.test_examines **>:  D ^^ ' 'e 5 uW~& doo& ]]_   R )}}T0011r6c tjjd}|j|jj ||j|j ddddddy)NrrrrqraFr)rrrrBrr^rrs r4rzIMAP4ServerTests._cbTestExamines]&&00@ ))40    !M#   r6cR d dfdfdfd} fd}g_jjt|jt|}j }t j ||g}|jj S)N)testboxtest/boxztest/ test/box/boxINBOX)rrc<jjdyrsr2r|rRsr4cbz'IMAP4ServerTests.testCreate..cb KK  q !r6c<jjdyNrrr$rEs r4ebz'IMAP4ServerTests.testCreate..ebrr6c<jjddSrGrzrRsr4rHz*IMAP4ServerTests.testCreate..loginr{r6czD]F}jj|}|jtj Hj j jyr0)rcreaterr7r' addCallbacksrr )rrrrrZrEr[s r4rz+IMAP4ServerTests.testCreate..creates_$ 8KK&&t, eBi(33B7 8 NN4--t ?r6)r2rrr7r#rr( _cbTestCreate) rErHrr)r^rrrrZr[s ` @@@@r4 testCreatezIMAP4ServerTests.testCreatesK& " " D @ @  ^^ ' 'e 5 A A%- P ]]_   R )}}T//$??r6c<|j|jdgt|zdgt|zzttj j }tgd}|j||Dcgc]}|jc}ycc}w)Nrr)inboxrrtestr)rBr2rrfrrrr,)rErTr[rZr^rzas r4rzIMAP4ServerTests._cbTestCreatesu qcCL&8A3T?&JKl--778QR 7;a ;<;s:B ctjjdfd}fd}jj t |}|j t |j|j jjj}tj||g}|j fd|S)N delete/mec<jjddSrGrzrRsr4rHz*IMAP4ServerTests.testDelete..loginr{r6c:jjdSNrrrrRsr4rz+IMAP4ServerTests.testDelete..delete;;%%k2 2r6cjjttjjgSr0)rBrrrrr;s r4r5z-IMAP4ServerTests.testDelete.. s&d&&tL,C,C,M,M'NPRSr6 rrrrrr7rr rr#rr()rErHrr)r^rs` r4 testDeletezIMAP4ServerTests.testDeletes**;7 D 3^^ ' 'e 5 f t7 **DOO< ]]_   R ) S r6ctjjdtjjdfd}fd}fd}jj t |}|j t |j|j||j jj}tj||g}|j fd|S)z Attempting to delete a mailbox with hierarchically inferior names fails with an informative error. @see: U{https://tools.ietf.org/html/rfc3501#section-6.3.4} @return: A L{Deferred} with assertions. rrc<jjddSrGrzrRsr4rHzGIMAP4ServerTests.testDeleteWithInferiorHierarchicalNames..login r{r6c:jjdSNrrrRsr4rzHIMAP4ServerTests.testDeleteWithInferiorHierarchicalNames..delete ;;%%h/ /r6c|jtjjt |j t dy)Ns-Name "DELETE" has inferior hierarchical names)rrrrBrrrs r4assertIMAPExceptionzUIMAP4ServerTests.testDeleteWithInferiorHierarchicalNames..assertIMAPException s: GLL-- .   GMM"DE r6cnjttjjddgS)NDELETEz DELETE/ME)rBrfrrrr;s r4r5zJIMAP4ServerTests.testDeleteWithInferiorHierarchicalNames.., s-d&&|..889Hk;Rr6) rrrrrr7rr r'rr#rr()rErHrrloggedIn loopedBackrs` r4'testDeleteWithInferiorHierarchicalNamesz8IMAP4ServerTests.testDeleteWithInferiorHierarchicalNames s **84**;7 D 0 >>--eEl;eFmT__=/0d001]]_   : 6 7   r6cd_fd}fd}fd}jjt|}|j t|j |j ||j jj j}tj||g}|jfd|S)Nc<jjddSrGrzrRsr4rHz6IMAP4ServerTests.testIllegalInboxDelete..login5 r{r6c:jjdS)NrrrRsr4rz7IMAP4ServerTests.testIllegalInboxDelete..delete8 s;;%%g. .r6c|_yr0stashedr2rEs r4stashz6IMAP4ServerTests.testIllegalInboxDelete..stash; s !DLr6cjjtjtjSr0rVrrr$Failurer;s r4r5z9IMAP4ServerTests.testIllegalInboxDelete..E doojw&OPr6 rrrr7rr rZrr#rr()rErHrrr)r^rs` r4testIllegalInboxDeletez'IMAP4ServerTests.testIllegalInboxDelete2 s  D / "^^ ' 'e 5 f t7 5 **DOO< ]]_   R ) P r6cfd}fd}fd}d_jjt|}|jt|j ||j j jj}tj||g}|jfd|S)Nc<jjddSrGrzrRsr4rHz5IMAP4ServerTests.testNonExistentDelete..loginJ r{r6c:jjdSrrrRsr4rz6IMAP4ServerTests.testNonExistentDelete..deleteM rr6c|_yr0r$rs r4 deleteFailedz.deleteFailedP "DLr6ctjtjjtdS)NrrBrr$rr;s r4r5z8IMAP4ServerTests.testNonExistentDelete..Z s)d&&s4<<+=+='>DV@WXr6) r$rrr7r'rrr r#rr()rErHrr r)r^rs` r4testNonExistentDeletez&IMAP4ServerTests.testNonExistentDeleteI s D 3 # ^^ ' 'e 5 uV}%00> **DOO< ]]_   R ) X r6cJt}d|_tjj d|tjj dfd}fd}fd}d_j jt|}|jt|j||jjjj}tj||g}t!d|jfd|S) N)z \Noselectrrc<jjddSrGrzrRsr4rHz1IMAP4ServerTests.testIllegalDelete..logind r{r6c:jjdSrrrRsr4rz2IMAP4ServerTests.testIllegalDelete..deleteg rr6c|_yr0rrs r4r z8IMAP4ServerTests.testIllegalDelete..deleteFailedj r r6s<Hierarchically inferior mailboxes exist and \Noselect is setcbjtjjSr0r )r&rhrEs r4r5z4IMAP4ServerTests.testIllegalDelete..v s# 0 0T\\5G5G1H( Sr6)rVrrrrr$rrr7r'rrr r#rr(r) rErrHrr r)r^rrhs ` @r4testIllegalDeletez"IMAP4ServerTests.testIllegalDelete^ s O!**8Q7**;7 D 0 # ^^ ' 'e 5 uV}%00> **DOO< ]]_   R ) P  STr6ctjjdfd}fd}jj t |}|j t |j|j jjj}tj||g}|j fd|S)Noldmboxc<jjddSrGrzrRsr4rHz*IMAP4ServerTests.testRename..login| r{r6c<jjddS)NsoldmboxsnewnamerrenamerRsr4rz+IMAP4ServerTests.testRename..rename s;;%%j*= =r6cjttjjj dgS)NNEWNAME)rBrrrrr]r;s r4r5z-IMAP4ServerTests.testRename.. s3d&&\,,66;;=> r6rrErHrr)r^rs` r4 testRenamezIMAP4ServerTests.testRenamey s**95 D >^^ ' 'e 5 f t7 **DOO< ]]_   R )   r6cd_fd}fd}fd}jjt|}|j t|j |j ||j jj j}tj||g}|jfd|S)Nc<jjddSrGrzrRsr4rHz6IMAP4ServerTests.testIllegalInboxRename..login r{r6c<jjddS)NrfrotzrrRsr4rz7IMAP4ServerTests.testIllegalInboxRename..rename s;;%%gw7 7r6c|_yr0r)stuffrEs r4rz6IMAP4ServerTests.testIllegalInboxRename..stash s  DLr6cjjtjtjSr0rr;s r4r5z9IMAP4ServerTests.testIllegalInboxRename.. rr6r)rErHrrr)r^rs` r4testIllegalInboxRenamez'IMAP4ServerTests.testIllegalInboxRename s  D 8 !^^ ' 'e 5 f t7 5 **DOO< ]]_   R ) P r6ctjjdtjjdfd}fd}jj t |}|j t |j|j jjj}tj||g}|j jS)Nz oldmbox/m1z oldmbox/m2c<jjddSrGrzrRsr4rHz6IMAP4ServerTests.testHierarchicalRename..login r{r6c<jjddS)NrnewnamerrRsr4rz7IMAP4ServerTests.testHierarchicalRename..rename s;;%%i; ;r6) rrrrrr7rr rr#rr(_cbTestHierarchicalRenamers` r4testHierarchicalRenamez'IMAP4ServerTests.testHierarchicalRename s&&|4&&|4 D <^^ ' 'e 5 f t7 **DOO< ]]_   R )}}T;;<!'')!>?!>sA0 cpfd}fd}jjt|}|jt|j|jj jj }tj||g}|jfd|S)Nc<jjddSrGrzrRsr4rHz-IMAP4ServerTests.testSubscribe..login r{r6c:jjdSNz this/mbox)r subscriberRsr4r2z1IMAP4ServerTests.testSubscribe..subscribe s;;((5 5r6cZjtjjdgS)N THIS/MBOXrBrr subscriptionsr;s r4r5z0IMAP4ServerTests.testSubscribe.. %d&&''55 }r6) rrr7rr rr#rr()rErHr2r)r^rs` r4 testSubscribezIMAP4ServerTests.testSubscribe s D 6^^ ' 'e 5 i($//: **DOO< ]]_   R )   r6cddgtj_fd}fd}jj t |}|j t |j|j jjj}tj||g}|j fd|S)Nr4 THAT/MBOXc<jjddSrGrzrRsr4rHz/IMAP4ServerTests.testUnsubscribe..login r{r6c:jjdSr1)r unsubscriberRsr4r=z5IMAP4ServerTests.testUnsubscribe..unsubscribe s;;**;7 7r6cZjtjjdgS)Nr:r5r;s r4r5z2IMAP4ServerTests.testUnsubscribe.. r7r6) rrr6rrr7rr rr#rr()rErHr=r)r^rs` r4testUnsubscribez IMAP4ServerTests.testUnsubscribe s1.login r{r6c|_yr0listed)rzrEs r4rEz+IMAP4ServerTests._listSetup..listed s !DKr6cjSr0rDr;s r4r5z-IMAP4ServerTests._listSetup.. s 4;;r6) rrrrErrr7rr rr#rr()rEr3rHrEr)r^s` r4 _listSetupzIMAP4ServerTests._listSetup s**?;**+?@**+>? D " ^^ ' 'e 5 a$//2 0 **DOO< ]]_""B8,889NOOr6c||D]6}|j|dtd|j|dtd8|S)z Assert a C{LIST} response's delimiter and mailbox are native strings. @param results: A list of tuples as returned by L{IMAP4Client.list} or L{IMAP4Client.lsub}. rzdelimiter %r is not a strrzmailbox %r is not a str)rr)rEresultsr2s r4'assertListDelimiterAndMailboxAreStringsz8IMAP4ServerTests.assertListDelimiterAndMailboxAreStrings sJ MF  ! !&)S2M N  ! !&)S2K L Mr6c\fd}j|}|jfd}|S)Nc<jjddSNroot%)rrrRsr4 mailboxListz.IMAP4ServerTests.testList..mailboxList ;;##FC0 0r6c&ttjddfttjddfg}tdD]5}|j d\}}}j t|||f|7j |d|y)NrQ ROOT/SUBTHINGzROOT/ANOTHER-THINGrrzMore results than expected: )rfrVrrnpoprrT)rEexpectedContentsr&r delimitermailboxrEs r4assertListContentsz5IMAP4ServerTests.testList..assertListContents s ++,c?C ++,c3GH   1X ,2JJqM)y' E]Iw7$    V'CF:%N Or6)rGr)rErPrrXs` r4testListzIMAP4ServerTests.testList s7 1 OOK (  P  Pr6ctjjdfd}j|}|j j |j j tjddfg|S)NrSc<jjddSrM)rlsubrRsr4r\z'IMAP4ServerTests.testLSub..lsub rQr6rQ) rrr2rGrrJrBrVr)rEr\rs` r4testLSubzIMAP4ServerTests.testLSub sg))/: 1 OOD ! dBBC d&&-*=*=sO)T(UVr6ctjjdfd}fd}fd}d_jj t |}|jt |j|j|j|jjjj}tj||g}|j fd|S)NrAc<jjddSrGrzrRsr4rHz*IMAP4ServerTests.testStatus..login* r{r6c@jjddddS)NrArQrSrUrstatusrRsr4rbz+IMAP4ServerTests.testStatus..status- s;;%%oz9hW Wr6c|_yr0statusedrs r4rez-IMAP4ServerTests.testStatus..statused0 "DMr6cDjjddddS)Nrs10r)rQrSrU)rBrer;s r4r5z-IMAP4ServerTests.testStatus..; s"d&& A%1Mr6) rrrrerrr7rr rr#rr()rErHrbrer)r^rs` r4 testStatuszIMAP4ServerTests.testStatus' s**?; D X # ^^ ' 'e 5 f t7 $//2 **DOO< ]]_   R )   r6cfd}fd}fd}fd}dx__jjt |}|j t |j |j |||j jj j}tj||gjjS)Nc<jjddSrGrzrRsr4rHz0IMAP4ServerTests.testFailedStatus..loginB r{r6c@jjddddS)Nzroot/nonexistentrQrSrUrarRsr4rbz1IMAP4ServerTests.testFailedStatus..statusE s#;;%%"J 8 r6c|_yr0rdrs r4rez3IMAP4ServerTests.testFailedStatus..statusedJ rfr6c|_yr0rrs r4failedz1IMAP4ServerTests.testFailedStatus..failedM r r6) rer$rrr7rr rr#rr(_cbTestFailedStatus)rErHrbrernr)r^s` r4testFailedStatusz!IMAP4ServerTests.testFailedStatusA s D   # #(,+  ^^ ' 'e 5 f t7 &) **DOO< ]]_""B8,889Q9QRRr6c|j|jd|j|jjjdy)N)sCould not open mailbox)rBrer$rrrSs r4roz$IMAP4ServerTests._cbTestFailedStatusX s7 - ++002NOr6ctjtdtjj dfd}t jfd}jjt|}|jt|j|jjjj}t j||g}|jj S)Nrfc822.messagerAc<jjddSrGrzrRsr4rHz.IMAP4ServerTests.testFullAppend..login` r{r6c3Ktd5}jjd|dd}tj|dddy#1swYyxYww)NrbrA)\SEEN\DELETEDz%Tue, 17 Jun 2003 11:22:16 -0600 (MDT))openrr|r returnValuerr2infilerEs r4r|z/IMAP4ServerTests.testFullAppend..appendc s\fd# *w#{{11#+;   !!&) * * *s A6A AAA)r&sibpath__file__rrrrinlineCallbacksrrr7rr rr#r(_cbTestFullAppendrErHr|r)r^rr|s` @r4testFullAppendzIMAP4ServerTests.testFullAppend\ sh(89**?; D    *  *^^ ' 'e 5 f t7 **DOO< ]]_   R )}}T33V<>Cctjtdtjj dfd}t jfd}jjt|}|jt|j|jjjj}t j||g}|jj S)NrsPARTIAL/SUBTHINGc<jjddSrGrzrRsr4rHz1IMAP4ServerTests.testPartialAppend..login r{r6c 3^Ktd5}jjtjdt dt jjfzdjj|}tj|dddy#1swYyxYww)NrvsAPPENDz)PARTIAL/SUBTHING (\SEEN) "Right now" {%d}r1) ryr sendCommandrr8r)ospathgetsize_IMAP4Client__cbContinueAppendrrzr{s r4r|z2IMAP4ServerTests.testPartialAppend..append sfd# *w#{{66MM! &#&(ggoof&=%?@  BB "!!&)% * * *s B-BB! B-!B*&B-)r&r}r~rrrrrrrr7rr rr#r(_cbTestPartialAppendrs` @r4testPartialAppendz"IMAP4ServerTests.testPartialAppend sh(89**+=> D    *  **^^ ' 'e 5 f t7 **DOO< ]]_   R )}}T66??r6ctjjd}|jdt |j |jdgddf|j dddt |d5}|j|j|j ddjdddy#1swYyxYw)Nrrrws Right nowrrvrrs r4rz%IMAP4ServerTests._cbTestPartialAppend s  $ $ . ./A B C ,- 8*lA6 Aqr8JK &$  E1   QVVXr{{1~a'8'A'A'C D E E Es 5?B==Cctjjdfd}fd}fd}jj t |}|j t |j|j t |j|j jjjS)N root/subthingc<jjddSrGrzrRsr4rHz*IMAP4ServerTests._testCheck..login r{r6c:jjdS)NrrrRsr4rz+IMAP4ServerTests._testCheck..select s;;%%&67 7r6c8jjSr0)rrrRsr4rz*IMAP4ServerTests._testCheck..check ;;$$& &r6) rrrrrr7rr rr#)rErHrrrs` r4 _testCheckzIMAP4ServerTests._testCheck s**+;< D 8 ' NN & &uU| 4 uV}doo6 uU|T__5 t))4??;}}r6c"|jS)zf Trigger the L{imap.IMAP4Server._cbSelectWork} callback by selecting an mbox. )rrRs r4 test_checkzIMAP4ServerTests.test_check s   r6cdd}fd}jtd|j}|j|S)zr Trigger the L{imap.IMAP4Server._ebSelectWork} errback by failing when we select an mbox. c,tjd)Nencoding)rIllegalMailboxEncoding)rErr{s r4 failSelectz3IMAP4ServerTests.test_checkFail..failSelect s..z: :r6c~j}j|djjddy)NrrsSELECT failed: Server error)r~rBrr)rfailuresrEs r4 checkResponsez6IMAP4ServerTests.test_checkFail..checkResponse s7--/H   Xa[..33A68V Wr6rr)patchrrr)rErrrs` r4test_checkFailzIMAP4ServerTests.test_checkFail s;  ; X 7Hj1 OO }}]++r6c2t}gd|_tjj d|fd}fd}fd}j j t|}|jt|j|jt|j|jjjj}tj||gj j|S)N)s Message 1)r AnotherFlagNrs Message 2)rNr)s Message 3)rNrrWc<jjddSrGrzrRsr4rHz)IMAP4ServerTests.testClose..login r{r6c:jjdS)NsmailboxrrRsr4rz*IMAP4ServerTests.testClose..select ;;%%j1 1r6c8jjSr0)rrrRsr4rz)IMAP4ServerTests.testClose..close rr6)rVrrrrrrr7rr rr#rr( _cbTestClose)rErrHrrrr^s` r4 testClosezIMAP4ServerTests.testClose s O  **9a8 D 2 ' NN & &uU| 4 uV}doo6 uU|T__5 t))4??; ]]_""Ar7+778I8I1MMr6c|jt|jd|j|jdd|j|jy)Nrrr)rBrrrVrrErTrs r4rzIMAP4ServerTests._cbTestClose sC QZZ!, A(QR !r6ct}gd|_tjj d|fd}fd}fd}fd}d_j jt|}|jt|j|jt|j|j|j|jjjj}tj||g}|jj|S)NrrWc<jjddSrGrzrRsr4rHz+IMAP4ServerTests.testExpunge..login r{r6c:jjdS)NrWrrRsr4rz,IMAP4ServerTests.testExpunge..select s;;%%i0 0r6c8jjSr0)rrrRsr4rz-IMAP4ServerTests.testExpunge..expunge s;;&&( (r6cbjjjdu|_yr0)rTrr^rI)rIrEs r4expungedz.IMAP4ServerTests.testExpunge..expunged s'   T[[--5 6"DLr6)rVrrrrrIrrr7rr rr#rr(_cbTestExpunge) rErrHrrrr)r^rs ` r4 testExpungezIMAP4ServerTests.testExpunge s O  **9a8 D 1 ) # ^^ ' 'e 5 f t7 g8 $//2 **DOO< ]]_   R )}}T00!44r6c|jt|jd|j|jdd|j|jddgy)Nrrrr)rBrrrIrs r4rzIMAP4ServerTests._cbTestExpunge sK QZZ!, A(QR 1v.r6N)6rsrtrur*r3r<rDrLrJr_r\rdrmrrrrrrrrrrrrrrrr rrr%r+r*r8r?rGrJrYr]rhrprorrrrrrrrrrrr1r6r4rrys IG. L M04666 6,!6F @4<6M,"4  #2J  @2= &%N.*6*.="@ &*P& 0 4S.P=6E"@HE$!,"N2" 5@/r6rceZdZdZdZdZdZdZdZdZ dZ d Z d Z d Z d Zd ZdZdZdZdZdZdZdZdZdZdZdZdZdZdZdZdZdZ dZ!d Z"d!Z#d"Z$d#Z%d$Z&d%Z'd&Z(d'Z)d(Z*y))*IMAP4ServerParsingTestsz6 Test L{imap4.IMAP4Server}'s command parsing. ct|_tj|_|jj |j|jj yr0)rrrrrmakeConnectionclearrRs r4rzIMAP4ServerParsingTests.setUp sB(*'')  ""4>>2 r6c|jjtjt j yr0rconnectionLostr$rrConnectionDonerRs r4rz IMAP4ServerParsingTests.tearDown& & ""7??53G3G3I#JKr6cGddtfd}d|j_||j_|jj d|j |j y)zO L{imap4.IMAP4Server} logs exceptions raised by parse methods. ceZdZdZy)SIMAP4ServerParsingTests.test_parseMethodExceptionLogged..UnhandledException1 An unhandled exception. Nrr1r6r4UnhandledExceptionr. rsr6rcr0r1)rrs r4raisesValueErrorzQIMAP4ServerParsingTests.test_parseMethodExceptionLogged..raisesValueError3 s $ $r6commandinvalidN)rr parseState parse_commandrrVr~)rErrs @r4test_parseMethodExceptionLoggedz7IMAP4ServerParsingTests.test_parseMethodExceptionLogged) sX     %"+ $4 !   , ../ABCr6c|jjd|j|jj d|jj t jtjdy)z L{imap4.IMAP4Server.parse_command} sends a C{BAD} response to a line that includes a tag but no command. 001s001 BAD Missing command DoneN) rrrBrrrr$rrrrRs r4test_missingCommandz+IMAP4ServerParsingTests.test_missingCommand= s] !!&) --/1OP "" OOE008 9 r6c|jjd|j|jj dy)zf L{imap4.IMAP4Server.parse_command} sends a C{BAD} response to an empty line. r6s* BAD Null command N)rrrBrrrRs r4test_emptyLinez&IMAP4ServerParsingTests.test_emptyLineJ s4 !!#& --/1JKr6cfd}||j_|jjdj|dg|j |j j dj||gy)aV Assert that the given exception results in the expected response. @param exception: The exception to raise. @type exception: L{Exception} @param tag: The IMAP tag. @type: L{bytes} @param expectedResponse: The expected bad response. @type expectedResponse: L{bytes} cr0r1)tagcmdrest exceptions r4raiseszDIMAP4ServerParsingTests.assertParseExceptionResponse..raisesc Or6rrN)rdispatchCommandrrrBrrrErrexpectedResponsers ` r4assertParseExceptionResponsez4IMAP4ServerParsingTests.assertParseExceptionResponseS sb  '- # !!$))S*,=">? --/CAQ;R1STr6cP|jtjdddy)zt When a parsing method raises L{IllegalClientResponse}, the server sends a C{BAD} response. client responser%BAD Illegal syntax: client response N)rrIllegalClientResponserRs r4'test_parsingRaisesIllegalClientResponsez?IMAP4ServerParsingTests.test_parsingRaisesIllegalClientResponsel s' ))  ' '(9 :  6 r6cP|jtjdddy)zn When a parsing method raises L{IllegalOperation}, the server sends a C{NO} response. operationr!NO Illegal operation: operation N)rrIllegalOperationrRs r4*test_parsingRaisesIllegalOperationResponsezBIMAP4ServerParsingTests.test_parsingRaisesIllegalOperationResponsew s& ))  " "; /  2 r6cP|jtjdddy)zt When a parsing method raises L{IllegalMailboxEncoding}, the server sends a C{NO} response. rr#NO Illegal mailbox name: encoding N)rrrrRs r4(test_parsingRaisesIllegalMailboxEncodingz@IMAP4ServerParsingTests.test_parsingRaisesIllegalMailboxEncoding s& ))  ( ( 4  4 r6c|jjd|j|jj dy)zi L{imap4.IMAP4Server} responds to an unsupported command with a C{BAD} response. s001 HULLABALOOs001 BAD Unsupported command N)rrrBrrrRs r4test_unsupportedCommandz/IMAP4ServerParsingTests.test_unsupportedCommand s5   !23 --/1STr6c|jjd|j|jj dt dj dzdzy)z~ L{imap4.IMAP4Server} responds with a C{BAD} response to a command with more arguments than expected. s001 LOGIN A B Cs8001 BAD Illegal syntax: Too many arguments for command: Czutf-8rN)rrrBrrrrCrRs r4test_tooManyArgumentsForCommandz7IMAP4ServerParsingTests.test_tooManyArgumentsForCommand s[   !34  NN "7t*##G,- r6cdfd}|j|jjd|f|jjddz|j_|jj |dd|j|j j dj||gy)aR Assert that the given exception results in the expected response. @param exception: The exception to raise. @type exception: L{Exception} @param: The IMAP tag. @type: L{bytes} @param expectedResponse: The expected bad response. @type expectedResponse: L{bytes} cr0r1)serverInstancerrvrwrs r4rzFIMAP4ServerParsingTests.assertCommandExceptionResponse..raises rr6rarNLOGINs user passwdr)rBrrR unauth_LOGINrrrrrs ` r4assertCommandExceptionResponsez6IMAP4ServerParsingTests.assertCommandExceptionResponse s   **H5$*9t{{/G/G/K#K   ##C>B --/CAQ;R1STr6cP|jtjdddy)zm When a command raises L{IllegalClientResponse}, the server sends a C{BAD} response. rrrN)rrrrRs r4'test_commandRaisesIllegalClientResponsez?IMAP4ServerParsingTests.test_commandRaisesIllegalClientResponse s' ++  ' '(9 :  6 r6cP|jtjdddy)zg When a command raises L{IllegalOperation}, the server sends a C{NO} response. rrrN)rrrrRs r4*test_commandRaisesIllegalOperationResponsezBIMAP4ServerParsingTests.test_commandRaisesIllegalOperationResponse s& ++  " "; /  2 r6cP|jtjdddy)zm When a command raises L{IllegalMailboxEncoding}, the server sends a C{NO} response. rrrN)rrrrRs r4(test_commandRaisesIllegalMailboxEncodingz@IMAP4ServerParsingTests.test_commandRaisesIllegalMailboxEncoding s& ++  ( ( 4  4 r6cGddt}|j|ddd|j|j|y)z Wehn a command raises an unhandled exception, the server sends a C{BAD} response and logs the exception. ceZdZdZy)XIMAP4ServerParsingTests.test_commandRaisesUnhandledException..UnhandledExceptionrNrr1r6r4rr rsr6r unhandledrsBAD Server error: unhandled N)rrrVr~)rErs r4$test_commandRaisesUnhandledExceptionzIMAP4ServerParsingTests.test_arg_astringUnmatchedLiteralBraces s' %55t{{7N7NPUVr6cn|jtj|jjdy)zc A non-integral string literal size raises L{imap4.IllegalClientResponse}. {[object Object]}Nr rRs r4"test_arg_astringInvalidLiteralSizez:IMAP4ServerParsingTests.test_arg_astringInvalidLiteralSize *   ' ')@)@BV r6cn|jtj|jjdy)z@ An empty atom raises L{IllegalClientResponse}. r6Nrrrrarg_atomrRs r4test_arg_atomEmptyLinez.IMAP4ServerParsingTests.test_arg_atomEmptyLine$ s& %55t{{7K7KSQr6cn|jtj|jjdy)zC A malformed atom raises L{IllegalClientResponse}. s not an atom NrrRs r4test_arg_atomMalformedAtomz2IMAP4ServerParsingTests.test_arg_atomMalformedAtom* s*   ' ')=)=?O r6cn|jtj|jjdy)zN An empty parenthesized list raises L{IllegalClientResponse}. r6Nrrrr arg_plistrRs r4test_arg_plistEmptyLinez/IMAP4ServerParsingTests.test_arg_plistEmptyLine2 s& %55t{{7L7LcRr6c|jtj|jjd|jtj|jjdy)ze A parenthesized with unmatched parentheses raises L{IllegalClientResponse}. s(foosfoo)NrrRs r4"test_arg_plistUnmatchedParenthesesz:IMAP4ServerParsingTests.test_arg_plistUnmatchedParentheses8 sH %55t{{7L7LgV %55t{{7L7LgVr6cn|jtj|jjdy)zH An empty file literal raises L{IllegalClientResponse}. r6Nrrrr arg_literalrRs r4test_arg_literalEmptyLinez1IMAP4ServerParsingTests.test_arg_literalEmptyLine@ s' %55t{{7N7NPSTr6c|jtj|jjd|jtj|jjdy)zZ A literal with unmatched braces raises L{IllegalClientResponse}. s{10s10}Nr"rRs r4test_arg_literalUnmatchedBracesz7IMAP4ServerParsingTests.test_arg_literalUnmatchedBracesF sJ %55t{{7N7NPVW %55t{{7N7NPVWr6cn|jtj|jjdy)z\ A non-integral literal size raises L{imap4.IllegalClientResponse}. rNr"rRs r4"test_arg_literalInvalidLiteralSizez:IMAP4ServerParsingTests.test_arg_literalInvalidLiteralSizeN rr6chd}|jj|\}}|j|dy)zH A sequence set returns the unparsed portion of a line. s1:* blah blah blahsblah blah blahN)r arg_seqsetrB)rEsequencer&rs r4test_arg_seqsetReturnsRestz2IMAP4ServerParsingTests.test_arg_seqsetReturnsRestW s2)++((24 01r6cn|jtj|jjdy)zL An invalid sequence raises L{imap4.IllegalClientResponse}. sx:yN)rrrrr*rRs r4test_arg_seqsetInvalidSequencez6IMAP4ServerParsingTests.test_arg_seqsetInvalidSequence_ s& %55t{{7M7MvVr6cd}|jj|\}}|j||g|j|y)zJ A single flag that is not contained in a list is parsed. sflagN)r arg_flaglistrBrT)rEflagrrs r4test_arg_flaglistOneFlagz0IMAP4ServerParsingTests.test_arg_flaglistOneFlage sA{{//5  $( r6cn|jtj|jjdy)zk A list of flags with unmatched parentheses raises L{imap4.IllegalClientResponse}. s(invalidNrrrrr0rRs r4&test_arg_flaglistMismatchedParentehsesz>IMAP4ServerParsingTests.test_arg_flaglistMismatchedParentehsesn s+   ' ' KK $ $  r6c|jtj|jjd|jtj|jjdy)zo A list of flags that contains a malformed flag raises L{imap4.IllegalClientResponse}. s (first )s(first second)Nr4rRs r4test_arg_flaglistMalformedFlagz6IMAP4ServerParsingTests.test_arg_flaglistMalformedFlagy sQ   ' ')A)A?    ' ')A)ACX r6cd}|jj|\}}|j||j||y)z A line that does not begin with an open parenthesis (C{(}) is parsed as L{None}, and the remainder is the whole line. snot (N)r opt_plistrrB)rErplist remainders r4$test_opt_plistMissingOpenParenthesiszrs r4"test_opt_datetimeMissingCloseQuotez:IMAP4ServerParsingTests.test_opt_datetimeMissingCloseQuote s, . %55t{{7O7OQUVr6crd}|jtj|jj|y)z A line that contains C{CHARSET} but no character set identifier raises L{imap4.IllegalClientResponse}. rN)rrrr opt_charsetrs r4!test_opt_charsetMissingIdentifierz9IMAP4ServerParsingTests.test_opt_charsetMissingIdentifier s,  %55t{{7N7NPTUr6cd}|jj|\}}|j|d|j|dy)z A line that ends with a C{CHARSET} identifier is parsed as that identifier, and the remainder is the empty string. s CHARSET UTF-8UTF-8r6NrrDrBrEr identifierr;s r4test_opt_charsetEndOfLinez1IMAP4ServerParsingTests.test_opt_charsetEndOfLine sB   $ 7 7 = I X. C(r6cd}|jj|\}}|j|d|j|dy)z A line that has additional data after a C{CHARSET} identifier is parsed as that identifier, and the remainder is that additional data. sCHARSET UTF-8 remainderrGs remainderNrHrIs r4test_opt_charsetWithRemainderz5IMAP4ServerParsingTests.test_opt_charsetWithRemainder sB * $ 7 7 = I X. L1r6N)+rsrtrur3rrrrrrrrrrrrrrrrrr rrrrrrr r$r&r(r,r.r2r5r7r<r@rBrErKrMr1r6r4rr s LD(  LU2      U U6      D&   W R  S WU X 2W     **WV) 2r6rcXeZdZdZdZdZdZdZdZdZ dZ d Z d Z d Z d Zd Zy)IMAP4ServerSearchTestszS Tests for the behavior of the search_* functions in L{imap4.IMAP4Server}. ctj|dg|_dg|_dg|_d|_t ddigddd d|_y) Nz 10-Dec-2009z 13-Dec-2009z 16-Dec-2009rrzMon, 13 Dec 2009 21:25:10 GMTz13 Dec 2009 00:00:00 GMTr()rr earlierQuery sameDateQuery laterQueryseqrrrRs r4rzIMAP4ServerSearchTests.setUp sXt$*O+_(/ 4 5  &     r6c,|j|jj|j|j|j |j |jj|j|j|j y)z L{imap4.IMAP4Server.search_SENTBEFORE} returns True if the message date is earlier than the query date. N)rTrsearch_SENTBEFORErRrUrrVrTrRs r4test_searchSentBeforez,IMAP4ServerSearchTests.test_searchSentBefore sf  KK ) )$*;*;TXXtxx P   KK ) )$//488TXX N r6c|j|jjdg|j|jd|j |jjdg|j|jd|j |jjdg|j|jdy)zq L{imap4.IMAP4Server.search_UID} returns True if the message UID is in the search range. r)rrQs2:*rN)rTr search_UIDrUrrVrRs r4test_searchWildcardz*IMAP4ServerSearchTests.test_searchWildcard s  KK " "F8TXXtxx K   ..x488YWX  ..vtxx9UVr6c|j|jjdg|j|jdy)z L{imap4.IMAP4Server.search_UID} should return True if there is a wildcard, because a wildcard means "highest UID in the mailbox". s1235:*)rQrN)rVrrZrUrrRs r4test_searchWildcardHighz.IMAP4ServerSearchTests.test_searchWildcardHigh s2  KK " "I;$((I N r6chtjd}|jt|gdy)| L{imap4.IMAP4Server.search_SENTON} returns True if the message date is the same as the query date. r>r$N)rrrBr)rEmsgsets r4test_reversedSearchTermsz/IMAP4ServerSearchTests.test_reversedSearchTerms s( ""6* fy1r6c|j|jj|j|j|j |j |jj|j|j|j |j|jj|j|j|j y)r_N) rTr search_SENTONrRrUrrVrSrTrRs r4test_searchSentOnz(IMAP4ServerSearchTests.test_searchSentOn s  KK % %d&7&7488 L   KK % %d&8&8$((DHH M  224??DHHdhhWXr6c,|j|jj|j|j|j |j |jj|j|j|j y)z~ L{imap4.IMAP4Server.search_SENTSINCE} returns True if the message date is later than the query date. N)rVrsearch_SENTSINCErRrUrrTrTrRs r4test_searchSentSincez+IMAP4ServerSearchTests.test_searchSentSince sf  KK ( ():):DHHdhh O   KK ( ($((DHH M r6cD|j|jjdg|jzdgz|jz|j |j d|j|jjdg|jzdgz|jz|j |j d|j|jjdg|jzdgz|jz|j |j dy)z L{imap4.IMAP4Server.search_OR} returns true if either of the two expressions supplied to it returns true and returns false if neither does. SENTSINCEr SENTONN)rVr search_ORrRrTrUrrTrRs r4 test_searchOrz$IMAP4ServerSearchTests.test_searchOr s  KK ! !  1 11[MADOOS     KK ! ! /;-?$BSBSS     KK ! ! T__, } XU Xr6rOc"eZdZdZdZddZdZy)rz A L{IRealm} for tests. @cvar theAccount: An C{Account} instance. Tests can set this to ensure predictable account retrieval. Nc6r fd_yfd_y)ab Create a realm for testing. @param accountHolder: (optional) An object whose C{theAccount} attribute will be returned instead of L{TestRealm.theAccount}. Attribute access occurs on every avatar request, so any modifications to C{accountHolder.theAccount} will be reflected here. cjSr0rrsr4r5z$TestRealm.__init__..| s }'?'?r6cjSr0r|rRsr4r5z$TestRealm.__init__..~ s tr6N) _getAccount)rErs``r4rzzTestRealm.__init__q s ?D 6D r6cFtj|jdfS)Ncyr0r1r1r6r4r5z)TestRealm.requestAvatar.. rhr6)rIAccountr~)rEavatarIdmindrs r4rlzTestRealm.requestAvatar s~~t//1<??r6r0)rsrtrur3rrzrlr1r6r4rrf sJ 7@r6rc(eZdZeefZddiZdZdZy) TestCheckerrsecretc|j|jvr[tj|j|j|jj |j |jSyr0)usernamerr maybeDeferred checkPasswordr_cbCheck)rE credentialss r4requestAvatarIdzTestChecker.requestAvatarId s\   4:: -&&))4::k6J6J+Kk$--)=)=> ? .r6c|r|Str0r)rEr2rs r4rzTestChecker._cbCheck s O!!r6N) rsrtrurrcredentialInterfacesrrrr1r6r4rr s"35FG ) $E? "r6rceZdZdZdZdZdZdZdZdZ dZ d Z d Z d Z d Zd ZdZdZdZdZdZdZdZy)AuthenticatorTestsc.tj|t}td|_t ||_|j jt|j |j_d|_ |j|_ y)Nrr) rrrrrrrrrr authenticatedrQ)rErs r4rzAuthenticatorTests.setUp sht$ ";/Um  ##KM2![[ '' r6c tttGdd}|}tt|t j d|i}|j |_t}|j||j|jtjd|jd|j|j|j!d|jt#j$|j'|j|j|j!t#j$ddz|j)|jd y ) z L{imap4.IMAP4Server} accepts a L{dict} mapping challenge type names to L{twisted.mail.interfaces.IChallengeResponse} providers. c$eZdZdZdZdZdZy)>AuthenticatorTests.test_customChallengers..SPECIALAuthcy)NSPECIALr1rRs r4 getChallengezKAuthenticatorTests.test_customChallengers..SPECIALAuth.getChallenge !r6cB|jdd\|_|_yrs)splitrpasswordrEresponses r4 setResponsezJAuthenticatorTests.test_customChallengers..SPECIALAuth.setResponse s/7~~dA/F, t}r6cyNFr1rRs r4moreChallengeszMAuthenticatorTests.test_customChallengers..SPECIALAuth.moreChallenges sr6c&|j|_yr0)r)rErs r4rzLAuthenticatorTests.test_customChallengers..SPECIALAuth.checkPassword s $  r6N)rsrtrurrrrr1r6r4 SPECIALAuthr s " G  .r6rrConnection done.s AUTH=SPECIALs001 AUTHENTICATE SPECIAL susername passwordrs"001 OK Authentication successful N)r r rr rrrrr addCleanuprrrrrr dataReceivedbase64 b64encoderrB)rErspecialrrs r4test_customChallengersz)AuthenticatorTests.test_customChallengers s& '): ; . . < .-'1""J #<=  #% i( --u/C/CDV/WX oy'89;< f&&w';';'=> @QRF,,-ABWLM *,STr6cdtj}|j|_t}|j ||j |j tjd|j|jd|j|jdy)z_ An unsupported C{AUTHENTICATE} method results in a negative response. rs001 AUTHENTICATE UNKNOWN s(001 NO AUTHENTICATE method unsupported N) rrrrrrrrrrrrBr)rErrs r4test_unsupportedMethodz)AuthenticatorTests.test_unsupportedMethod s ""$  #% i( --u/C/CDV/WX;<  OO L r6ctjjjd<tjd}j j |dj_fd}jjt|}|jjd|jjjt!j"|j%gS)zv An L{imap4.IMAP4Server} that is missing a L{Portal} responds negatively to an authentication rrNc:jjdSNrr authenticaterRsr4rOz3AuthenticatorTests.test_missingPortal..auth ;;++I6 6r6s Temporary authentication failure)rLOGINCredentialsrr2LOGINAuthenticatorrregisterAuthenticatorrrrr7r'rrrr rr(r#)rEcAuthrOrs` r4test_missingPortalz%AuthenticatorTests.test_missingPortal s -2,B,B )((5 ))%0!  7 NN & &uT{ 3  + +-P  t))4??;""At}}#788r6c~ttGdd}ttGdd}|}tt||jj d<j j|fd}jjt|}|jjdt|jzjd|j!j"j$t'j(|j+gS) z When a challenger's L{getChallenge} method raises any exception, a C{NO} response is sent. c"eZdZdZdZdZdZy)RAuthenticatorTests.test_challengerRaisesException..ValueErrorAuthChallengesA challenge failurec,t|jr0)rrrRs r4rz_AuthenticatorTests.test_challengerRaisesException..ValueErrorAuthChallenge.getChallenges ..r6cyzw Never called. @param response: See L{IChallengeResponse.setResponse} Nr1rs r4rz^AuthenticatorTests.test_challengerRaisesException..ValueErrorAuthChallenge.setResponserhr6cyz/ Never called. Nr1rRs r4rzaAuthenticatorTests.test_challengerRaisesException..ValueErrorAuthChallenge.moreChallenges rhr6Nrsrtrurrrrr1r6r4ValueErrorAuthChallenger s,G /  r6rceZdZdZdZy)RAuthenticatorTests.test_challengerRaisesException..ValueErrorAuthenticatorcy)NERRORr1rRs r4getNamezZAuthenticatorTests.test_challengerRaisesException..ValueErrorAuthenticator.getNamesr6cy)NsIGNOREDr1)rEsecretchals r4challengeResponsezdAuthenticatorTests.test_challengerRaisesException..ValueErrorAuthenticator.challengeResponserr6N)rsrtrurrr1r6r4ValueErrorAuthenticatorrs   "r6rrc:jjdSrrrRsr4rOz?AuthenticatorTests.test_challengerRaisesException..authrr6zServer error: r)r r r!r rr2rrrrr7r'rrrrCrrr rr(r#)rErrbadrOrs` r4test_challengerRaisesExceptionz1AuthenticatorTests.test_challengerRaisesException s  ' (   ) $ * + " " , "&''-,C ) ))*A*CD 7 NN & &uT{ 3  + + $;$C$C D D L LW U  t))4??;""At}}#788r6c$ttGdd}|}tt|tj}|j |_||j d<t}|j||j|jtjd|jd|j|j|j!d|jt#j$|j'|j|j|j!d|j)|jdj+d |j,d gy ) z A client that responds with a challenge that cannot be decoded as Base 64 receives an L{IllegalClientResponse}. c"eZdZdZdZdZdZy)EAuthenticatorTests.test_authNotBase64..NotBase64AuthChallengesMalformed Response - not base64cy)Ns SomeChallenger1rRs r4rzRAuthenticatorTests.test_authNotBase64..NotBase64AuthChallenge.getChallenge5s'r6cyrr1rs r4rzQAuthenticatorTests.test_authNotBase64..NotBase64AuthChallenge.setResponse8rhr6cyrr1rRs r4rzTAuthenticatorTests.test_authNotBase64..NotBase64AuthChallenge.moreChallenges?rhr6Nrr1r6r4NotBase64AuthChallenger1s8G (  r6rs NOTBASE64rsAUTH=NOTBASE64s001 AUTHENTICATE NOTBASE64 s Not base64 r6s001 NO Authentication failed: rN)r r r rrrr2rrrrrrrrrrrrrrBrr)rEr notBase64rrs r4test_authNotBase64z%AuthenticatorTests.test_authNotBase64+s8 ' (   ) $+, '3""$  +A<(#% i( --u/C/CDV/WX '):;=> f&&y'='='?@)//BST23  OO  HH79J9JGT U r6cFt}t|}|j_tj xjj d<}tt|t jd}jj|fd}jjt|}|jj d|j#j$j&t)j*j-|g}|S)z A challenger that causes the login to fail L{UnhandledCredentials} results in an C{NO} response. @return: A L{Deferred} that fires when the authorization has failed. rrc:jjdSrrrRsr4rOz:AuthenticatorTests.test_unhandledCredentials..authsrr6s+Authentication failed: server misconfigured)rrrrrrr2r r rrrrrr7r'rrrr rr(r#)rErr loginCredrrOr)rs` r4test_unhandledCredentialsz,AuthenticatorTests.test_unhandledCredentials^s $ 8=8N8NN )I& 2((5 ))%0 7^^ ' 'd 4  + + :  **DOO<   " 5 6r6c Gddt G fdd}t}t|}|j||j_t jxjjd<}tt|t jd}jj|fd} fd}jjt!|}|j#j$d |jt!||j'j(j*t-j.j1|g} | S) z If the portal raises an exception other than L{UnauthorizedLogin} or L{UnhandledCredentials}, the server responds with a C{BAD} response and the exception is logged. ceZdZdZy)KAuthenticatorTests.test_unexpectedLoginFailure..UnexpectedExceptionrqNrr1r6r4rrrrsr6rrc$eZdZdZeefZfdZy)FAuthenticatorTests.test_unexpectedLoginFailure..FailingCheckerzz A credentials checker whose L{requestAvatarId} method raises L{UnexpectedException}. cd)NzUnexpected error.r1)rErrrs r4rzVAuthenticatorTests.test_unexpectedLoginFailure..FailingChecker.requestAvatarIds)*=>>r6N)rsrtrur3rrrr)rrsr4FailingCheckerrs  %<=N#O  ?r6rrrc:jjdSrrrRsr4rOz.authrr6cFjjyr0r})rrrEsr4assertUnexpectedExceptionLoggedzWAuthenticatorTests.test_unexpectedLoginFailure..assertUnexpectedExceptionLoggeds OOD223FG Hr6s'Server error: login failed unexpectedly)rrrrrrrrr2r r rrrrrr7r'rrrr rr(r#) rErrrrrrOrr)rrrs ` @r4test_unexpectedLoginFailurez.AuthenticatorTests.test_unexpectedLoginFailures )  ? ? ~/0# 8=8N8NN )I& 2((5 ))%0 7 I^^ ' 'd 4  + +-W  u<=> **DOO<   " 5 6r6ctjjd<tjd}j j |fd}fd}jjt|}|jt|j|jjjj}tj||g}|jj S)Nr,rc:jjdSrrrRsr4rOz,AuthenticatorTests.testCramMD5..authrr6cd_yrsrrRsr4authedz.AuthenticatorTests.testCramMD5..authed !"D r6)rrr2rCramMD5ClientAuthenticatorrrrrr7rr rr#rr(_cbTestCramMD5)rErrOrr)r^rs` r4 testCramMD5zAuthenticatorTests.testCramMD5s/A  ,00= ))%0 7 #^^ ' 'd 4 f t7 **DOO< ]]_   R )}}T0011r6c|j|jd|j|jj|jyrsrBrrrQrSs r4rz!AuthenticatorTests._cbTestCramMD56 ++Q/ ,,dll;r6ctjjd<tjd}j j |fd}fd}fd}jjt|}|jt|t||jjjtjj|g}|jj S)Nr,rc:jjdSNsnot the secretrrRsr4misauthz5AuthenticatorTests.testFailedCramMD5..misauth;;++,=> >r6cd_yrsrrRsr4rz4AuthenticatorTests.testFailedCramMD5..authedrr6cd_yNrrRsr4 misauthedz7AuthenticatorTests.testFailedCramMD5..misauthed !#D r6)rrr2rrrrrrr7rrr rr(r#_cbTestFailedCramMD5rErrrrr)rs` r4testFailedCramMD5z$AuthenticatorTests.testFailedCramMD5s/A  ,00= ))%0 ? # $^^ ' 'g 7 f uY'78 **DOO<   " 5 6}}T6677r6c|j|jd|j|jjdyrrrSs r4rz'AuthenticatorTests._cbTestFailedCramMD52 ++R0 ,,d3r6cHtjxjjd<}t t |tj d}jj|fd}fd}jjt|}|jt|j|jjjtj j#|g}|jj$S)Nrrc:jjdSrrrRsr4rOz*AuthenticatorTests.testLOGIN..authrr6cd_yrsrrRsr4rz,AuthenticatorTests.testLOGIN..authedrr6)rrrr2r r rrrrrr7rr rrr(r# _cbTestLOGIN)rErrrOrr)rs` r4 testLOGINzAuthenticatorTests.testLOGIN8=8N8NN )I& 2((5 ))%0 7 #^^ ' 'd 4 f t7 **DOO<   " 5 6}}T..//r6c|j|jd|j|jj|jyrsrrSs r4rzAuthenticatorTests._cbTestLOGINrr6c,tjjjd<tjd}j j |fd}fd}fd}jjt|}|jt|t||jjjtjj|g}|jj S)Nrrc:jjdSrrrRsr4rz3AuthenticatorTests.testFailedLOGIN..misauthrr6cd_yrsrrRsr4rz2AuthenticatorTests.testFailedLOGIN..authedrr6cd_yrrrRsr4rz5AuthenticatorTests.testFailedLOGIN..misauthedrr6)rrrr2rrrrrr7rrr rr(r#_cbTestFailedLOGINrs` r4testFailedLOGINz"AuthenticatorTests.testFailedLOGIN,1,B,B )((5 ))%0 ? # $^^ ' 'g 7 f uY'78 **DOO<   " 5 6}}T4455r6c|j|jd|j|jjdyrrrSs r4rz%AuthenticatorTests._cbTestFailedLOGIN rr6cHtjxjjd<}t t |tj d}jj|fd}fd}jjt|}|jt|j|jjjtj j#|g}|jj$S)Nrrc:jjdSrrrRsr4rOz*AuthenticatorTests.testPLAIN..authrr6cd_yrsrrRsr4rz,AuthenticatorTests.testPLAIN..authedrr6)rPLAINCredentialsrr2r r PLAINAuthenticatorrrrrr7rr rrr(r# _cbTestPLAIN)rE plainCredrrOrr)rs` r4 testPLAINzAuthenticatorTests.testPLAINr r6c|j|jd|j|jj|jyrsrrSs r4rzAuthenticatorTests._cbTestPLAIN#rr6c,tjjjd<tjd}j j |fd}fd}fd}jjt|}|jt|t||jjjtjj|g}|jj S)Nrrc:jjdSrrrRsr4rz3AuthenticatorTests.testFailedPLAIN..misauth,rr6cd_yrsrrRsr4rz2AuthenticatorTests.testFailedPLAIN..authed/rr6cd_yrrrRsr4rz5AuthenticatorTests.testFailedPLAIN..misauthed2rr6)rrrr2rrrrrr7rrr rr(r#_cbTestFailedPLAINrs` r4testFailedPLAINz"AuthenticatorTests.testFailedPLAIN'rr6c|j|jd|j|jjdyrrrSs r4r!z%AuthenticatorTests._cbTestFailedPLAIN;rr6N)rsrtrurrrrrrrrrrrrr rrrrrr"r!r1r6r4rr sl ()UV &9.29h1 fB0d2$<8(40(<6(40(<6(4r6rc"eZdZdZdZdZdZy)SASLPLAINTestsz Tests for I{SASL PLAIN} authentication, as implemented by L{imap4.PLAINAuthenticator} and L{imap4.PLAINCredentials}. @see: U{http://www.faqs.org/rfcs/rfc2595.html} @see: U{http://www.faqs.org/rfcs/rfc4616.html} cd}d}d}tj|}|j||}|j|d|zdz|zy)z L{PLAINAuthenticator.challengeResponse} returns challenge strings of the form:: NULNUL rrs challengeN)rrrrB)rErrrrrs r4#test_authenticatorChallengeResponsez2SASLPLAINTests.test_authenticatorChallengeResponseIsT((2**648 58#3e#;f#DEr6ctj}|jd|j|jd|j|j dy)z L{PLAINCredentials.setResponse} parses challenge strings of the form:: NULNUL stestusersecretrrN)rrrrBrrrEcreds r4test_credentialsSetResponsez*SASLPLAINTests.test_credentialsSetResponseWsI%%' ./  4  2r6c.tj}|jtj|jd|jtj|jd|jtj|jdy)z L{PLAINCredentials.setResponse} raises L{imap4.IllegalClientResponse} when passed a string not of the expected form. shellos helloworldshelloworldZoom!N)rrrrrr*s r4test_credentialsInvalidResponsez.SASLPLAINTests.test_credentialsInvalidResponsecsu %%' %55t7G7GR   ' ')9)9?    ' ')9)9;S r6N)rsrtrur3r(r,r.r1r6r4r%r%@s F 3  r6r%cTeZdZdZdZdZdZdZdZdZ dZ d Z d Z d Z d Zy )UnsolicitedResponseTestscFfd}fd}jjt|}|jt|jjt j j|g}|jjS)Nc<jjddSrGrzrRsr4rHz5UnsolicitedResponseTests.testReadWrite..logintr{r6c<jjdyrsrrrRsr4rz8UnsolicitedResponseTests.testReadWrite..loggedInw KK # #A &r6) rrr7r'r rr(r#_cbTestReadWriterErHrr)rs` r4 testReadWritez&UnsolicitedResponseTests.testReadWritessw D '^^ ' 'e 5 uX'224??C   " 5 6}}T2233r6cZ|jj}|j|ddggy)NrrrrrBrErTEs r4r6z)UnsolicitedResponseTests._cbTestReadWrite) KK   mQ/01r6cFfd}fd}jjt|}|jt|jjt j j|g}|jjS)Nc<jjddSrGrzrRsr4rHz4UnsolicitedResponseTests.testReadOnly..loginr{r6c<jjdyrr4rRsr4rz7UnsolicitedResponseTests.testReadOnly..loggedInr5r6) rrr7r'r rr(r#_cbTestReadOnlyr7s` r4 testReadOnlyz%UnsolicitedResponseTests.testReadOnlysw D '^^ ' 'e 5 uX'224??C   " 5 6}}T1122r6cZ|jj}|j|ddggy)Nrrr:r;s r4rAz(UnsolicitedResponseTests._cbTestReadOnlyr=r6c^ddggdgdfd}fd}jjt|}|jt|jjt j j|g}|jjS)N \Answeredr\Recent)rrrc<jjddSrGrzrRsr4rHz6UnsolicitedResponseTests.testFlagChange..loginr{r6c<jjyr0)rr)rrEsr4rz9UnsolicitedResponseTests.testFlagChange..loggedIns KK $ $U +r6) rrr7r'r rr(r#_cbTestFlagChange)rErHrr)rrs` @r4testFlagChangez'UnsolicitedResponseTests.testFlagChanges!;/BZLI D ,^^ ' 'e 5 uX'224??C   " 5 6}}T33U;;r6c|jj}|jDcgc]}d|d|dig}}|jd|jd|j ||ycc}w)Nrrrc |dSrr1rps r4r5z.s QqTr6)keyc |dSrr1rMs r4r5z.s !A$r6)rritemsrrB)rErTrr<r\expects r4rIz*UnsolicitedResponseTests._cbTestFlagChangesm KK  :?++-HQ>AaD!A$<0HH >"  ' F#IsA7cFfd}fd}jjt|}|jt|jjt j j|g}|jjS)Nc<jjddSrGrzrRsr4rHz7UnsolicitedResponseTests.testNewMessages..loginr{r6c>jjddyNrrrrRsr4rz:UnsolicitedResponseTests.testNewMessages..loggedIns KK # #B -r6) rrr7r'r rr(r#_cbTestNewMessagesr7s` r4testNewMessagesz(UnsolicitedResponseTests.testNewMessagessw D .^^ ' 'e 5 uX'224??C   " 5 6}}T4455r6cZ|jj}|j|gdgy)N)rrNr:r;s r4rWz+UnsolicitedResponseTests._cbTestNewMessages% KK   678r6cFfd}fd}jjt|}|jt|jjt j j|g}|jjS)Nc<jjddSrGrzrRsr4rHz=UnsolicitedResponseTests.testNewRecentMessages..loginr{r6c>jjddyrUrVrRsr4rz@UnsolicitedResponseTests.testNewRecentMessages..loggedIns KK # #D" -r6) rrr7r'r rr(r#_cbTestNewRecentMessagesr7s` r4testNewRecentMessagesz.UnsolicitedResponseTests.testNewRecentMessagessw D .^^ ' 'e 5 uX'224??C   " 5 6}}T::;;r6cZ|jj}|j|gdgy)NrNrr:r;s r4r^z1UnsolicitedResponseTests._cbTestNewRecentMessagesrZr6cFfd}fd}jjt|}|jt|jjt j j|g}|jjS)Nc<jjddSrGrzrRsr4rHz@UnsolicitedResponseTests.testNewMessagesAndRecent..loginr{r6c>jjddy)Nr@rrVrRsr4rzCUnsolicitedResponseTests.testNewMessagesAndRecent..loggedIns KK # #B +r6) rrr7r'r rr(r#_cbTestNewMessagesAndRecentr7s` r4testNewMessagesAndRecentz1UnsolicitedResponseTests.testNewMessagesAndRecentsw D ,^^ ' 'e 5 uX'224??C   " 5 6}}T==>>r6c`|jj}|j|gdgdgy)N)rr@Nrar:r;s r4rez4UnsolicitedResponseTests._cbTestNewMessagesAndRecents( KK   68QRSr6N)rsrtrur8r6rBrArJrIrXrWr_r^rfrer1r6r4r0r0rs? 42 32 <$ 69 <9 ?Tr6r0c(eZdZdZdZdZdZdZy)ClientCapabilityTestszT Tests for issuance of the CAPABILITY command and handling of its response. ct|_tj|_|jj |j|jj dy)zS Create an L{imap4.IMAP4Client} connected to a L{StringTransport}. s* OK [IMAP4rev1] N)rrrrprotocolrrrRs r4rzClientCapabilityTests.setUpsG)*))+  $$T^^4 ""#:;r6cjjd}jjdjjdfd}|j||S)z A capability response consisting only of atoms without C{'='} in them should result in a dict mapping those atoms to L{None}. FuseCaches&* CAPABILITY IMAP4rev1 LOGINDISABLED 0001 OK Capability completed. c0j|dddy)N)r!s LOGINDISABLEDr% capabilitiesrEs r4gotCapabilitiesz?ClientCapabilityTests.test_simpleAtoms..gotCapabilitiess   \$RV+W Xr6rkrrrrEcapabilitiesResultrss` r4test_simpleAtomsz&ClientCapabilityTests.test_simpleAtomss_ "]]::E:J ""#NO ""#GH Y &&7!!r6cjjd}jjdjjdfd}|j||S)a A capability response consisting of atoms including C{'='} should have those atoms split on that byte and have capabilities in the same category aggregated into lists in the resulting dictionary. (n.b. - I made up the word "category atom"; the protocol has no notion of structure here, but rather allows each capability to define the semantics of its entry in the capability response in a freeform manner. If I had realized this earlier, the API for capabilities would look different. As it is, we can hope that no one defines any crazy semantics which are incompatible with this API, or try to figure out a better API when someone does. -exarkun) Frms.* CAPABILITY IMAP4rev1 AUTH=LOGIN AUTH=PLAIN roc4j|dddgdy)Nrr)r!r/r%rqs r4rszAClientCapabilityTests.test_categoryAtoms..gotCapabilitiess   TXxClientCapabilityTests.test_mixedAtoms..gotCapabilitiess&   #dF^fd^T r6rtrus` r4test_mixedAtomsz%ClientCapabilityTests.test_mixedAtomssd "]]::E:J "" A  ""#GH  &&7!!r6N)rsrtrur3rrwrzrr1r6r4riris< ""4"r6riceZdZdZdZdZy)StillSimplerClientzH An IMAP4 client which keeps track of unsolicited flag changes. cPtjj|i|_yr0)rrrzrrRs r4rzzStillSimplerClient.__init__-s ""4( r6c:|jj|yr0)rrrs r4rzStillSimplerClient.flagsChanged1s (#r6N)rsrtrur3rzrr1r6r4rr(s$r6rcBeZdZdZdZdZdZdZdZdZ dZ d Z y ) HandCraftedTestscttjjj dfdfdfd}j dd}j d|j||S)N* OK [IMAP4rev1]chjjjddy)Nrs0003 FETCH 1 (RFC822)rBrrg)rTrErs r4cbCheckTransportz>HandCraftedTests.testTrailingLiteral..cbCheckTransport<s,   !,,.r2( r6cjd}jdjd|j|S)Nrs6* 1 FETCH (RFC822 {10} 0123456789 RFC822.SIZE 10) s0003 OK FETCH ) fetchMessagerr)rTrrrs r4cbSelectz6HandCraftedTests.testTrailingLiteral..cbSelectBsAs#A NNO  NN/ 0 MM* +Hr6cnjd}jd|j|SNr0002 OK SELECT)rrr)rTrrrs r4cbLoginz5HandCraftedTests.testTrailingLiteral..cbLoginKs/!A NN, - MM( #Hr6blah0001 OK LOGIN )rrrrrrHrr)rErrrrrrs` @@@@r4testTrailingLiteralz$HandCraftedTests.testTrailingLiteral6ss#%     # *+     GGGW % +, gr6cx|jjjddt}|jj ||j |jj d|j|jd|j |jj d|j|jd|j |jj d|j|j|jj d|j|jd |j|jjd |jjtjd y ) z] String literals whose data is not immediately available are parsed. rrs01 LOGIN {8} s+ Ready for 8 octets of text stestuser {13} s+ Ready for 13 octets of text spasswords-test 01 OK LOGIN succeeded rOrN)rrrrrrrrBr assertNotrRrrrrErs r4test_fragmentedStringLiteralsz.HandCraftedTests.test_fragmentedStringLiteralsVs4 ##K1AB#%  ""9-   !45 *,OP   !56 *,PQ   - y()   . *,HI **F3 ""5#7#78J#KLr6c\ddi|jj_t}|jj ||j |jj d|j|jd|j |jj d|j|jd|j|jjd|jjtjdy) z3 Empty string literals are parsed. r6s01 LOGIN {0} s+ Ready for 0 octets of text s{0} rrOrN) rrrrrrrrBrrRrrrrs r4test_emptyStringLiteralz(HandCraftedTests.test_emptyStringLiteralps&)#J !#%  ""9-   !45 *,OP   , *,HI **F3 ""5#7#78J#KLr6c,ttjjdfd}fd}fd}fd}|j t |j t |j |S)a^ If unsolicited data is received along with solicited data in the response to a I{FETCH} command issued by L{IMAP4Client.fetchSpecific}, the unsolicited data is passed to the appropriate callback and not included in the result with which the L{Deferred} returned by L{IMAP4Client.fetchSpecific} fires. rcNjdd}jd|SNrrrHrrrs r4rHzRHandCraftedTests.test_unsolicitedResponseMixedWithSolicitedResponse..login%)A NN/ 0Hr6cLjd}jd|Srrrrs r4rzSHandCraftedTests.test_unsolicitedResponseMixedWithSolicitedResponse..select#!A NN, -Hr6cjdddg}jdjdjdjdjd jd jd jdjdjd |S) Nr HEADER.FIELDSSUBJECT headerType headerArgss1* 1 FETCH (BODY[HEADER.FIELDS ("SUBJECT")] {38} s$Subject: Suprise for your woman... r) s* 1 FETCH (FLAGS (\Seen)) s1* 2 FETCH (BODY[HEADER.FIELDS ("SUBJECT")] {75} sISubject: What you been doing. Order your meds here . ,. handcuff madsen 0003 OK FETCH completed  fetchSpecificrrs r4rzRHandCraftedTests.test_unsolicitedResponseMixedWithSolicitedResponse..fetchs/yk A NNQ R NND E NN7 # NN8 $ NN< = NNQ R NN^  NN7 # NN8 $ NN9 :Hr6cjjjddj|dddggdggdddggdggdjjd d giy) Nr,0003 FETCH 1:* BODY[HEADER.FIELDS (SUBJECT)]rrrz&Subject: Suprise for your woman... zKSubject: What you been doing. Order your meds here . ,. handcuff madsen rrr\SeenrBrrgrresrrErs r4rzQHandCraftedTests.test_unsolicitedResponseMixedWithSolicitedResponse..tests   !,,.r2?    #,yk:H#,yk:m (   QWWq8*o 6r6rrrrrr7rErHrrrrrs` @@r42test_unsolicitedResponseMixedWithSolicitedResponsezCHandCraftedTests.test_unsolicitedResponseMixedWithSolicitedResponsesv$%   # *+     $ 7: G [v ' [u & [   r6cNttjjj dfd}fd}fd}fd}|}|j t ||j t ||j ||S)zf Literals should be recognized even when they are not preceded by whitespace. rcNjdd}jd|Srrrrks r4rHzFHandCraftedTests.test_literalWithoutPrecedingWhitespace..login'w0A  ! !"6 7Hr6cLjd}jd|S)Ninboxrrrs r4rzGHandCraftedTests.test_literalWithoutPrecedingWhitespace..selects%)A  ! !"3 4Hr6cvjdddg}jdjd|S)Nrrrrs8* 1 FETCH (BODY[HEADER.FIELDS ({7} SUBJECT)] "Hello") rrrs r4rzFHandCraftedTests.test_literalWithoutPrecedingWhitespace..fetchsJ&&/yk'A  ! !O   ! !"@ AHr6cjjjddj|ddddggdggiy)NrrrrrrHellor)r2rErs r4rzEHandCraftedTests.test_literalWithoutPrecedingWhitespace..testsW   !,,.r2?    f &DgNOP r6rrrrrrr7)rErHrrrrrkrs` @@r4&test_literalWithoutPrecedingWhitespacez7HandCraftedTests.test_literalWithoutPrecedingWhitespaces $% $$& *12       G eFm$ eEl# dr6c$ttjjj dfd}fd}fd}|}|j t ||j t ||S)z If the server sends a literal length which cannot be parsed as an integer, L{IMAP4Client.lineReceived} should cause the protocol to be disconnected by raising L{imap4.IllegalServerResponse}. rcNjdd}jd|Srrrs r4rHz.login rr6cLjd}jd|Srrrs r4rz=HandCraftedTests.test_nonIntegerLiteralLength..selects%(A  ! !"3 4Hr6cjdddgjjjddj t j jdy)Nrrrrrrs* 1 FETCH {xyz} ...)rrBrrgrrIllegalServerResponser)rkrErsr4rz.fetchso  " "/yk #    !,,.r2?    ++%%) r6r)rErHrrrrkrs` @@r4test_nonIntegerLiteralLengthz-HandCraftedTests.test_nonIntegerLiteralLengthsu $% $$& *12      G eFm$ eEl#r6c(t}tj|jdfd}fd}fd}fd}|j t |j t |j |S)a Any unrequested flag information received along with other requested information in an untagged I{FETCH} received in response to a request issued with L{IMAP4Client.fetchSpecific} is passed to the C{flagsChanged} callback. rcNjdd}jd|Srrrs r4rHzLHandCraftedTests.test_flagsChangedInsideFetchSpecificResponse..login4rr6cLjd}jd|Srrrs r4rzMHandCraftedTests.test_flagsChangedInsideFetchSpecificResponse..select9rr6c jdddg}jdjdjdjdjd jd jd |S) Nrrrrs1* 1 FETCH (BODY[HEADER.FIELDS ("SUBJECT")] {22} sSubject: subject one s FLAGS (\Recent)) s?* 2 FETCH (FLAGS (\Seen) BODY[HEADER.FIELDS ("SUBJECT")] {22} sSubject: subject two rrrrs r4rzLHandCraftedTests.test_flagsChangedInsideFetchSpecificResponse..fetch>s? { A NNQ R NN6 7 NN4 5 NNU  NN6 7 NN8 $ NN9 :Hr6cj|dddggdggdddggdggdjjdgdgdy) NrrrzSubject: subject one zSubject: subject two rrFr)rBr)rrrEs r4rzKHandCraftedTests.test_flagsChangedInsideFetchSpecificResponse..testOsp   #,yk:6#,yk:6 (   QWW:,H:&F Gr6r)rErrHrrrrs` @r4,test_flagsChangedInsideFetchSpecificResponsez=HandCraftedTests.test_flagsChangedInsideFetchSpecificResponse(sw$%   # *+     " H0 G [v ' [u & [   r6c,ttjjdfd}fd}fd}fd}|j t |j t |j |S)a Any unrequested flag information received along with other requested information in an untagged I{FETCH} received in response to a request issued with L{IMAP4Client.fetchMessage} is passed to the C{flagsChanged} callback. rcNjdd}jd|Srrrs r4rHzKHandCraftedTests.test_flagsChangedInsideFetchMessageResponse..loginyrr6cLjd}jd|Srrrs r4rzLHandCraftedTests.test_flagsChangedInsideFetchMessageResponse..select~rr6cjd}jdjdjdjdjdjdjd|S) Nrs* 1 FETCH (RFC822 {24} sSubject: first subject s FLAGS (\Seen)) s.* 2 FETCH (FLAGS (\Recent \Seen) RFC822 {25} sSubject: second subject rr)rrrs r4rzKHandCraftedTests.test_flagsChangedInsideFetchMessageResponse..fetchspu%A NN8 9 NN8 9 NN2 3 NNP Q NN9 : NN8 $ NN9 :Hr6cjjjddj|ddiddidjjdgddgdy) Nrs0003 FETCH 1:* (RFC822)rzSubject: first subject zSubject: second subject rrrFrrs r4rzJHandCraftedTests.test_flagsChangedInsideFetchMessageResponse..testsx   !,,.r2*     ">? "?@    QWW8**h9O&P Qr6rrs` @@r4+test_flagsChangedInsideFetchMessageResponsezHandCraftedTests.test_authenticationChallengeDecodingExceptions 56 $$&%  * ' 00=&&u-  ! !( + 1e223=>''(C(CD Va( --a02KLr6N) rsrtrurrrrrrrrrr1r6r4rr5s9@M4M&J X,\)VC J6 pr6rc:eZdZUdZej Zded<dZy)PreauthIMAP4ClientMixinav Mixin for L{SynchronousTestCase} subclasses which provides a C{setUp} method which creates an L{IMAP4Client} connected to a L{StringTransport} and puts it into the I{authenticated} state. @ivar transport: A L{StringTransport} to which C{client} is connected. @ivar client: An L{IMAP4Client} which is connected to C{transport}. zType[imap4.IMAP4Client]clientProtocolct|_|j|_|jj |j|jj dy)zm Create an IMAP4Client connected to a fake transport and in the authenticated state. s* PREAUTH Hello unittest N)rrrrrrrRs r4rzPreauthIMAP4ClientMixin.setUpsG )*))+  ""4>>2   !@Ar6N) rsrtrur3rrrrrr1r6r4rrs  /4.?.?N+?Br6rcpeZdZdZdZdZdZdZdZdZ dZ d Z d Z d Z d Zd ZdZdZdZdZy)SelectionTestsMixinzl Mixin for test cases which defines tests which apply to both I{EXAMINE} and I{SELECT} support. ct|j|jd}|j|jj d|j zdz|S)z Issue either an I{EXAMINE} or I{SELECT} command (depending on C{self.method}), assert that the correct bytes are written to the transport, and return the L{Deferred} returned by whichever method was called. fooboxs0001 s foobox )rrmethodrBrrrrErs r4_examineOrSelectz$SelectionTestsMixin._examineOrSelectsT .GDKK -h 7  NN "Ht||$;n$L r6c|D] }|jj|dz"|jjd|jzdzy)z Deliver the given (unterminated) response lines to C{self.client} and then deliver a tagged SELECT or EXAMINE completion line to finish the SELECT or EXAMINE response. rs0001 OK [READ-ONLY] s completed N)rrr)rElinesrs r4 _responsezSelectionTestsMixin._responsesM  5D KK $ $TG^ 4 5   #dll 25F F r6c|j}|jd|j|j|dddy)a If the server response to a I{SELECT} or I{EXAMINE} command includes an I{EXISTS} response, the L{Deferred} return by L{IMAP4Client.select} or L{IMAP4Client.examine} fires with a C{dict} including the value associated with the C{'EXISTS'} key. s * 3 EXISTSFr)rrNrrrBsuccessResultOfrs r4 test_existszSelectionTestsMixin.test_exists?  ! ! # }% --a0RS2TUr6c|j}|jd|j|tjy)a If the server returns a non-integer EXISTS value in its response to a I{SELECT} or I{EXAMINE} command, the L{Deferred} returned by L{IMAP4Client.select} or L{IMAP4Client.examine} fails with L{IllegalServerResponse}. s * foo EXISTSNrrfailureResultOfrrrs r4test_nonIntegerExistsz)SelectionTestsMixin.test_nonIntegerExists 4  ! ! # ' Q ; ;    #E%%P r6c|j}|jd|j|tjy)a If the server returns a non-integer UIDVALIDITY value in its response to a I{SELECT} or I{EXAMINE} command, the L{Deferred} returned by L{IMAP4Client.select} or L{IMAP4Client.examine} fails with L{IllegalServerResponse}. s!* OK [UIDVALIDITY foo] UIDs validNrrs r4test_nonIntegerUIDVALIDITYz.SelectionTestsMixin.test_nonIntegerUIDVALIDITYMs5  ! ! # ;< Q ; ;  ! ! # w --a0<2GHr6N)rsrtrur3rrrrrrrrrrrrrrr r r1r6r4rrs\    V = V = V =   =   = " " IIr6rceZdZdZdZdZy)IMAP4ClientExamineTestsa Tests for the L{IMAP4Client.examine} method. An example of usage of the EXAMINE command from RFC 3501, section 6.3.2:: S: * 17 EXISTS S: * 2 RECENT S: * OK [UNSEEN 8] Message 8 is first unseen S: * OK [UIDVALIDITY 3857529045] UIDs valid S: * OK [UIDNEXT 4392] Predicted next UID S: * FLAGS (\Answered \Flagged \Deleted \Seen \Draft) S: * OK [PERMANENTFLAGS ()] No permanent flags permitted S: A932 OK [READ-ONLY] EXAMINE completed rsEXAMINENrsrtrur3rrr1r6r4r r s FGr6r ceZdZdZdZdZy)IMAP4ClientSelectTestsa Tests for the L{IMAP4Client.select} method. An example of usage of the SELECT command from RFC 3501, section 6.3.1:: C: A142 SELECT INBOX S: * 172 EXISTS S: * 1 RECENT S: * OK [UNSEEN 12] Message 12 is first unseen S: * OK [UIDVALIDITY 3857529045] UIDs valid S: * OK [UIDNEXT 4392] Predicted next UID S: * FLAGS (\Answered \Flagged \Deleted \Seen \Draft) S: * OK [PERMANENTFLAGS (\Deleted \Seen \*)] Limited S: A142 OK [READ-WRITE] SELECT completed rsSELECTNrr1r6r4rrs FGr6rc(eZdZdZdZdZdZdZy)IMAP4ClientExpungeTestsa Tests for the L{IMAP4Client.expunge} method. An example of usage of the EXPUNGE command from RFC 3501, section 6.4.3:: C: A202 EXPUNGE S: * 3 EXPUNGE S: * 3 EXPUNGE S: * 5 EXPUNGE S: * 8 EXPUNGE S: A202 OK EXPUNGE completed c|jj}|j|jj d|jj |S)Ns0001 EXPUNGE )rrrBrrrrs r4_expungez IMAP4ClientExpungeTests._expungesG KK   ! --/1DE r6c|D]*}|jjtd|d,|jjdy)Nz* z EXPUNGEs0001 OK EXPUNGE COMPLETED)rrr))rEsequenceNumbersnumbers r4rz!IMAP4ClientExpungeTests._responsesF% KF KK $ $]Rxx3H%I J K   !=>r6c|j}|jgd|j|j|gdy)z L{IMAP4Client.expunge} sends the I{EXPUNGE} command and returns a L{Deferred} which fires with a C{list} of message sequence numbers given by the server's response. )rrrrN)rrrBrrs r4 test_expungez$IMAP4ClientExpungeTests.test_expunges6 MMO |$ --a0,?r6c|j}|jgd|j|tjy)z If the server responds with a non-integer where a message sequence number is expected, the L{Deferred} returned by L{IMAP4Client.expunge} fails with L{IllegalServerResponse}. )rrrHrN)rrrrrrs r4test_nonIntegerExpungedz/IMAP4ClientExpungeTests.test_nonIntegerExpungeds2 MMO '( Q ; ;2J)KL L    !<=r6c|j}|jgd|j|j|gdy)z L{IMAP4Client.search} sends the I{SEARCH} command and returns a L{Deferred} which fires with a C{list} of message sequence numbers given by the server's response. )rrrN)r!rrBrrs r4 test_searchz"IMAP4ClientSearchTests.test_searchs6 LLN z" --a0*=r6c|j}|jgd|j|tjy)z If the server responds with a non-integer where a message sequence number is expected, the L{Deferred} returned by L{IMAP4Client.search} fails with L{IllegalServerResponse}. )rrHrN)r!rrrrrs r4test_nonIntegerFoundz+IMAP4ClientSearchTests.test_nonIntegerFound%s1 LLN ~& Q ; ; >=r6rc|eZdZdZdZdZdZdZdZdZ dZ d Z d Z d Z d Zd ZdZdZdZdZdZdZy)IMAP4ClientFetchTestszV Tests for the L{IMAP4Client.fetch} method. See RFC 3501, section 6.4.5. c|jjd}|j|jj d|jj d|jj d|jj d|jj d|jj d|j|j |dd idd idd idd id y)a L{IMAP4Client.fetchUID} sends the I{FETCH UID} command and returns a L{Deferred} which fires with a C{dict} mapping message sequence numbers to C{dict}s mapping C{'UID'} to that message's I{UID} in the server's response. 1:70001 FETCH 1:7 (UID) * 2 FETCH (UID 22)s* 3 FETCH (UID 23)* 4 FETCH (UID 24)s* 5 FETCH (UID 25)0001 OK FETCH completedr22232425rrrrN)rfetchUIDrBrrrrrs r4 test_fetchUIDz#IMAP4ClientFetchTests.test_fetchUID7s KK  ' --/1LM   !67   !67   !67   !67   !;<    # 5$-UDMudm T r6c:|jjd}|j|jj d|jj d|jj d|j |tjy)z If the server responds with a non-integer where a message sequence number is expected, the L{Deferred} returned by L{IMAP4Client.fetchUID} fails with L{IllegalServerResponse}. rs0001 FETCH 1 (UID) s* foo FETCH (UID 22)r1N rr7rBrrrrrrrs r4test_fetchUIDNonIntegerFoundz2IMAP4ClientFetchTests.test_fetchUIDNonIntegerFoundJsr KK  % --/1JK   !89   !;< Q ; ;|jjdd}|j|jj d|jj d|jj d|j |tjy)z If the server responds to a I{BODY[TEXT]} request with a I{FETCH} line which is truncated after the I{BODY[TEXT]} tokens, the L{Deferred} returned by L{IMAP4Client.fetchUID} fails with L{IllegalServerResponse}. rPrQrRrSs* 8 FETCH (BODY[TEXT])r1N rrrBrrrrrrrs r4(test_incompleteFetchSpecificTextResponsez>IMAP4ClientFetchTests.test_incompleteFetchSpecificTextResponsesw KK % %cf % = --/1OP   !:;   !;< Q ; ;}). It returns a L{Deferred} which fires with a C{dict} mapping message sequence numbers to C{list}s of corresponding message data given by the server's response. 9rQrDr)roffsetlengths0001 FETCH 9 BODY[TEXT]<17.3> s * 9 FETCH (BODY[TEXT]<17> "foo")r1rrz<17>rHNrFrs r4test_fetchSpecificPartialz/IMAP4ClientFetchTests.test_fetchSpecificPartials KK % %cfRPQ % R --/1UV   !DE   !;<    #a6F8VU*K)L%M r6c>|jjdd}|j|jj d|jj d|jj d|j |tjy)a If the server responds to a I{BODY[TEXT]} request with a I{FETCH} line which is truncated after the I{BODY[TEXT]} tokens, the L{Deferred} returned by L{IMAP4Client.fetchUID} fails with L{IllegalServerResponse}. rPrQrRrSs* 8 FETCH (BODY[TEXT]<17>)r1NrZrs r4+test_incompleteFetchSpecificPartialResponsezAIMAP4ClientFetchTests.test_incompleteFetchSpecificPartialResponsesw KK % %cf % = --/1OP   !>?   !;< Q ; ;} (as, for example, HTML bodies typically will), this is still interpreted as the body by L{IMAP4Client.fetchSpecific} (and particularly, not as a length indicator for a response to a request for a partial body). rCrDs&* 7 FETCH (BODY[] "test")r1rrztestNrFrs r4test_fetchSpecificHTMLz,IMAP4ClientFetchTests.test_fetchSpecificHTMLs KK % %c * --/1KL   !JK   !;<    #a627J*K)L%M r6c|jjd|}|j|jj d|j dzdz|jj d|j dzdz|jj d|j|j|d d |ggd ggiy ) a Assert that the provided C{BODY} section, when invoked with no arguments, produces an empty list, and that it returns a L{Deferred} which fires with a C{dict} mapping message sequence numbers to C{list}s of corresponding message data given by the server's response. @param section: The C{BODY} section to test: either C{'HEADER.FIELDS'} or C{'HEADER.FIELDS.NOT'} @type section: L{str} 10rRs0001 FETCH 10 BODY[rs ()] s* 10 FETCH (BODY[s ()] "")r1rrr(N)rrrBrrrCrr)rEsectionrs r4&assertFetchSpecificFieldsWithEmptyListz>'#: :[ H    !;< --a02'2PR8S7T2UVr6c&|jdy)az L{IMAP4Client.fetchSpecific}, when passed C{'HEADER.FIELDS'} for C{headerType} but no C{headerArgs}, sends the I{BODY[HEADER.FIELDS]} command with no arguments. It returns a L{Deferred} which fires with a C{dict} mapping message sequence numbers to C{list}s of corresponding message data given by the server's response. rNrjrRs r4,test_fetchSpecificHeaderFieldsWithoutHeaderszBIMAP4ClientFetchTests.test_fetchSpecificHeaderFieldsWithoutHeaderss 33ODr6c&|jdy)a L{IMAP4Client.fetchSpecific}, when passed C{'HEADER.FIELDS.NOT'} for C{headerType} but no C{headerArgs}, sends the I{BODY[HEADER.FIELDS.NOT]} command with no arguments. It returns a L{Deferred} which fires with a C{dict} mapping message sequence numbers to C{list}s of corresponding message data given by the server's response. zHEADER.FIELDS.NOTNrlrRs r4/test_fetchSpecificHeaderFieldsNotWithoutHeaderszEIMAP4ClientFetchTests.test_fetchSpecificHeaderFieldsNotWithoutHeaders's 334GHr6cN|jjdd}|j|jj d|jj d|jj d|j|j |dddgd ggiy ) a= L{IMAP4Client.fetchSpecific}, when passed C{'HEADER'} for C{headerType}, sends the I{BODY[HEADER]} command. It returns a L{Deferred} which fires with a C{dict} mapping message sequence numbers to C{list}s of corresponding message data given by the server's response. 11HEADERrRs0001 FETCH 11 BODY[HEADER] sJ* 11 FETCH (BODY[HEADER] "From: someone@localhost Subject: Some subject")r1r?rz.From: someone@localhost Subject: Some subjectNrFrs r4test_fetchSpecificHeaderz.IMAP4ClientFetchTests.test_fetchSpecificHeader2s KK % %dx % @ --/1RS    D    !;<    #! J  r6N)rsrtrur3r8r;r=rArGrJrNrTrXr[r]rbrdrfrjrmrorsr1r6r4r+r+0sg  & = = X T T   =   = W2 E I r6r+c\eZdZdZeZdZdZdZdZ dZ dZ dZ d Z d Zd Zd Zd Zy)IMAP4ClientStoreTestsa Tests for the L{IMAP4Client.setFlags}, L{IMAP4Client.addFlags}, and L{IMAP4Client.removeFlags} methods. An example of usage of the STORE command, in terms of which these three methods are implemented, from RFC 3501, section 6.4.6:: C: A003 STORE 2:4 +FLAGS (\Deleted) S: * 2 FETCH (FLAGS (\Deleted \Seen)) S: * 3 FETCH (FLAGS (\Deleted)) S: * 4 FETCH (FLAGS (\Deleted \Flagged \Seen)) S: A003 OK STORE completed cZt|j|ddd}|j|jj d|zdz|jj d|jj d|j|j |dd d d giiy ) am Test a non-silent flag modifying method. Call the method, assert that the correct bytes are sent, deliver a I{FETCH} response, and assert that the result of the Deferred returned by the method is correct. @param method: The name of the method to test. @param item: The data item which is expected to be specified. r?\ReadrF 0001 STORE 3  (\Read \Seen) s* 3 FETCH (FLAGS (\Read \Seen))0001 OK STORE completedrrrxrNrrrBrrrrrEritemrs r4 _flagsTestz IMAP4ClientStoreTests._flagsTest`s )GDKK (.BE J  NN "$4t$;>U$U    !EF   !;< --a01w8@T6U2VWr6ct|j|ddd}|j|jj d|zdz|jj d|j|j |iy)ag Test a silent flag modifying method. Call the method, assert that the correct bytes are sent, deliver an I{OK} response, and assert that the result of the Deferred returned by the method is correct. @param method: The name of the method to test. @param item: The data item which is expected to be specified. r?rwTryrzr{Nr|r}s r4_flagsSilentlyTestz(IMAP4ClientStoreTests._flagsSilentlyTestqs| )GDKK (.BD I  NN "$4t$;>U$U    !;< --a0"5r6ct|j|ddd}|j|jj d|zdz|jj d|jj d|j|j |i|j|jjdd d giy ) a Test unsolicited data received in response to a silent flag modifying method. Call the method, assert that the correct bytes are sent, deliver the unsolicited I{FETCH} response, and assert that the result of the Deferred returned by the method is correct. @param method: The name of the method to test. @param item: The data item which is expected to be specified. r?rwTryrzs* 2 FETCH (FLAGS (\Read \Seen))r{rrxrN)rrrBrrrrrr}s r4%_flagsSilentlyWithUnsolicitedDataTestz;IMAP4ClientStoreTests._flagsSilentlyWithUnsolicitedDataTests )GDKK (.BD I  NN "$4t$;>U$U    !EF   !;< --a0"5 **Q80D,EFr6c(|jddy)aQ When passed a C{False} value for the C{silent} parameter, L{IMAP4Client.setFlags} sends the I{STORE} command with a I{FLAGS} data item and returns a L{Deferred} which fires with a C{dict} mapping message sequence numbers to C{dict}s mapping C{'FLAGS'} to the new flags of those messages. setFlagsrNrrRs r4 test_setFlagsz#IMAP4ClientStoreTests.test_setFlagss  H-r6c(|jddy)z When passed a C{True} value for the C{silent} parameter, L{IMAP4Client.setFlags} sends the I{STORE} command with a I{FLAGS.SILENT} data item and returns a L{Deferred} which fires with an empty dictionary. r FLAGS.SILENTNrrRs r4test_setFlagsSilentlyz+IMAP4ClientStoreTests.test_setFlagsSilentlys  OIMAP4ClientStoreTests.test_setFlagsSilentlyWithUnsolicitedDatas 22:Or6c(|jddy)z{ L{IMAP4Client.addFlags} is like L{IMAP4Client.setFlags}, but sends I{+FLAGS} instead of I{FLAGS}. addFlagss+FLAGSNrrRs r4 test_addFlagsz#IMAP4ClientStoreTests.test_addFlagss  I.r6c(|jddy)z L{IMAP4Client.addFlags} with a C{True} value for C{silent} behaves like L{IMAP4Client.setFlags} with a C{True} value for C{silent}, but it sends I{+FLAGS.SILENT} instead of I{FLAGS.SILENT}. r +FLAGS.SILENTNrrRs r4test_addFlagsSilentlyz+IMAP4ClientStoreTests.test_addFlagsSilentlys  ,<=r6c(|jddy)z L{IMAP4Client.addFlags} behaves like L{IMAP4Client.setFlags} when used in silent mode and unsolicited data is received. rrNrrRs r4(test_addFlagsSilentlyWithUnsolicitedDataz>IMAP4ClientStoreTests.test_addFlagsSilentlyWithUnsolicitedDatas 22:?OPr6c(|jddy)z~ L{IMAP4Client.removeFlags} is like L{IMAP4Client.setFlags}, but sends I{-FLAGS} instead of I{FLAGS}. removeFlagss-FLAGSNrrRs r4test_removeFlagsz&IMAP4ClientStoreTests.test_removeFlagss  y1r6c(|jddy)z L{IMAP4Client.removeFlags} with a C{True} value for C{silent} behaves like L{IMAP4Client.setFlags} with a C{True} value for C{silent}, but it sends I{-FLAGS.SILENT} instead of I{FLAGS.SILENT}. r -FLAGS.SILENTNrrRs r4test_removeFlagsSilentlyz.IMAP4ClientStoreTests.test_removeFlagsSilentlys  /?@r6c(|jddy)z L{IMAP4Client.removeFlags} behaves like L{IMAP4Client.setFlags} when used in silent mode and unsolicited data is received. rrNrrRs r4+test_removeFlagsSilentlyWithUnsolicitedDatazAIMAP4ClientStoreTests.test_removeFlagsSilentlyWithUnsolicitedDatas 22=BRSr6N)rsrtrur3rrrrrrrrrrrrrrr1r6r4ruruOsP (NX"6 G&.=P/>Q2ATr6ruceZdZdZdZdZy)IMAP4ClientStatusTestsa_ Tests for the L{IMAP4Client.status} method. An example of usage of the STATUS command from RFC 3501, section 5.1.2:: C: A042 STATUS blurdybloop (UIDNEXT MESSAGES) S: * STATUS blurdybloop (MESSAGES 231 UIDNEXT 44292) S: A042 OK STATUS completed @see: U{https://tools.ietf.org/html/rfc3501#section-5.1.2} c|jt|jjdd}|j t |dt dhzy)z Only allow sending the C{STATUS} names defined in RFC 3501. @see: U{https://tools.ietf.org/html/rfc3501#section-5.1.2} rTz IMPOSSIBLE?!zUnknown names: N)rrrrbrBrr)rEexcs r4testUnknownNamez&IMAP4ClientStatusTests.testUnknownNamesN   KK       S#4t^>2 r6cyr0r1rEr\s r4rhzNewStoreTests.addListenerrr6cyr0r1rs r4rjzNewStoreTests.removeListenerrr6c,||f|_|jSr0) storeArgsr)rErrs r4rzNewStoreTests.storesr}}r6cjfd}fd}jjt|j|jjj j fd}t jjjd}|j||S)Nc|jjjjjSr0)functionrrsilentrrRsr4rz+NewStoreTests._storeWork..connecteds(== DKKR Rr6c|_yr0r2RrEs r4r2z(NewStoreTests._storeWork..result DKr6cjjjjjjyr0)rBr2rhr expectedArgsrTrEs r4rz'NewStoreTests._storeWork..checks5   T[[$-- 8   T^^T->-> ?r6Fnoisy rrr7rr'r r# loopbackTCPrr)rErr2rrs` r4 _storeWorkzNewStoreTests._storeWorks S  ""5#34@@HTT    *T__ % @  dkk G er6c|jj|_d|_gd|_d|_||_gdgdgdd|_dgdidgdidgdid|_tj}|jd|jd|jd|gdd fd d if|_ |jS) Nz1,5,9)z\Az\BCF)rrrrrrrrr)rrrrrrrrrhrrrrr)rErrs r4 testSetFlagszNewStoreTests.testSetFlagss ,,  (  """  ,-,-,-         !#6:UAJG  r6r) rsrtrur2rrrhrjrrrr1r6r4rrs* FI3  &!r6rcFeZdZdZdZdZdZdZdZdZ dZ d Z d Z y ) GetBodyStructureTestsz Tests for L{imap4.getBodyStructure}, a helper for constructing a list which directly corresponds to the wire information needed for a I{BODY} or I{BODYSTRUCTURE} response. c d}d}d}d}d}d}d}t|dz|zd z|zd z|||d d d |dd}tj|} |j||d|ddg|||t |g| y)z L{imap4.getBodyStructure} accepts a L{IMessagePart} provider and returns a list giving the basic fields for the I{BODY} response for that message. hello, worldimagejpegus-asciisome kind of id great justicemaximumrQ ; charset=; x=yr content-idcontent-descriptioncontent-transfer-encodingr1r6rNcharsetr\yrrgetBodyStructurerBr rErmajorminorrrJ descriptionrr structures r4test_singlePartz%GetBodyStructureTests.test_singleParts & %  % e 3l BW Lw V('2-5         **3/  GS#.D    r6ctiddddd}tj|}|dd\}}|jd||jd|tddiddddd}tj|}|dd\}}|jd||jd|tddiddddd} tj| } | dd\} } |jd| |jd| y) z L{imap4.getBodyStructure} returns L{None} for the major and minor MIME types of a L{IMessagePart} provider whose headers lack a C{Content-Type}, or have an empty value for it. r1r6rNrrr( )rrrassertIs) rEmissingmissingContentTypeStructure missingMajor missingMinorremptyContentTypeStructure emptyMajor emptyMinornewlinenewlineContentTypeStructure newlineMajor newlineMinors r4test_emptyContentTypez+GetBodyStructureTests.test_emptyContentTypes r2sCd;&+&<& J dJ' dJ'5r3S$O&+&<&  GS#.D =>   r6c d}d}d}td|dz|zidd|dd }tj|d }|j||d d d d t |d d d d g |y ) z For fields with no information contained in the message headers, L{imap4.getBodyStructure} fills in L{None} values in its result. rrrrrQr1r6rNTr-r)rEr r rrr s r4test_singlePartWithMissingz0GetBodyStructureTests.test_singlePartWithMissingOs|  US[50 12sD#t **3>   E4tT3t9dD$PT U  r6c d}d}d}d}d}d}d}t|dz|zd z|zd z|||d d d |dd}tj|} |j||d|ddg|||t |t |j g| y)z For a I{text/*} message, the number of lines in the message body are included after the common single-part basic fields. "hello, world how are you? goodbye rFrrrrrrQrrrr1r6rNrr\r)rrrrBrrgr s r4 test_textPartz#GetBodyStructureTests.test_textPart`s 8& %  % e 3l BW Lw V('2-5         **3/  GS#.D DOO%&   r6c @d}d}d}d}d}d}d}t|dz|zd z|zd zd d |||d dd|dd}tddidddd|g} tj| } |jdddddddtj|tj|dg | y)z For a I{message/rfc822} message, the common basic fields are followed by information about the contained message. r5rFrrrrrrQrrzAlice zBob )rrrrrrr1r(rNrmessage/rfc822r6rrrr)rrrrB getEnvelope) rErr r rrJr rr containerr s r4test_rfc822Messagez(GetBodyStructureTests.test_rfc822Messages 8& %  % e 3l BW Lw V3-('2-5         ! 0      E  **95  !!#&&&s+   r6c tddddddddd d }td d iddd dd }td didddd||g}|jtj|tj|dgtj|y )z For a I{multipart/*} message, L{imap4.getBodyStructure} returns a list containing the body structure information for each part of the message followed by an element giving the MIME subtype of the message. zimage/jpeg; x=yrrrrr1r6 hello worldrNrztext/plain; charset=us-ascii some stuffAzmultipart/related+relatedrrBrrrE oneSubPartanotherSubPartr:s r4test_multiPartz$GetBodyStructureTests.test_multiParts " 1/'6-6         & >        ! 3       (   &&z2&&~6   " "9 -  r6c <tddddddddd d }td d iddd dd }tddddddddd||g}|jtj|dtj|ddddgdddggddgtj|dy )a) When passed a I{multipart/*} message and C{True} for the C{extended} argument, L{imap4.getBodyStructure} includes extended structure information from the parts of the multipart message and extended structure information about the multipart message itself. simage/jpeg; x=yssome kind of ids great justicesmaximum) content-types content-idscontent-descriptionscontent-transfer-encodingr1r6r=rNrHstext/plain; charset=us-asciir>r?zmultipart/related; foo=baresSpainzattachment; name=monkeys)rr+r,r*r@Tr-rArHrIr/rmonkeysrBrCs r4test_multiPartExtendedz,GetBodyStructureTests.test_multiPartExtendeds"!31(8.8         &!@        ! <$($+'A        (   &&zDA&&~E 23   " "9t < r6N) rsrtrur3rrr#r1r3r6r;rFrLr1r6r4rrs9 & P*0 '/ b "& P6 p1 f9 r6rceZdZdZdZdZdZdZdZd-dZ dZ d-d Z d Z e je jd Z e je jd e je jed ZeeddZd-dZdZd-dZdZd-dZd-dZdZd-dZdZd-dZdZdZ d-dZ!dZ"d-dZ#d Z$d-d!Z%d"Z&d#Z'd$Z(d-d%Z)d&Z*d-d'Z+d(Z,d-d)Z-d*Z.d-d+Z/d,Z0y #e j$$rdZYwxYw). NewFetchTestsc dx|_|_d|_tj|_d|j _||j _tj|_ t|j|_ yr) rrr2rrrrRr^rrrrrrRs r4rzNewFetchTests.setUp0s_599!2 '') $  )"4>>2 r6cyr0r1rs r4rhzNewFetchTests.addListener:rr6cyr0r1rs r4rjzNewFetchTests.removeListener=rr6c ||_||_ttt t |j |j Sr0)rriterrrnrmsgObjsrs r4rzNewFetchTests.fetch@s6!)Cc$,,/0$,,?@@r6crctttjjD].\}}t |j j |d<0fd}jjfdj|jjjjtjjjd}|jfd|S)Nrc|_yr0rrs r4r2z(NewFetchTests._fetchWork..resultJrr6c<jjSr0rr)r&rErs r4r5z*NewFetchTests._fetchWork..NsdmmDMM37r6FrcPjjjSr0rBr2rh)r\rEs r4r5z*NewFetchTests._fetchWork..Ts 0 0dmm Lr6)rrnrrTrrrhrrrr'r r#rrr)rErrrr2rs`` r4 _fetchWorkzNewFetchTests._fetchWorkEs eC $56 E <3*-cjjl*; a ' <  "" 7 +f kk$*<*<=jj OO?   dkk G LMr6c fd_d_tidddddtidddddtidddddg_dd idd idd id _j d S)Nc:jj|Sr0rr7)rurEs r4r5z,NewFetchTests.testFetchUID..XsT[[%9%9!%<r6rCr1r6r4u'r1234599910101)rrrr)rrrrTrhr[rRs`r4 testFetchUIDzNewFetchTests.testFetchUIDWs<  Rc5$ 7 Rc3 5 Rc5$ 7  wu~w  q!!r6c |jj|_d|_t igdddddt igdddddg|_dgdidgdid|_|j|S) Nr_)FlagAFlagB\FlagCr61)rirgrhr4rrr)r fetchFlagsrrrrTrhr[rErs r4testFetchFlagszNewFetchTests.testFetchFlagsgsw ..  :CeT R :CeT R  6767  s##r6c$|jdSrs)rnrRs r4testFetchFlagsUIDzNewFetchTests.testFetchFlagsUIDts""1%%r6c |jj|_d|_t idddddt idddddt idddd dt idd dd dg|_d d id did did did|_|j|S)N13r1sFri, 02 Nov 2003 21:25:10 GMTr6iZsThu, 29 Dec 2013 11:31:52 ESTesMon, 10 Mar 1992 02:44:30 CSTsSat, 11 Jan 2000 14:40:24 PSTi/rz02-Nov-2003 21:25:10 +0000z29-Dec-2013 11:31:52 -0500z10-Mar-1992 02:44:30 -0600z11-Jan-2000 14:40:24 -0800)rrrr)rfetchInternalDaterrrrTrhr[rms r4testFetchInternalDatez#NewFetchTests.testFetchInternalDatews 55  R!A3t T R!A3T R R!A3T R R!A3T R    <= <= <= <=   s##r6c$|jdSrs)rvrRs r4testFetchInternalDateUIDz&NewFetchTests.testFetchInternalDateUIDs))!,,r6N es_AR.UTF8FTz'The es_AR.UTF8 locale is not installed.ctjtjd}tjtjd|jtjtj||j dS)zC The month name in the date is locale independent. Nryr)locale setlocaleLC_ALLrrv)rE currentLocales r4'test_fetchInternalDateLocaleIndependentz5NewFetchTests.test_fetchInternalDateLocaleIndependentsY ((=  5 ((&--G))!,,r6c |jj|_d|_t dddddddd d d dg|_d d ddgd ggd ggd ggdgddddg ii|_|j|S)N15z user@domainz resu@domainthursdayzit is a messagezid-id-id-yayaya)rrrrz message-idr1r6ixrr)NNrvdomain)NNresur)r fetchEnveloperrrrTrhr[rms r4testFetchEnvelopezNewFetchTests.testFetchEnvelopes 11  )'&0"3    " %34343434%    s##r6c$|jdSrs)rrRs r4testFetchEnvelopeUIDz"NewFetchTests.testFetchEnvelopeUIDs%%a((r6c|jj|_d|_t dddddddd d d d d ddg|_ddddgddddddddddggdd g ii|_|j|S)a[ L{IMAP4Client.fetchBodyStructure} issues a I{FETCH BODYSTRUCTURE} command and returns a Deferred which fires with a structure giving the result of parsing the server's response. The structure is a list reflecting the parenthesized data sent by the server, as described by RFC 3501, section 7.4.2. 3:9,10:*#text/plain; name=thing; key="value"this-is-the-content-id!describing-the-content-goes-here!8BIT abcdef123456zattachment; filename=monkeysrIzhttp://example.com/monkeysr(r1r(Body Text Goes Here NrrrFplainrNrrthing20rWr/filenamerKrfetchBodyStructurerrrrTrhr[rms r4test_fetchBodyStructurez%NewFetchTests.test_fetchBodyStructures 66 " $I":+N17#1+I(,(D +   ( 5,7"!J #:;0 "  $s##r6c$|jdS)z If passed C{True} for the C{uid} argument, C{fetchBodyStructure} can also issue a I{UID FETCH BODYSTRUCTURE} command. r)rrRs r4testFetchBodyStructureUIDz'NewFetchTests.testFetchBodyStructureUIDs ++A..r6c|jj|_d|_t dddddddd d d d d dd}t ddddd d d d|gg|_ddddgdddddddddgdd g dddgdddgii|_|j|S)z L{IMAP4Client.fetchBodyStructure} can also parse the response to a I{FETCH BODYSTRUCTURE} command for a multipart message. rrrrrr& 123456abcdefinlinez outer space)rrrrr+r)r*r,r1r6rrNzmultipart/mixed; boundary="xyz"ennearby)rr+r,rrrFrrrrWmixedboundaryxyzr)rEr innerMessages r4 test_fetchBodyStructureMultipartz.NewFetchTests.test_fetchBodyStructureMultiparts  66 " # E6'J-3$(-'/$1    '   $ $E(,(0      90;&!4(% ''"  2s##r6c|jj|_d|_t iddddt ddidddddgg|_d d gd ii|_|j|S) N21r1r6 Yea whateverfr image/jpgBody Body BodyrrNNNNNN12rfetchSimplifiedBodyrrrrTrhr[rms r4testFetchSimplifiedBodyz%NewFetchTests.testFetchSimplifiedBodyEs 77   '5)      &V%OPQ s##r6c$|jdSrs)rrRs r4testFetchSimplifiedBodyUIDz(NewFetchTests.testFetchSimplifiedBodyUID_s++A..r6c|jj|_d|_t ddidddddg|_dd gd ii|_|j|S) Nrrrr1r6rrrr)rFrNNNNrrrrms r4testFetchSimplifiedBodyTextz)NewFetchTests.testFetchSimplifiedBodyTextbse 77  .C%QU   LM  s##r6c$|jdSrs)rrRs r4testFetchSimplifiedBodyTextUIDz,NewFetchTests.testFetchSimplifiedBodyTextUIDps//22r6c|jj|_d|_t ddiddddt ddidd d ddgg|_d d d ddddddddgdggdgddddddg gddg ii|_|j|S)Nrrr8r1r6rrrr(rrrrrrNNN)rjpgNNNN14rrrms r4testFetchSimplifiedBodyRFC822z+NewFetchTests.testFetchSimplifiedBodyRFC822ss 77  !12 '5)      ( +,+, C+  8s##r6c$|jdSrs)rrRs r4 testFetchSimplifiedBodyRFC822UIDz.NewFetchTests.testFetchSimplifiedBodyRFC822UIDs11!44r6c 2|jj|_d|_t ddidddddt dd iddd d dg}t dd idd dd|}t ddidd dd|g}|g|_ddgdgddgdgii|_|jdS)ah L{IMAP4Client.fetchSimplifiedBody} returns a dictionary mapping message sequence numbers to fetch responses for the corresponding messages. In particular, for a multipart message, the value in the dictionary maps the string C{"BODY"} to a list giving the body structure information for that message, in the form of a list of subpart body structure information followed by the subtype of the message (eg C{"alternative"} for a I{multipart/alternative} message). This structure is self-similar in the case where a subpart is itself multipart. rrrr1sdatesStuffrjNrsThingsi~rr6s Irrelevantr4zmultipart/mixedsRootOfírr)rFrNNNN5r)rFhtmlNNNNrIr alternativerFr)rEsinglesrrs r4!test_fetchSimplifiedBodyMultipartz/NewFetchTests.test_fetchSimplifiedBodyMultiparts 77   .GXud  -r7Iud   # 4 5        . /     M w  KJ%      u%%r6c|jj|_d|_t ddidddddg|_dd d ii|_|j|S) Nz 1,3,7,10101rValuer1r6s BODY TEXT [rrzHeader: Value BODY TEXT )rrrrrrTrhr[rms r4testFetchMessagezNewFetchTests.testFetchMessages^ 00 % (G,b#7GT R  X'KLM s##r6c$|jdSrs)rrRs r4testFetchMessageUIDz!NewFetchTests.testFetchMessageUID$$Q''r6c|jj|_d|_t ddddddddg|_t tjddd}dd |ii|_ |j|S) Nz9,6,2V1V2)H1H2r1r6crr) r fetchHeadersrrrrTr(rrerhr[)rErrs r4testFetchHeaderszNewFetchTests.testFetchHeaderss| 00  D12sCT J  u334t4LMN )  s##r6c$|jdSrs)rrRs r4testFetchHeadersUIDz!NewFetchTests.testFetchHeadersUIDrr6c|jj|_d|_t ddidddddg|_dd d ii|_|j|S) Nz 1,2,3,4,5,6,7rrr1r(sBody goes here rrzBody goes here )rr@rrrrTrhr[rms r4 testFetchBodyzNewFetchTests.testFetchBodysc -- ' (G,b"6KSRV W    34  s##r6c$|jdSrs)rrRs r4testFetchBodyUIDzNewFetchTests.testFetchBodyUID!!!$$r6cjj_d_d}d}d}t }d|d<d|d<d |d <d |d <t }d |d <d|d <t }d|d <d|d <t |dd|dt |dd|ddt |dd|ddgg_dddgdggi_fd}jjfdjj|jjjjjjtjjjd}|jfd|S)zT Test the server's handling of requests for specific body sections. rr(rrrrrrrrrrrrrrr1Nrrrz&Contained body message text. Squarge.c|_yr0rrs r4r2z0NewFetchTests.testFetchBodyParts..result8rr6c>jjdS)NrrLrXr;s r4r5z2NewFetchTests.testFetchBodyParts..<sdmmDMMmBr6FrcPjjjSr0rZignrEs r4r5z2NewFetchTests.testFetchBodyParts..C$"2"24;; "Nr6rrrrrrrTrhrrrr'r r#rr) rErrrrrrr2rs ` r4testFetchBodyPartsz NewFetchTests.testFetchBodyPartss 11   > F -'* . "I"} "8 Y'3 ^$# #; i (3 n%  r4T4P D*dDQ    fse-UVWX   "" B  ""6* ""4#5#56 !!$//2  dkk G NOr6cnjj_d_dgd}t }d|d<d|d<d|d <d |d <t |d d |dd g_dddgdggi_fd}jjfdjj|jjjjjjtjjjd}|jfd|S)z Single-part messages have an implicit first part which clients should be able to retrieve explicitly. Test that a client requesting part 1 of a text/plain message receives the body of the text/plain part. rrsDA bodyrrrrrrrrr1NrrrzDA bodyc|_yr0rrs r4r2z>NewFetchTests.test_fetchBodyPartOfNonMultipart..resultZrr6c>jjS)NrLrX)r&partsrEs r4r5z@NewFetchTests.test_fetchBodyPartOfNonMultipart..^sdmmDMMmFr6FrcPjjjSr0rZrs r4r5z@NewFetchTests.test_fetchBodyPartOfNonMultipart..err6r)rErrr2rrs` @r4 test_fetchBodyPartOfNonMultipartz.NewFetchTests.test_fetchBodyPartOfNonMultipartFs 11   -'* . ".$Wb$ 3MN fseY789   "" F  ""6* ""4#5#56 !!$//2  dkk G NOr6c|jj|_d|_t idddddg|_dddii|_|j|S) Nz 1:100,2:*r1r6sxxxxxxxxxxxxxxxxxxxxrrrr)r fetchSizerrrrTrhr[rms r4 testFetchSizezNewFetchTests.testFetchSizehs[ -- # Rid ;    t$  s##r6c$|jdSrs)rrRs r4testFetchSizeUIDzNewFetchTests.testFetchSizeUIDsrr6c.|jj|_d|_t idddddt idddd dg|_gdd d ddgd ggd gddddddg gd dgdddddgd ggd gddddddg gddd|_|j|S)Nz1,3)z\XYZz\YZXAbcs%Sun, 25 Jul 2010 06:20:30 -0400 (EDT)sxyzxyzi)z\Onez\TwoThreesMon, 14 Apr 2003 19:43:44 -0400s abcabcabcabcr@z25-Jul-2010 06:20:30 -0400rIr)NNNNNNrI)rrrrrz14-Apr-2003 19:43:44 -0400rrrk)r fetchFullrrrrTrhr[rms r4 testFetchFullzNewFetchTests.testFetchFullvs --  )8   +2    (3 <"'('( B!&5 <#'('( C!'%  Ls##r6c$|jdSrs)rrRs r4testFetchFullUIDzNewFetchTests.testFetchFullUIDrr6c |jj|_d|_t idddddt idddddg|_ddgd ggd gddddddg d d gd ddgd ggd gddddddg d d gd d|_|j|S)Nz1,2:3r1sMon, 14 Apr 2003 19:43:44 +0400sLalalarasTue, 15 Apr 2003 19:43:44 +0200sAlalaliNrrIz14-Apr-2003 19:43:44 +0400)rrrrz15-Apr-2003 19:43:44 +0200rk)rfetchAllrrrrTrhr[rms r4 testFetchAllzNewFetchTests.testFetchAlls ,,  B:Iud  B:Iud    '('(  # <&'('(  # <%#  Hs##r6c$|jdSrs)rrRs r4testFetchAllUIDzNewFetchTests.testFetchAllUIDs  ##r6c|jj|_d|_t idddddg|_ddgdd d i|_|j|S) Nr)\Xs19 Mar 2003 19:22:21 -0500r6rrrz19-Mar-2003 19:22:21 -05000)rrr)r fetchFastrrrrTrhr[rms r4 testFetchFastzNewFetchTests.testFetchFastse --  X'Dc1d S    <"  s##r6c$|jdSrs)rrRs r4testFetchFastUIDzNewFetchTests.testFetchFastUIDrr6r)1rsrtrurrhrjrr[rernrprvrxr{r|r}r~ noEsARLocaleErrorr rrrrrrrrrrrrrrrrrrrrrrrrrrrrr r1r6r4rNrN/sR3  A $" $&$"-%F$$V]]D9M 5  6  LCD-E-#$J)/$b/?$B$4/ $32$h5>&@$( $( $%/b D $%;$z%/$b$ $%M << sC00DDrNcpeZdZdZdZdZdZdZdZdZ dZ d Z d Z d Z d Zd ZdZdZdZdZy)DefaultSearchTestszz Test the behavior of the server's SEARCH implementation, particularly in the face of unhandled search terms. c tj|_d|j_||j_t j |_t|j|_ tidddddtidddddtidddddtidddddtidddddg|_ y) Nrr1r6r`rar4i!Ni"N) rrrrRr^rrrrrrrTrRs r4rzDefaultSearchTests.setUps'') $  )"4>>2 Rc3 5 Rc5$ 7 Rc5$ 7 Rc5$ 7 Rc5$ 7   r6c tttdt|jdz|jS)zW Pretend to be a mailbox and let C{self.server} lookup messages on me. r)rrrnrrTrs r4rzDefaultSearchTests.fetchs/CaT\\!2Q!67FGGr6cfd}jjt|}fd}|j||jj|j j j |S)a Issue a search with given query and verify that the returned messages match the given expected messages. @param queryTerms: A string giving the search query. @param expectedMessages: A list of the message sequence numbers expected as the result of the search. @return: A L{Deferred} which fires when the test is complete. c:jjSr0rr  queryTermsrEsr4r z8DefaultSearchTests._messageSetSearchTest..search"rr6c*j|yr0r%)rIexpectedMessagesrEs r4searchedz:DefaultSearchTests._messageSetSearchTest..searched's   W&6 7r6)rrr7rr'r r#)rEr r r rr s``` r4_messageSetSearchTestz(DefaultSearchTests._messageSetSearchTestse 2 NN & &uV} 5 8 h d(() T__% r6c(|jddgS)z Test that a search which starts with a message set properly limits the search results to messages in that set. rrr rRs r4test_searchMessageSetz(DefaultSearchTests.test_searchMessageSet0s ))#s33r6c*|jdgdS)zv If the search filter ends with a star, all the message from the starting point are returned. z2:*r6r rRs r4test_searchMessageSetWithStarz0DefaultSearchTests.test_searchMessageSetWithStar7 ))%>>r6c*|jdgdS)z If the search filter starts with a star, the result should be identical with if the filter would end with a star. z*:2r6r rRs r4"test_searchMessageSetWithStarFirstz5DefaultSearchTests.test_searchMessageSetWithStarFirst>r r6c*|jdgdS)z If the search filter ends with a star, all the message from the starting point are returned (also for the SEARCH UID case). z UID 10000:*r6r rRs r4 test_searchMessageSetUIDWithStarz3DefaultSearchTests.test_searchMessageSetUIDWithStarE ))-FFr6c*|jdgdS)z If the search filter starts with a star, the result should be identical with if the filter would end with a star (also for the SEARCH UID case). z UID *:10000r6r rRs r4%test_searchMessageSetUIDWithStarFirstz8DefaultSearchTests.test_searchMessageSetUIDWithStarFirstLr r6c(|jddgS)z A search filter of 1234:* should include the UID of the last message in the mailbox, even if its UID is less than 1234. z UID 30000:*rr rRs r4,test_searchMessageSetUIDWithStarAndHighStartz?DefaultSearchTests.test_searchMessageSetUIDWithStarAndHighStartSs ))-!==r6c(|jddgS)z If the search filter contains nesting terms, one of which includes a message sequence set with a wildcard, IT ALL WORKS GOOD. z(6:*)rr rRs r4test_searchMessageSetWithListz0DefaultSearchTests.test_searchMessageSetWithList[s))'A377r6c*|jdddgS)z If the search filter contains an I{OR} term, all messages which match either subexpression are returned. zOR 1 2rrr rRs r4rlz DefaultSearchTests.test_searchOres ))(QF;;r6c*|jdgdS)z If the search filter contains an I{OR} term with a subexpression which includes a message sequence set wildcard, all messages in that set are considered for inclusion in the results. z OR 2:* 2:*r6r rRs r4test_searchOrMessageSetz*DefaultSearchTests.test_searchOrMessageSetls)), EEr6c*|jdgdS)z If the search filter contains a I{NOT} term, all messages which do not match the subexpression are returned. zNOT 3)rrrrr rRs r4roz!DefaultSearchTests.test_searchNotus ))'<@@r6c(|jddgS)z If the search filter contains a I{NOT} term with a subexpression which includes a message sequence set wildcard, no messages in that set are considered for inclusion in the result. zNOT 2:*rr rRs r4test_searchNotMessageSetz+DefaultSearchTests.test_searchNotMessageSet|s)))aS99r6c(|jddgS)z If the search filter contains multiple terms implicitly conjoined with a message sequence set wildcard, only the intersection of the results of each term are returned. z2:* 3rr rRs r4test_searchAndMessageSetz+DefaultSearchTests.test_searchAndMessageSets ))'A377r6c$dfd}jjt|}j|tj }fd}|j||j jj|S)z If the search criteria is not a valid key, a NO result is returned to the client (resulting in an error callback), and an IllegalQueryError is logged on the server side. FOOc:jjSr0r r sr4r z=DefaultSearchTests.test_searchInvalidCriteria..searchrr6cRjjjjjjj t j }jt|djtdt|y) Verify that the server logs an IllegalQueryError and the client raises an IMAP4Exception with 'Search failed:...' rs)SEARCH failed: Invalid search command FOON rrrrr~rr$rBrrrIr{rEs r4 errorReceivedzDDefaultSearchTests.test_searchInvalidCriteria..errorReceiveds} KK ! ! 0 0 2 KK ! ! 0 0 2++E,C,CDF   S[! ,   @AG  r6 rrr7rrrr'r r#)rEr rr1 r s` @r4test_searchInvalidCriteriaz-DefaultSearchTests.test_searchInvalidCriteriasr   2 NN & &uV} 5   q%"6"6 7 $ m$ T__% r6N)rsrtrur3rrr r r r r r r r! rlr$ ror' r) r3 r1r6r4r r s\  H 24??GG>8<FA:8#r6r cLeZdZdZdZdZeZdZdZdZ dZ dZ d Z d Z y ) FetchSearchStoreTestsc4dx|_|_d|_d|_d|_d|_t j|_d|j_ ||j_ tj|_ t|j|_yr)rhr2server_received_queryserver_received_uidserver_received_partsserver_received_messagesrrrrRr^rrrrrrRs r4rzFetchSearchStoreTests.setUpsv&**  %)"#' %)"(,%'') $  )"4>>2 r6cl|dgk(rtjd||_||_|jS)Nr~z"FOO is not a valid search criteria)rr$r7 r8 rh)rErrs r4r zFetchSearchStoreTests.searchs8 VH ))*NO O%*"#& }}r6cyr0r1)rErrs r4rhz!FetchSearchStoreTests.addListenerrr6cnfd}fd}jjt|j|jjj j fd}t jjjd}|j||S)NcRjjjS)Nr )rr rrmsr4r z1FetchSearchStoreTests._searchWork..searchs!;;%%djjc%: :r6c|_yr0rrs r4r2z1FetchSearchStoreTests._searchWork..resultrr6c|jjjujjjjjj jt jjjdjy)Ncharmap) rTr2rhrBrr8 rrrrCr7 rs r4rz0FetchSearchStoreTests._searchWork..checks   T[[DMM9 :   T[[$-- 8   TXXt'?'? @   '' (9(9)(DE**  r6Frr)rErr r2rrs`` r4 _searchWorkz!FetchSearchStoreTests._searchWorks ;  ""5=1==fEQQ    *T__ %   dkk G er6ctjtjdtjdd|_gd|_d|_|j dS)Nr substringrr r )rrrrr)rrrrrhrrB rRs r4 testSearchz FetchSearchStoreTests.testSearchsNXX KK7 8 KKtT 2  % ""r6ctjtjdtjdd|_d|_gd|_|j dS)NrD rF rG rH rI rr)rrrrrrhrB rRs r4 testUIDSearchz#FetchSearchStoreTests.testUIDSearchsNXX KK7 8 KKtT 2  ! ""r6c |j|dS#ttf$r|j|dz cYSt$rYywxYw)Nrrrq)rhr IndexErrorKeyErrorrErs r4rzFetchSearchStoreTests.getUIDsM ==%e, ,:& *==q) )  s!AAAcH||_t||_|jSr0)r8 rr: rhrs r4rzFetchSearchStoreTests.fetchs #& (+H %}}r6c`fd}jjt|j|jjj j fd}t jjjd}|j||S)Nc|_yr0rrs r4r2z0FetchSearchStoreTests._fetchWork..result rr6cjjjujxrjj j xrj j j r0jjD]\}}t||d<jjjjj jjjj jtjjtjjy)Nr)rTr2rhrrr9 rrPrrBr8 rrrr: )rTkvrEs r4rz/FetchSearchStoreTests._fetchWork..checks    T[[DMM9 : JJ ,4::??,  & & L4+E+E+J+J+Lxx MM//1&DAq"1vAeH&   T[[$-- 8   TXXt'?'? @   TZZ)C)C D   !!$--0!!$"?"?@ r6Frr)rErr2rrs` r4r[z FetchSearchStoreTests._fetchWork s  ""5<0<.search2s;;%%e, ,r6cRjjjjjjj t j }jt|djtdt|y)r. rs1SEARCH failed: FOO is not a valid search criteriaNr/ r0 s r4r1 z=FetchSearchStoreTests.test_invalidTerm..errorReceived8s| KK ! ! 0 0 2 KK ! ! 0 0 2++E,C,CDF   S[! ,   HI3w< r6r2 )rEr rr1 rs` @r4test_invalidTermz&FetchSearchStoreTests.test_invalidTerm*sr  - NN & &uV} 5   q%"6"6 7 " m$ T__% r6N)rsrtrurr rhrjrB rJ rL rrr[rZ r1r6r4r5 r5 s; 3 !N8## >"r6r5 ceZdZdZdZy) FakeMailboxcg|_yr0)rrRs r4rzzFakeMailbox.__init__P  r6ch|jj|||ftjdSr0)rr|rr[)rErrrs r4rzFakeMailbox.addMessageSs* $t,-}}T""r6N)rsrtrurzrr1r6r4r\ r\ Os #r6r\ ceZdZdZdZdZy)FeaturefulMessagecy)Nrr1rRs r4rnzFeaturefulMessage.getFlagsZsr6cy)Nrr1rRs r4rz!FeaturefulMessage.getInternalDate]sr6ctdS)NopenrrRs r4ryzFeaturefulMessage.open`s wr6N)rsrtrurnrryr1r6r4ra ra Xs r6ra ceZdZdZdZy)MessageCopierMailboxcg|_yr0)msgsrRs r4rzzMessageCopierMailbox.__init__fr^ r6cb|jj|t|jSr0)ri r|rrP s r4rzMessageCopierMailbox.copyis" 499~r6N)rsrtrurzrr1r6r4rg rg ds r6rg ceZdZdZdZdZy)CopyWorkerTestsctj}|j}t|t ddDcgc]}|t fc}d}fd}|j |Scc}w)Nrr?rcjD]O}j|djdj|ddj|ddQ|D](\}}j|j|d*y)Nrre rrrr)rrBrWrV)rIrrbr2rrEs r4cbCopyz5CopyWorkerTests.testFeaturefulMessage..cbCopysVV 7  1g6  1w/  1~6 7 #* /'  . /r6)rr_IMAP4Server__cbCopyr\ rnra r)rEr|r3rrro rs` @r4testFeaturefulMessagez%CopyWorkerTests.testFeaturefulMessageosh      " " M q">A$&'>q I /}}V$$?sA0c ftj}|j}tt ddDcgc]$}t dt |iddd|fz|dzd&}}|tt dd|Dcgc]}|c}d}fd }|j|Scc}wcc}w) Nrr?zHeader-Counterr1DatesBody %drrcg}jD]N}|j|djj|ddj|ddP|j t dt ddD}j|||D](\}}j|j|d*y)Nrrr1rrs c3*K|] }d||fz yw)sHeader-Counter: %d Body %dNr1r+s r4r-zJCopyWorkerTests.testUnfeaturefulMessage..cbCopy..sBC41v=sr?)rr|rWrBrrfrnrV)rIseenrexprbr2rrEs r4ro z7CopyWorkerTests.testUnfeaturefulMessage..cbCopysDVV 0 AaDIIK(  1r*  1w/ 0 IIKGLQPR|C   T3 '") /'  . /r6) rrrp r\ rnrrrr) rEr|r3rri imrro rs ` @r4testUnfeaturefulMessagez'CopyWorkerTests.testUnfeaturefulMessages      " " M 1b\   !3q6*Bqd9JAPRFTX   Ca d34br4eQ ? /"}}V$$3 5s )B) B.c<tj}|j}tt ddDcgc] }t c}|t t ddDcgc]}|c}d}fd}|j|Scc}wcc}w)Nrr?stagc j|ttdgdztddtjD]\}}j ||y)Nrrr?)rBrrrnri r)rIorigrrri rEs r4ro z1CopyWorkerTests.testMessageCopier..cbCopysY   Wd3sRxq"+F&G H qvv. 0 c$$T3/ 0r6)rrrp rg rnobjectrr) rEr|r3rrx rro rri s ` @@r4testMessageCopierz!CopyWorkerTests.testMessageCopiers      " " ""'2,/Q/ Ca d34br4fa @ 0 }}V$$04s B* BN)rsrtrurq ry r~ r1r6r4rl rl ns%8 %D%r6rl zOpenSSL not presentzReactor doesn't support SSLcveZdZdZdZereZereZdZdZdZ dZ dZ d dZ dZ d Zd Zd Zy) TLSTestsNcZtj|j|jdS)NFr)r#rrrrRs r4r#zTLSTests.loopbacks##DKKEJJr6c tjjdg fd} fd} fd} fd} fd}dj_|||||g D]&}j j t|(j jjj fd}j}|j ||S) Nrc^jdjjddSrG)r|rrHcalledrEsr4rHz)TLSTests.testAPileOfThings..logins' MM$ ;;$$[2BC Cr6c^jdjjddS)Nr%)r|rrr sr4rz(TLSTests.testAPileOfThings..lists& MM$ ;;##Hd3 3r6c^jdjjddS)NrrS)r|rrbr sr4rbz*TLSTests.testAPileOfThings..statuss& MM$ ;;%%h : :r6c\jdjjdS)Nr)r|rrr sr4rz+TLSTests.testAPileOfThings..examines$ MM$ ;;&&x0 0r6cZjdjjSr0)r|rr9r sr4r9z*TLSTests.testAPileOfThings..logouts" MM$ ;;%%' 'r6Tcjjjdjjjdjt t yr)rBr startedTLSrr)rTr methodsrEs r4rz)TLSTests.testAPileOfThings..checksO   T[[33T :   T[[33T :   S[#g, 7r6) rrrrrequireTransportSecurityrrr7rrr r#) rErHrrbrr9rrrr r s ` @@r4testAPileOfThingszTLSTests.testAPileOfThingss**84 D 4 ; 1 (04 ,$8 6F NN & &uV} 5 6 ##D$6$6H 8 MMO er6cjjjddgjj t j djjfdjfdjjjjjjj}|jfd|S)Nrrc:jjdS)Nrrr;s r4r5z)TLSTests.testLoginLogin..sdkk../?@r6c8jjSr0)rr9r;s r4r5z)TLSTests.testLoginLogin..s 2 2 4r6c:jtdSrs)rBrr\rEsuccesss r4r5z)TLSTests.testLoginLogin..s 0 0Wq Ar6)rrrrrrrrrr|rr'r r#)rErr s` @r4testLoginLoginzTLSTests.testLoginLogins ##K1AB ))%*B*B;*OP "" @ +4 5kk NN7 +    * OO  MMO ABr6cgjjtjjfd}jj|jjj j }|jfdtj|jgS)z Begin a C{STARTTLS} sequence and assert that it results in a TLS session. @return: A L{Deferred} that fires when the underlying connection between the client and server has been terminated. cjtjjjj yr0)rVr ISSLTransport providedByrrrs r4 checkSecurez6TLSTests.startTLSAndAssertSession..checkSecures* OOJ44?? @U@UV Wr6c&jSr0)rVr s r4r5z3TLSTests.startTLSAndAssertSession..s 8r6) rrr7rstartTLSr|r#rr()rEr rr s` @r4startTLSAndAssertSessionz!TLSTests.startTLSAndAssertSessions ""5)=)=#>? X "";/ ""7>>2 MMO 89""At~~#677r6c|j}|jj|j|jj |j |S)z L{IMAP4Client.startTLS} triggers TLS negotiation and returns a L{Deferred} which fires after the client's transport is using encryption. )r rrrr'r rE disconnecteds r4 test_startTLSzTLSTests.test_startTLSsF 446  ""4#5#56 !!$//2r6c&|j|jjd|j_|j}|jj |j |jj|j|S)zd L{IMAPClient.startTLS} supplies a default TLS context if none is supplied. N) assertIsNotNonercontextr rrrr'r r s r4test_startTLSDefaultzTLSTests.test_startTLSDefault'sj T[[001" )-)F)F)H  ""4#5#56 !!$//2r6cGddt}||j|j|_|j }|jj t |jj|jj|jd|jj |j|jj|j|S)z] A server that receives a second C{STARTTLS} sends a C{NO} response. ceZdZdZy):TLSTests.test_doubleSTARTTLS..DoubleSTARTTLSClientc|jstj|S|jt j dS)NsSTARTTLS)r rr rrr8rRs r4r zCTLSTests.test_doubleSTARTTLS..DoubleSTARTTLSClient.startTLS:s4'0066'' k(BCCr6N)rsrtrur r1r6r4DoubleSTARTTLSClientr 9s Dr6r rsTLS already negotiated) rrrrr rr7r r'rrr )rEr r s r4test_doubleSTARTTLSzTLSTests.test_doubleSTARTTLS3s  D< D+ NN4>>  446  ""5)=)=#>? !!  + +-F  ""4#5#56 !!$//2r6ctjtjdj_t j fd}jjt|j}jjt|jjjjjj|S)z Starting a TLS negotiation with an L{IMAP4Server} that already has C{LOGIN} and C{PLAIN} L{IChallengeResponse} factories uses those factories. )rrc3Kjj}jd|jd|djd|dyw)Nr/rr)rrrrqs r4assertLOGINandPLAINzJTLSTests.test_startTLSWithExistingChallengers..assertLOGINandPLAIN[sP!%!>L MM'< 0 MM(L$9 : MM(L$9 :sAA)rrrrr2rrrrr7r rr'r )rEr r s` r4$test_startTLSWithExistingChallengersz-TLSTests.test_startTLSWithExistingChallengersPs,,,,#      ;  ; ""5)<#=>446  ""5)<#=> ""4#5#56 !!$//2r6cdj_jjfdjj j djjj jj jtjjjgS)z| A client that attempts to log in before issuing the C{STARTTLS} command receives a C{NO} response. c0tjgdfS)NzOK Begin TLS negotiation now)rr[r1r6r4r5z3TLSTests.test_loginBeforeSTARTTLS..ssu}} / 0( r6c<jjddS)Nswrongstimerzr;s r4r5z3TLSTests.test_loginBeforeSTARTTLS..wsdkk''':r6s!LOGIN is disabled before STARTTLS) rr rrr'rrr rr(r#rRs`r4test_loginBeforeSTARTTLSz!TLSTests.test_loginBeforeSTARTTLSms    "" :  !!  + + 0 ""4#5#56 !!$//2""DMMOT^^#DEEr6cgfd}jj|jjfdjjfdjjjjjjfd}j j|S)Nc(dj_yr)r canStartTLSrs r4breakServerTLSz3TLSTests.testFailedStartTLS..breakServerTLSs&+DKK #r6c8jjSr0)rr rs r4r5z-TLSTests.testFailedStartTLS..st{{/C/C/Er6c`j|jtjSr0)r|rrr)r rs r4r5z-TLSTests.testFailedStartTLS..s1E1E(FGr6cnjjdtjyr)rVrrr)rTrrEs r4rz*TLSTests.testFailedStartTLS..checks) OOH %  !e.B.B Cr6)rrr'rr r#)rEr rrs` @r4testFailedStartTLSzTLSTests.testFailedStartTLSs , "">2 ""#EF !! G  ""4#5#56 !!$//2 D}}**511r6)returnzDeferred[object])rsrtrurrr-r,r#r r r r r r r r r r1r6r4r r sYII$& $& K'R$8*  ::F.2r6r ceZdZdZdZdZdZy) SlowMailboxrNctj}|j|j|jd|j j d|S)Nr1)rr callLaterhowSlowr fetchDeferred)rErrrs r4rzSlowMailbox.fetchs? NN  t||QZZ4 ##D)r6)rsrtrur r r rr1r6r4r r sGIMr6r c0eZdZdZdZdZdZdZdZy) TimeoutTestsctdj_dj_j j_d_fd}fdjjt|}|jjtj|jgS)z{ The *client* has a timeout mechanism which will close connections that are inactive for a period. TrNcjjdd}jd|j|S)Nrrr)rrHadvancer')rrrEtimedOuts r4rHz.TimeoutTests.test_serverTimeout..logins6 !!+/?@A IIaL LL "Hr6chjd|jtjyr0)rrr TimeoutErrorrs r4r z1TimeoutTests.test_serverTimeout..timedOuts%   t $ GLL++ ,r6)rrrrrr rrrr7r'r rr(r#)rErHrrr s` @@r4test_serverTimeoutzTimeoutTests.test_serverTimeouts G"&   !      - NN & &uU| 4 T__%""At}}#788r6c,tjj_fd}fd}jj t |}|j t |t j|jgS)z4 The server times out a connection. c<jjddSrGrzrRsr4rHz/TimeoutTests.test_serverTimesOut..loginr{r6cVjjjdzyNrr rPOSTAUTH_TIMEOUTrrEsr4 expireTimez4TimeoutTests.test_serverTimesOut..expireTime IIdkk22Q6 7r6) rr rrrr7rr(r#)rErHr rrs` @r4test_serverTimesOutz TimeoutTests.test_serverTimesOutsp G !   D 8 NN & &uU| 4 eJ'( ""At}}#788r6cjtjdttjj dtjj dj tjtjj_ fd}fd}fd}fd}fd}jjt|}|jt||jt||jt||jt|tj |j#gS) z^ The server unsets the selected mailbox when timing out a connection. r mailbox-test MAILBOX-TESTc<jjddSrGrzrRsr4rHz7TimeoutTests.test_serverUnselectsMailbox..loginr{r6c:jjdSNr rrRsr4rz8TimeoutTests.test_serverUnselectsMailbox..selectrr6cRjjjyr0)rrr^r^rEsr4 assertSetz;TimeoutTests.test_serverUnselectsMailbox..assertSets MM$ 0 0 1r6cVjjjdzyr r r sr4r z.expireTimer r6cPjjjyr0)rTrr^rRsr4 assertUnsetz=TimeoutTests.test_serverUnselectsMailbox..assertUnsets   T[[-- .r6)rrrrrrrTr"r rr rrrr7rr(r#) rErHrr r r rrr^s ` @@r4test_serverUnselectsMailboxz(TimeoutTests.test_serverUnselectsMailboxs  <**,<>PQ**>:&&00@ .99$?@ G !   D 6 2 8 / NN & &uU| 4 eFm$ eI&' eJ'( eK() ""At}}#788r6ctjjdtjjdt t t jj_fd}fd}fd}fd}fd}jjt|}|jt||jt||jt||jt|tj|jgS)zi The server closes the selected, closeable mailbox when timing out a connection. r r c<jjddSrGrzrRsr4rHz?TimeoutTests.test_serverTimesOutAndClosesMailbox..login r{r6c:jjdSr rrRsr4rz@TimeoutTests.test_serverTimesOutAndClosesMailbox..select rr6c<jjyr0)rTrr sr4assertMailboxOpenzKTimeoutTests.test_serverTimesOutAndClosesMailbox..assertMailboxOpens   T[[ )r6cVjjjdzyr r r sr4r zDTimeoutTests.test_serverTimesOutAndClosesMailbox..expireTimer r6c<jjyr0)rVrr sr4assertMailboxClosedzMTimeoutTests.test_serverTimesOutAndClosesMailbox..assertMailboxCloseds OODKK (r6)rrrrr r"rr rrrr7rr(r#) rErHrr r r rrr^s ` @@r4#test_serverTimesOutAndClosesMailboxz0TimeoutTests.test_serverTimesOutAndClosesMailboxs **>:&&00@*D1 G !   D 6 * 8 ) NN & &uU| 4 eFm$ e-./ eJ'( e/01 ""At}}#788r6chtjt_tjt_jj _ttj_ tjjdj jdfd}fd}fd}fd}fd}tj j|jjt|}|jt||jt||jt||jj|j!j"tj$|j'g}|S)zM The connection timeout does not take effect during fetches. r rc<jjddSrGrzrRsr4rHz7TimeoutTests.test_longFetchDoesntTimeout..login0r{r6cpjjdjjdS)Nrr )r setTimeoutrrrRsr4rz8TimeoutTests.test_longFetchDoesntTimeout..select3s* KK " "1 %;;%%n5 5r6c:jjdS)Nrr^rRsr4rz7TimeoutTests.test_longFetchDoesntTimeout..fetch7s;;''. .r6cRjjjdy)Nr)rrrRrRsr4stillConnectedz@TimeoutTests.test_longFetchDoesntTimeout..stillConnected:s    1 19 =r6cHtdD]}jdy)Nrg?)rnr )rTrrs r4 cbAdvancez;TimeoutTests.test_longFetchDoesntTimeout..cbAdvance=s!1X  # r6)rr r rrr rrrrrr rrr7rr'r r(r#) rErHrrr r r)rrs ` @r4test_longFetchDoesntTimeoutz(TimeoutTests.test_longFetchDoesntTimeout#s& G ! $)NN$4 ! !  1< .**>: q! D 6 / >  !!--i8 ^^ ' 'e 5 uV}% uU|$ u^,- t))* doo&   T]]_ 5 6r6ct}t}|j|_|j|j_|jj |g|jj fd|j_|jdg|jjdz gdzz|j|jd|jjdz g|jy)z{ The *server* has a timeout mechanism which will close connections that are inactive for a period. c<jd|fdSrs)r|)reasonconnLostlosts r4r5z.[s( KK  V 5  5 r6gg@rg@N) rrrrkr rrpumptimeOutrTrV)rErrr r s @@r4test_idleClientDoesDisconnectz*TimeoutTests.test_idleClientDoesDisconnectLs G46 ![[  !   ""9-;;--&  " u ++c12Q667 t$ T[[((3./0 r6N) rsrtrur r r r r r r1r6r4r r s#929*%9N$9L'Rr6r ceZdZdZy)DisconnectionTestsc tj}t}|j||j |j ddt j}|jt jd|S)Nrz example.comConnection closed) rrrrrrHrrr)rErtrs r4"testClientDisconnectFailsDeferredsz5DisconnectionTests.testClientDisconnectFailsDeferredsjsm     , .     GGK /1E1E  --.ABCr6N)rsrtrur r1r6r4r r isr6r ceZdZdZdZdZy)SynchronousMailboxzb Trivial, in-memory mailbox implementation which can produce a message synchronously. c||_yr0r)rErs r4rzzSynchronousMailbox.__init__{s   r6c#XK|rJd|D]}||j|dz fyw)NzCannot handle uid requests.rr)rEr`rrs r4rzSynchronousMailbox.fetch~s;555w .Ct}}S1W-- - .s(*N)rsrtrur3rzrr1r6r4r r us !.r6r c eZdZdZeigddddeigddddeigddddgZdZdZd fd Zd Z d Z d Z y)PipeliningTestszM Tests for various aspects of the IMAP4 server's pipelining support. r6r:Nr=2chg|_t|_tjdd|j |_|j j|jt|j}d|j _ ||j _ |jjyr) iteratorsrrrriterateInReactorrrr rrRr^r)rErWs r4rzPipeliningTests.setUps(*''dD4I4IJ  ""4>>2$T]]3% "  r6chtj}|jj||f|S)z A fake L{imap4.iterateInReactor} that records the iterators it receives. @param iterator: An iterator. @return: A L{Deferred} associated with this iterator. )rrr r|)rEiteratorrs r4r z PipeliningTests.iterateInReactors+ NN  xm,r6cyrr1r1r6r4r5zPipeliningTests.rhr6c|jr|r|jddD]T}|jjs|jjj|jjr;V|jj ddj d|jr |ryyyy)a Advance pending iterators enqueued with L{iterateInReactor} in a round-robin fashion, resuming the transport's producer until it has completed. This ensures bodies are flushed. @param asLongAs: (optional) An optional predicate function. Flushing iterators continues as long as there are iterators and this returns L{True}. rrN)r rproducerr~rTr)rEasLongAses r4 flushPendingzPipeliningTests.flushPendingsnn^^A&q) 8nn--NN++;;=nn-- 8""1%a(11$7 nnnnr6c|jjtjt j yr0rrRs r4rzPipeliningTests.tearDownrr6cL|jjd|j|j|jj dj dtdt|jdjjdtdt|jdjjd td t|jd jjgy ) z Test that pipelined FETCH commands which can be responded to synchronously are responded to correctly. s901 FETCH 1 BODY[] 02 FETCH 2 BODY[] 03 FETCH 3 BODY[] r6* 1 FETCH (BODY[] ) 01 OK FETCH completed {5} r* 2 FETCH (BODY[] ) z 02 OK FETCH completed {5} rs* 3 FETCH (BODY[] ) z 03 OK FETCH completed {5} rN) rrr rBrrrr)r(rrrWrRs r4test_synchronousFetchz%PipeliningTests.test_synchronousFetchs   V    NN " HH.!' a(8(D(D(F(K(K(MNQ/!' a(8(D(D(F(K(K(MNQ/!' a(8(D(D(F(K(K(MNQ  r6cl|jjdtjtt gd}|j ||j|jjdjdtdt|jdjjg|jj!|jj#d |j%|jj|j |j|jjdjd d td t|jd jjgy)z When a server status change occurs during an ongoing FETCH command, the server status is buffered until the FETCH completes. s01 FETCH 1,2 BODY[] )TTF)r r6r z {5} rT)rr s* [READ-WRITE] r rN)rr functoolspartialnextrSr rBrrrr)r(rrrWrrrT)rEtwices r4test_bufferedServerStatusz)PipeliningTests.test_bufferedServerStatussa   !;<!!$-@(AB 5)  NN " HH/!' a(8(D(D(F(K(K(MNQ     $/ --/0   NN " HH/)!' a(8(D(D(F(K(K(MNQ   r6) rsrtrur3rrrr r rr r" r1r6r4r r sk RS$d3RS$d3RS$d3H  %18"L! F5 r6r ceZdZdZdZdZy)IMAP4ServerFetchTestszV This test case is for the FETCH tests that require a C{StringTransport}. ct|_tj|_d|j_|jj |jyr)rrrrrrRrrRs r4rzIMAP4ServerFetchTests.setUp!s>(*'') $  ""4>>2r6cV|jj|jjdd}|j |jj ||jj|jj tjdy)a If by any chance, extra bytes got appended at the end of a valid FETCH arguments, the client should get a BAD - arguments invalid response. See U{RFC 3501}, section 6.4.5, s0001 FETCH 1 FULLL s+0001 BAD Illegal syntax: Invalid Argument r N) rrrrrBrrrr)rErhs r4"test_fetchWithPartialValidArgumentz8IMAP4ServerFetchTests.test_fetchWithPartialValidArgument'sw    !:;C --/:  ""5#7#78K#LMr6N)rsrtrur3rr' r1r6r4r$ r$ s 3 Nr6r$ c.eZdZdZdZdZdZdZdZy)LiteralTestsMixinz Shared tests for literal classes. @ivar literalFactory: A callable that returns instances of the literal under test. c6tj|_y)z Shared setup. N)rrrrRs r4rzLiteralTestsMixin.setUpBs( r6c|jd|j}|jd|jd|j |jy)ze The literal returns L{None} when given less data than the literal requires. rG Ns incomplete)literalFactoryrrr\assertNoResult)rEliterals r4test_partialWritez#LiteralTestsMixin.test_partialWriteHsC %%dDMM: dGMM-89 DMM*r6cd}|jt||j}|j|}|j |t |j ||j|jy)zz The literal returns an empty L{bytes} instance when given exactly the data the literal requires. completeN)r, rrr\rrLrTr- rEdatar. leftovers r4test_exactWritez!LiteralTestsMixin.test_exactWriteQsa %%c$i?==& h. " DMM*r6cd}|jtd|j}|j|}|j |dy)zt The literal returns any left over L{bytes} when given more data than the literal requires. scompleteleftoverr1 leftoverN)r, rrr\rBr2 s r4test_overlongWritez$LiteralTestsMixin.test_overlongWrite^sB #%%c+&6 F==& ;/r6c|jd|j}d}|j|}|j||y)zo The literal returns an empty L{bytes} instance when given an empty L{bytes} instance. rr7 N)r, rr\rB)rEr. r3 r4 s r4test_emptyLiteralz#LiteralTestsMixin.test_emptyLiteraljs= %%a7==& 4(r6N) rsrtrur3rr/ r5 r8 r: r1r6r4r) r) :s ) + + 0 )r6r) c.eZdZdZej ZdZy)LiteralStringTestsz+ Tests for L{self.literalFactory}. c d}d}tjt||j}t |D]}|j ||j d|j|j}|j|||fy)z Calling L{imap4.LiteralString.callback} with a line fires the instance's L{Deferred} with a 2-L{tuple} whose first element is the collected data and whose second is the provided line. datar7N) r LiteralStringrrr'r\rrrB)rEr3 extrar. rr2s r4 test_callbackz LiteralStringTests.test_callback~s %%c$i?4 A MM!   "%%dmm4 $/r6N)rsrtrur3rr? r, rA r1r6r4r< r< ws((N0r6r< c4eZdZdZej ZdZdZy)LiteralFileTestsz) Tests for L{imap4.LiteralFile}. cxd}d}tjt||j}t |D]}|j ||j d|j|j}|jt|d|\}}|j|jdy)z Calling L{imap4.LiteralFile.callback} with a line fires the instance's L{Deferred} with a 2-L{tuple} whose first element is the file and whose second is the provided line. r> r7rN) r LiteralFilerrr'r\rrrBrWrEr3 r@ r. rr2dataFiles r4rA zLiteralFileTests.test_callbacks ##CIt}}=4 A MM!   "%%dmm4 Va( % '2r6cd}d}|jtjddtjt||j}t |D]}|j ||jd|j|j}|jt|d|\}}|j|jdy)a= A L{imap4.LiteralFile} whose size exceeds the maximum in-memory size spools its content to disk, and invoking its L{callback} with a line fires the instance's L{Deferred} with a 2-L{tuple} whose first element is the spooled file and whose second is the provided line. r> r7_memoryFileLimitrrN) rrrE rrr'r\rrrBrWrF s r4test_callbackSpooledToDiskz+LiteralFileTests.test_callbackSpooledToDisks 5$$&8!<##CIt}}=4 A MM!   "%%dmm4 Va( % '2r6N) rsrtrur3rrE r, rA rJ r1r6r4rC rC s&&N3,3r6rC c4eZdZdZdZdZdZdZdZdZ y) WriteBufferTestsz) Tests for L{imap4.WriteBuffer}. c"t|_yr0)rrrRs r4rzWriteBufferTests.setUps (*r6ctj|j}d|jz}|j ||j |jj y)zd L{imap4.WriteBuffer} buffers writes that are smaller than its buffer size. xN)r WriteBufferr bufferSizer\rTrrEbufr3 s r4r/ z"WriteBufferTests.test_partialWritesL /cnn$ $ --/0r6ctj|j}d|jdzz}|j ||j |jj |y)z L{imap4.WriteBuffer} writes data without buffering it when the size of the data exceeds the size of its buffer. rO rN)rrP rrQ r\rBrrR s r4r8 z#WriteBufferTests.test_overlongWritesS /s~~)* $ --/6r6cTtj|j}d|jz}d}|j ||j |jj |j ||j|jj ||zy)zp L{imap4.WriteBuffer} buffers writes until its buffer's size exceeds its maximum value. rO yN)rrP rrQ r\rTrrB)rErS firstData secondDatas r4test_writesImplyFlushz&WriteBufferTests.test_writesImplyFlushs /3>>)   ) --/0 * --/Z1GHr6cHtj|j}d|jz}|j ||j |jj |j|j|jj |y)z{ L{imap4.WriteBuffer.flush} flushes the buffer even when its size is smaller than the buffer size. rO N) rrP rrQ r\rTrflushrBrR s r4test_explicitFlushz#WriteBufferTests.test_explicitFlushsr /s~~& $ --/0  --/6r6ctj|j}|j|j |jj y)z_ L{imap4.WriteBuffer.flush} has no effect if when the buffer is empty. N)rrP rr[ rTr)rErS s r4test_explicitFlushEmptyBufferz.WriteBufferTests.test_explicitFlushEmptyBuffer s< /  --/0r6N) rsrtrur3rr/ r8 rY r\ r^ r1r6r4rL rL s&+ 1 7I"7 1r6rL )r3 __future__rrrUr r{rr collectionsrior itertoolsrtypingrr unittestr zope.interfacer zope.interface.verifyr r twisted.cred.checkersrtwisted.cred.credentialsrrrtwisted.cred.errorrtwisted.cred.portalrrtwisted.internetrrrrtwisted.internet.deferrtwisted.internet.taskrtwisted.internet.testingrr twisted.mailrtwisted.mail.imap4rtwisted.mail.interfacesr r!r"twisted.protocolsr#twisted.pythonr$r%r&twisted.python.compatr'r(r)twisted.trial.unittestr*r+twisted.test.ssl_helpersr,r- ImportErrorr7r9rwrrr5 IMailboxInfoIMailboxICloseableMailboxrVrMemoryAccountWithoutNamespacesrrrrrrrrrrrOrrrr%r0rirrrrr rrrr+rurrrIMessage FancyStrMixinrrrrNr ISearchableMailboxr5 r\ IMessageFilera IMessageCopierrg rl IReactorSSLr r r r r r r$ r) r< rC rL r1r6r4r s #  #!&;I 1.>>+'V) '--HH@K #b;Xb;J"d).d)NHV)HVV q +xq +h U  1H1HIP P JP f U  0T T 1T nuCC"&(;(; 35$$3,(5$$(,.,.,b_/'_/Da21a2H dX-xdXN V@@@:"""h4)8h4V / X/ ddT/dTNL"HL"^ $** $L'L^ BB6EI1EIP13F(02E*+=57J+=\/=46I/=d\ 35H\ ~JT3XJTZ,=46I,=^KS24GKS\ %##  U^^$"4%%$"$"N?!H.?!Da Ha H K %H.K %\s)8sl U % %&XH&6X'Xv## U     !  U ! !"#N%hN%b 34 "J " "7D 113PQU2U2R5U2p - #XD   . .T hT nNHN>:):)z0*,?0653((53pJ1*J1mtsQ Q"!Q"