/ProSnooperFx_src/indy10.0.52_source/Protocols/IdIMAP4.pas
Pascal | 6600 lines | 4687 code | 264 blank | 1649 comment | 708 complexity | ec27c6e2f5e54696e1225257f3a7e214 MD5 | raw file
Large files files are truncated, but you can click here to view the full file
- { $HDR$}
- {**********************************************************************}
- { Unit archived using Team Coherence }
- { Team Coherence is Copyright 2002 by Quality Software Components }
- { }
- { For further information / comments, visit our WEB site at }
- { http://www.TeamCoherence.com }
- {**********************************************************************}
- {}
- { $Log: 11627: IdIMAP4.pas
- {
- Rev 1.57 11/8/2004 8:39:00 AM DSiders
- Removed comment in TIdIMAP4.SearchMailBox implementation that caused DOM
- problem when locating the symbol id.
- }
- {
- { Rev 1.56 10/26/2004 10:19:58 PM JPMugaas
- { Updated refs.
- }
- {
- { Rev 1.55 2004.10.26 2:19:56 PM czhower
- { Resolved alias conflict.
- }
- {
- Rev 1.54 6/11/2004 9:36:34 AM DSiders
- Added "Do not Localize" comments.
- }
- {
- { Rev 1.53 6/4/04 12:48:12 PM RLebeau
- { ContentTransferEncoding bug fix
- }
- {
- { Rev 1.52 01/06/2004 19:03:46 CCostelloe
- { .NET bug fix
- }
- {
- { Rev 1.51 01/06/2004 01:16:18 CCostelloe
- { Various improvements
- }
- {
- { Rev 1.50 20/05/2004 22:04:14 CCostelloe
- { IdStreamVCL changes
- }
- {
- { Rev 1.49 20/05/2004 08:43:12 CCostelloe
- { IdStream change
- }
- {
- { Rev 1.48 16/05/2004 20:40:46 CCostelloe
- { New TIdText/TIdAttachment processing
- }
- {
- { Rev 1.47 24/04/2004 23:54:42 CCostelloe
- { IMAP-style UTF-7 encoding/decoding of mailbox names added
- }
- {
- { Rev 1.46 13/04/2004 22:24:28 CCostelloe
- { Bug fix (FCapabilities not created if not DOTNET)
- }
- {
- { Rev 1.45 3/18/2004 2:32:40 AM JPMugaas
- { Should compile under D8 properly.
- }
- {
- { Rev 1.44 3/8/2004 10:10:32 AM JPMugaas
- { IMAP4 should now have SASLMechanisms again. Those work in DotNET now.
- { SSL abstraction is now supported even in DotNET so that should not be
- { IFDEF'ed out.
- }
- {
- { Rev 1.43 07/03/2004 17:55:16 CCostelloe
- { Updates to cover changes in other units
- }
- {
- { Rev 1.42 2/4/2004 2:36:58 AM JPMugaas
- { Moved more units down to the implementation clause in the units to make them
- { easier to compile.
- }
- {
- { Rev 1.41 2/3/2004 4:12:50 PM JPMugaas
- { Fixed up units so they should compile.
- }
- {
- { Rev 1.40 2004.02.03 5:43:48 PM czhower
- { Name changes
- }
- {
- { Rev 1.39 2004.02.03 2:12:10 PM czhower
- { $I path change
- }
- {
- { Rev 1.38 1/27/2004 4:01:12 PM SPerry
- { StringStream ->IdStringStream
- }
- {
- { Rev 1.37 1/25/2004 3:11:12 PM JPMugaas
- { SASL Interface reworked to make it easier for developers to use.
- { SSL and SASL reenabled components.
- }
- {
- { Rev 1.36 23/01/2004 01:48:28 CCostelloe
- { Added BinHex4.0 encoding support for parts
- }
- {
- { Rev 1.35 1/21/2004 3:10:40 PM JPMugaas
- { InitComponent
- }
- {
- { Rev 1.34 31/12/2003 09:40:32 CCostelloe
- { ChangeReplyClass removed, replaced AnsiSameText with TextIsSame, stream code
- { not tested.
- }
- { Rev 1.33 28/12/2003 23:48:18 CCostelloe
- { More TEMPORARY fixes to get it to compile under D7 and D8 .NET
- }
- {
- { Rev 1.32 22/12/2003 01:20:20 CCostelloe
- { .NET fixes. This is a TEMPORARY combined Indy9/10/.NET master file.
- }
- {
- { Rev 1.31 14/12/2003 21:03:16 CCostelloe
- { First version for .NET
- }
- {
- { Rev 1.30 10/17/2003 12:11:06 AM DSiders
- { Added localization comments.
- { Added resource strings for exception messages.
- }
- {
- { Rev 1.29 2003.10.12 3:53:10 PM czhower
- { compile todos
- }
- {
- { Rev 1.28 10/12/2003 1:49:50 PM BGooijen
- { Changed comment of last checkin
- }
- {
- { Rev 1.27 10/12/2003 1:43:34 PM BGooijen
- { Changed IdCompilerDefines.inc to Core\IdCompilerDefines.inc
- }
- {
- { Rev 1.26 20/09/2003 15:38:38 CCostelloe
- { More patches added for different IMAP servers
- }
- {
- { Rev 1.25 12/08/2003 01:17:38 CCostelloe
- { Retrieve and AppendMsg updated to suit changes made to attachment encoding
- { changes in other units
- }
- {
- { Rev 1.24 21/07/2003 01:22:24 CCostelloe
- { Added CopyMsg and UIDCopyMsgs. (UID)Receive(Peek) rewritten. AppendMsg
- { still buggy with attachments. Public variable FGreetingBanner added. Added
- { "if Connected then " to Destroy. Attachment filenames now decoded if
- { necessary. Added support for multisection parts. Resolved issue of some
- { servers leaving out the trailing "NIL NIL NIL" at the end of some body
- { structures. UIDRetrieveAllHeaders removed
- }
- {
- { Rev 1.23 18/06/2003 21:53:36 CCostelloe
- { Rewrote GetResponse from scratch. Restored Capabilities for login. Compiles
- { and runs properly (may be a couple of minor bugs not yet discovered).
- }
- {
- { Rev 1.22 6/16/2003 11:48:18 PM JPMugaas
- { Capabilities has to be restored for SASL and SSL support.
- }
- {
- { Rev 1.21 17/06/2003 01:33:46 CCostelloe
- { Updated to support new LoginSASL. Compiles OK, may not yet run OK.
- }
- {
- { Rev 1.20 12/06/2003 10:17:54 CCostelloe
- { Partial update for Indy 10's new Reply structure. Compiles but does not run
- { correctly. Checked in to show problem with Get/SetNumericCode in IdReplyIMAP.
- }
- {
- { Rev 1.19 04/06/2003 02:33:44 CCostelloe
- { Compiles under Indy 10 with the revised Indy 10 structure, but does not yet
- { work properly due to some of the changes. Will be fixed by me in a later
- { check-in.
- }
- {
- { Rev 1.18 14/05/2003 01:55:50 CCostelloe
- { This version (with the extra IMAP functionality recently added) now compiles
- { on Indy 10 and works in a real application.
- }
- {
- { Rev 1.17 5/12/2003 02:19:56 AM JPMugaas
- { Now should work properly again. I also removed all warnings and errors in
- { Indy 10.
- }
- {
- { Rev 1.16 5/11/2003 07:35:44 PM JPMugaas
- }
- {
- { Rev 1.15 5/11/2003 07:11:06 PM JPMugaas
- { Fixed to eliminate some warnings and compile errors in Indy 10.
- }
- {
- { Rev 1.14 11/05/2003 23:53:52 CCostelloe
- { Bug fix due to Windows 98 / 2000 discrepancies
- }
- {
- { Rev 1.13 11/05/2003 23:08:36 CCostelloe
- { Lots more bug fixes, plus IMAP code moved up from IdRFCReply
- }
- {
- { Rev 1.12 5/10/2003 07:31:22 PM JPMugaas
- { Updated with some bug fixes and some cleanups.
- }
- {
- { Rev 1.11 5/9/2003 10:51:26 AM JPMugaas
- { Bug fixes. Now works as it should. Verified.
- }
- {
- { Rev 1.9 5/9/2003 03:49:44 AM JPMugaas
- { IMAP4 now supports SASL. Merged some code from Ciaran which handles the +
- { SASL continue reply in IMAP4 and makes a few improvements. Verified to work
- { on two servers.
- }
- {
- { Rev 1.8 5/8/2003 05:41:48 PM JPMugaas
- { Added constant for SASL continuation.
- }
- {
- { Rev 1.7 5/8/2003 03:17:50 PM JPMugaas
- { Flattened ou the SASL authentication API, made a custom descendant of SASL
- { enabled TIdMessageClient classes.
- }
- {
- { Rev 1.6 5/8/2003 11:27:52 AM JPMugaas
- { Moved feature negoation properties down to the ExplicitTLSClient level as
- { feature negotiation goes hand in hand with explicit TLS support.
- }
- {
- { Rev 1.5 5/8/2003 02:17:44 AM JPMugaas
- { Fixed an AV in IdPOP3 with SASL list on forms. Made exceptions for SASL
- { mechanisms missing more consistant, made IdPOP3 support feature feature
- { negotiation, and consolidated some duplicate code.
- }
- {
- { Rev 1.4 5/7/2003 10:20:32 PM JPMugaas
- }
- {
- { Rev 1.3 5/7/2003 04:35:30 AM JPMugaas
- { IMAP4 should now compile. Started on prelimary SSL support (not finished
- { yet).
- }
- {
- { Rev 1.2 15/04/2003 00:57:08 CCostelloe
- }
- {
- { Rev 1.1 2/24/2003 09:03:06 PM JPMugaas
- }
- {
- { Rev 1.0 11/13/2002 07:54:50 AM JPMugaas
- }
- unit IdIMAP4;
- {*
- IMAP 4 (Internet Message Access Protocol - Version 4 Rev 1)
- By Idan Cohen i_cohen@yahoo.com
- 2001-FEB-27 IC: First version most of the IMAP features are implemented and
- the core IdPOP3 features are implemented to allow a seamless
- switch.
- The unit is currently oriented to a session connection and not
- to constant connection, because of that server events that are
- raised from another user actions are not supported.
- 2001-APR-18 IC: Added support for the session's connection state with a
- special exception for commands preformed in wrong connection
- states. Exceptions were also added for response errors.
- 2001-MAY-05 IC:
- 2001-Mar-13 DS: Fixed Bug # 494813 in CheckMsgSeen where LastCmdResult.Text
- was not using the Ln index variable to access server
- responses.
- 2002-Apr-12 DS: fixed bug # 506026 in TIdIMAP4.ListSubscribedMailBoxes. Call
- ParseLSubResut instead of ParseListResult.
- 2003-Mar-31 CC: Added GetUID and UIDSearchMailBox, sorted out some bugs (details
- shown in comments in those functions which start with "CC:").
- 2003-Apr-15 CC2:Sorted out some more bugs (details shown in comments in those
- functions which start with "CC2:"). Set FMailBoxSeparator
- in ParseListResult and ParseLSubResult.
- Some IMAP servers generally return "OK completed" even if they
- returned no data, such as passing a non-existent message
- number to them: they possibly should return NO or BAD; the
- functions here have been changed to return FALSE unless they
- get good data back, even if the server answers OK. Similar
- change made for other functions.
- There are a few exceptions, e.g. ListMailBoxes may only return
- "OK completed" if the user has no mailboxes, these are noted.
- Also, RetrieveStructure(), UIDRetrieveStructure, RetrievePart,
- UIDRetrievePart, RetrievePartPeek and UIDRetrievePartPeek
- added to allow user to find the structure of a message and
- just retrieve the part or parts he needs.
- 2003-Apr-30 CC3:Added functionality to retrieve the text of a message (only)
- via RetrieveText / UIDRetrieveText / RetrieveTextPeek /
- UIDRetrieveTextPeek.
- Return codes now generally reflect if the function succeeded
- instead of returning True even though function fails.
- 2003-May-15 CC4:Added functionality to retrieve individual parts of a message
- to a file, including the decoding of those parts.
- 2003-May-29 CC5:Response of some servers to UID version of commands varies,
- code changed to deal with those (UID position varies).
- Some servers return NO such as when you request an envelope
- for a message number that does not exist: functions return
- False instead of throwing an exception, as was done for other
- servers. The general logic is that if a valid result is
- returned from the IMAP server, return True; if there is no
- result (but the command is validly structured), return FALSE;
- if the command is badly structured or if it gives a response
- that this code does not expect, throw an exception (typically
- when we get a BAD response instead of OK or NO).
- Added IsNumberValid, IsUIDValid to prevent rubbishy parameters
- being passed through to IMAP functions.
- Sender field now filled in correctly in ParseEnvelope
- functions.
- All fields in ParseEnvelopeAddress are cleared out first,
- avoids an unwitting error where some entries, such as CC list,
- will append entries to existing entries.
- Full test script now used that tests every TIdIMAP command,
- more bugs eradicated.
- First version to pass testing against both CommuniGate and
- Cyrus IMAP servers.
- Not tested against Microsoft Exchange, don't have an Exchange
- account to test it against.
- 2003-Jun-10 CC6:Added (UID)RetrieveEnvelopeRaw, in case the user wants to do
- their own envelope parsing.
- Code in RetrievePart altered to make it more consistent.
- Altered to incorporate Indy 10's use of IdReplyIMAP4 (not
- complete at this stage).
- ReceiveBody added to IdIMAP4, due to the response of some
- servers, which gets (UID)Receive(Peek) functions to work on
- more servers.
- 2003-Jun-20 CC7:ReceiveBody altered to work with Indy 10. Made changes due to
- LoginSASL moving from TIdMessageSASLClient to TIdSASLList.
- Public variable FGreetingBanner added to help user identify
- the IMAP server he is connected to (may help him decide the
- best strategy). Made AppendMsg work a bit better (now uses
- platform-independent EOL and supports ExtraHeaders field).
- Added 2nd version of AppendMsg. Added "if Connected then "
- to Destroy. Attachment filenames now decoded if necessary.
- Added support for multisection parts.
- 2003-Jul-16 CC8:Added RemoveAnyAdditionalResponses. Resolved issue of some
- servers leaving out the trailing "NIL NIL NIL" at the end of
- some body structures. (UID)Retrieve(Peek) functions
- integrated via InternalRetrieve, new method of implementing
- these functions (all variations of Retrieve) added for Indy
- 10 based on getting message by the byte-count and then feeding
- it into the standard message parser.
- UIDRetrieveAllHeaders removed: it was never implemented anyway
- but it makes no sense to retrieve a non-contiguous list which
- would have gaps due to missing UIDs.
- In the Indy 10 version, AppendMsg functions were altered to
- support the sending of attachments (attachments had never
- been supported in AppendMsg prior to this).
- Added CopyMsg and UIDCopyMsgs to complete the command set.
- 2003-Jul-30 CC9:Removed wDoublePoint so that the code is compliant with
- the guidelines. Allowed for servers that don't implement
- search commands in Indy 9 (OK in 10). InternalRetrieve
- altered to (hopefully) deal with optional "FLAGS (\Seen)"
- in response.
- 2003-Aug-22 CCA:Yet another IMAP oddity - a server returns NIL for the
- mailbox separator, ParseListResult modified. Added "Length
- (LLine) > 0)" test to stop GPF on empty line in ReceiveBody.
- 2003-Sep-26 CCB:Changed SendCmd altered to try to remove anything that may
- be unprocessed from a previous (probably failed) command.
- This uses the property FMilliSecsToWaitToClearBuffer, which
- defaults to 10ms.
- Added EIdDisconnectedProbablyIdledOut, trapped in
- GetInternalResponse.
- Unsolicited responses now filtered out (they are now transferred
- from FLastCmdResult.Text to a new field, FLastCmdResult.Extra,
- leaving just the responses we want to our command in
- FLastCmdResult.Text).
- 2003-Oct-21 CCC:Original GetLineResponse merged with GetResponse to reduce
- complexity and to add filtering unsolicited responses when
- we are looking for single-line responses (which GetLineResponse
- did), removed/coded-out much of these functions to make the
- code much simpler.
- Removed RemoveAnyAdditionalResponses, no longer needed.
- Parsing of body structure reworked to support ParentPart concept
- allowing parsing of indefinitely-nested MIME parts. Note that
- a`MIME "alternative" message with a plain-text and a html part
- will have part[0] marked "alternative" with size 0 and ImapPartNumber
- of 1, a part[1] of type text/plain with a ParentPart of 0 and an
- ImapPartNumber of 1.1, and finally a part[2] of type text/html
- again with a ParentPart of 0 and an ImapPartNumber of 1.2.
- Imap part number changed from an integer to string, allowing
- retrieval of IMAP sub-parts, e.g. part '3.2' is the 2nd subpart
- of part 3.
- 2003-Nov-20 CCD:Added UIDRetrievePartHeader & RetrievePartHeader. Started to
- use an abstracted parsing method for the command response in
- UIDRetrieveFlags. Added function FindHowServerCreatesFolders.
- 2003-Dec-04 CCE:Copied DotNet connection changes from IdSMTP to tempoarily bypass
- the SASL authentications until they are ported.
- 2004-Jan-23 CCF:Finished .NET port, added BinHex4.0 encoding.
- 2004-Apr-16 CCG:Added UTF-7 decoding/encoding code kindly written and submitted by
- Roman Puls for encoding/decoding mailbox names. IMAP does not use
- standard UTF-7 code (what's new?!) so these routines are localised
- to this unit.
- *}
- { Todo -oIC :
- Change the mailbox list commands so that they receive TMailBoxTree
- structures and so they can store in them the mailbox name and it's attributes. }
- { Todo -oIC :
- Add support for \* special flag in messages, and check for \Recent
- flag in STORE command because it cant be stored (will get no reply!!!) }
- { Todo -oIC :
- 5.1.2. Mailbox Namespace Naming Convention
- By convention, the first hierarchical element of any mailbox name
- which begins with "#" identifies the "namespace" of the remainder of
- the name. This makes it possible to disambiguate between different
- types of mailbox stores, each of which have their own namespaces.
- For example, implementations which offer access to USENET
- newsgroups MAY use the "#news" namespace to partition the USENET
- newsgroup namespace from that of other mailboxes. Thus, the
- comp.mail.misc newsgroup would have an mailbox name of
- "#news.comp.mail.misc", and the name "comp.mail.misc" could refer
- to a different object (e.g. a user's private mailbox). } {Do not Localize}
- { TO BE CONSIDERED -CC :
- Double-quotes in mailbox names can cause major but subtle failures. Maybe
- add the automatic stripping of double-quotes if passed in mailbox names,
- to avoid ending up with ""INBOX""
- }
- interface
- {CC3: WARNING - if the following gives a "File not found" error on compilation,
- you need to add the path "C:\Program Files\Borland\Delphi7\Source\Indy" in
- Project -> Options -> Directories/Conditionals -> Search Path}
- {$I IdCompilerDefines.inc}
- uses
- IdMessage,
- Classes,
- IdAssignedNumbers,
- IdMailBox,
- IdException,
- IdGlobal,
- IdMessageParts,
- IdMessageClient,
- IdReply,
- IdComponent, {CC6: Now needed for ReceiveBody}
- IdMessageCoder, {CC2: Now needed for parsing BODYSTRUCTURE}
- IdHeaderList, {CC7: Added for 2nd version of AppendMsg}
- IdCoderHeader, {CC7: Needed for decoding filenames}
- IdCoderMIME,
- IdCoderQuotedPrintable,
- IdCoderBinHex4,
- IdSASLCollection, {JPM - SASL authentication for IMAP4 in Indy 10}
- IdTStrings,
- IdMessageCollection;
- { MUTF7 }
- type
- EmUTF7Encode = class(EIdSilentException);
- EmUTF7Decode = class(EIdSilentException);
- const
- b64Chars : array[0..63] of char =
- 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+,'; {Do not Localize}
- b64Index : array [0..127] of integer = (
- -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1, // 16
- -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1, // 32
- -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,62,63,-1,-1,-1, // 48
- 52,53,54,55,56,57,58,59,60,61,-1,-1,-1,-1,-1,-1, // 64
- -1,00,01,02,03,04,05,06,07,08,09,10,11,12,13,14, // 80
- 15,16,17,18,19,20,21,22,23,24,25,-1,-1,-1,-1,-1, // 96
- -1,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40, // 112
- 41,42,43,44,45,46,47,48,49,50,51,-1,-1,-1,-1,-1 // 128
- );
- b64Table : array[0..127] of integer = (
- $FF,$FF,$FF,$FF, $FF,$FF,$FF,$FF, $FF,$FF,$FF,$FF, $FF,$FF,$FF,$FF, // 16
- $FF,$FF,$FF,$FF, $FF,$FF,$FF,$FF, $FF,$FF,$FF,$FF, $FF,$FF,$FF,$FF, // 32
- $20,$21,$22,$23, $24,$25,$FF,$27, $28,$29,$2A,$2B, $2C,$2D,$2E,$2F, // 48
- $30,$31,$32,$33, $34,$35,$36,$37, $38,$39,$3A,$3B, $3C,$3D,$3E,$3F, // 64
- $40,$41,$42,$43, $44,$45,$46,$47, $48,$49,$4A,$4B, $4C,$4D,$4E,$4F, // 80
- $50,$51,$52,$53, $54,$55,$56,$57, $58,$59,$5A,$5B, $5C,$5D,$5E,$5F, // 96
- $60,$61,$62,$63, $64,$65,$66,$67, $68,$69,$6A,$6B, $6C,$6D,$6E,$6F, // 112
- $70,$71,$72,$73, $74,$75,$76,$77, $78,$79,$7A,$7B, $7C,$7D,$7E,$FF);// 128
- type
- TIdMUTF7 = class(TObject)
- public
- function Encode(aString : string):string;
- function Decode(aString : string):string;
- function Valid(aMUTF7String : string):boolean;
- function Append(const aMUTF7String, aAnsiStr : string):string;
- end;
- { TIdIMAP4 }
- const
- wsOk = 1;
- wsNo = 2;
- wsBad = 3;
- wsPreAuth = 4;
- wsBye = 5;
- wsContinue = 6;
- type
- TIdIMAP4FolderTreatment = ( //Result codes from FindHowServerCreatesFolders
- ftAllowsTopLevelCreation, //Folders can be created at the same level as Inbox (the top level)
- ftFoldersMustBeUnderInbox, //Folders must be created under INBOX, such as INBOX.Sent
- ftDoesNotAllowFolderCreation, //Wont allow you create folders at top level or under Inbox (may be read-only connection)
- ftCannotTestBecauseHasNoInbox, //Wont allow top-level creation but cannot test creation under Inbox because it does not exist
- ftCannotRetrieveAnyFolders //No folders present for that user, cannot be determined
- );
- type
- TIdIMAP4AuthenticationType = (atUserPass, atSASL);
- const
- DEF_IMAP4_AUTH = atUserPass;
- IDF_DEFAULT_MS_TO_WAIT_TO_CLEAR_BUFFER = 10;
- {CC3: TIdImapMessagePart and TIdImapMessageParts added for retrieving
- individual parts of a message via IMAP, because IMAP uses some additional
- terms.
- Note that (rarely) an IMAP can have two sub-"parts" in the one part -
- they are sent in the one part by the server, typically a plain-text and
- html version with a boundary at the start, in between, and at the end.
- TIdIMAP fills in the boundary in that case, and the FSubpart holds the
- info on the second part. I call these multisection parts.}
- type
- TIdImapMessagePart = class(TCollectionItem)
- protected
- FBodyType: string;
- FBodySubType: string;
- FFileName: string;
- FDescription: string;
- FEncoding: TIdMessageEncoding;
- FContentTransferEncoding: string;
- FSize: integer;
- FUnparsedEntry: string; {Text returned from server: useful for debugging or workarounds}
- FBoundary: string; {Only used for multisection parts}
- FParentPart: Integer;
- FImapPartNumber: string;
- public
- property BodyType : String read FBodyType write FBodyType;
- property BodySubType : String read FBodySubType write FBodySubType;
- property FileName : String read FFileName write FFileName;
- property Description : String read FDescription write FDescription;
- property Encoding: TIdMessageEncoding read FEncoding write FEncoding;
- property ContentTransferEncoding : String read FContentTransferEncoding write FContentTransferEncoding;
- property Size : integer read FSize write FSize;
- property UnparsedEntry : string read FUnparsedEntry write FUnparsedEntry;
- property Boundary : string read FBoundary write FBoundary;
- property ParentPart: integer read FParentPart write FParentPart;
- property ImapPartNumber: string read FImapPartNumber write FImapPartNumber;
- constructor Create(Collection: TCollection); override;
- end;
- type
- {CC3: Added for validating message number}
- EIdNumberInvalid = class(EIdException);
- {CCB: Added for server disconnecting you if idle too long...}
- EIdDisconnectedProbablyIdledOut = class(EIdException);
- TIdImapMessageParts = class(TOwnedCollection)
- protected
- function GetItem(Index: Integer): TIdImapMessagePart;
- procedure SetItem(Index: Integer; const Value: TIdImapMessagePart);
- public
- function Add: TIdImapMessagePart;
- property Items[Index: Integer]: TIdImapMessagePart read GetItem write SetItem; default;
- end;
- {CCD: Added to parse out responses, because the order in which the responses appear
- varies between servers. A typical line that gets parsed into this is:
- * 9 FETCH (UID 1234 FLAGS (\Seen \Deleted))
- }
- TIdIMAPLineStruct = class(TObject)
- protected
- HasStar: Boolean; //Line starts with a '*'
- MessageNumber: string; //Line has a message number (after the *)
- Command: string; //IMAP servers send back the command they are responding to, e.g. FETCH
- UID: string; //Sometimes the UID is echoed back
- Flags: TIdMessageFlagsSet; //Sometimes the FLAGS are echoed back
- Complete: Boolean; //If false, line has no closing bracket (response continues on following line(s))
- ByteCount: integer; //The value in a trailing byte count like {123}, -1 means not present
- IMAPFunction: string; //E.g. FLAGS
- IMAPValue: string; //E.g. '(\Seen \Deleted)'
- end;
- type
- TIdIMAP4Commands =
- ( cmdCAPABILITY,
- cmdNOOP,
- cmdLOGOUT,
- cmdAUTHENTICATE,
- cmdLOGIN,
- cmdSELECT,
- cmdEXAMINE,
- cmdCREATE,
- cmdDELETE,
- cmdRENAME,
- cmdSUBSCRIBE,
- cmdUNSUBSCRIBE,
- cmdLIST,
- cmdLSUB,
- cmdSTATUS,
- cmdAPPEND,
- cmdCHECK,
- cmdCLOSE,
- cmdEXPUNGE,
- cmdSEARCH,
- cmdFETCH,
- cmdSTORE,
- cmdCOPY,
- cmdUID,
- cmdXCmd );
- {CC3: Add csUnexpectedlyDisconnected for when we receive "Connection reset by peer"}
- TIdIMAP4ConnectionState = ( csAny, csNonAuthenticated, csAuthenticated, csSelected , csUnexpectedlyDisconnected );
- {****************************************************************************
- Universal commands CAPABILITY, NOOP, and LOGOUT
- Authenticated state commands SELECT, EXAMINE, CREATE, DELETE, RENAME,
- SUBSCRIBE, UNSUBSCRIBE, LIST, LSUB, STATUS, and APPEND
- Selected state commands CHECK, CLOSE, EXPUNGE, SEARCH, FETCH, STORE, COPY, and UID
- *****************************************************************************}
- TIdIMAP4SearchKey =
- ( skAll, //All messages in the mailbox; the default initial key for ANDing.
- skAnswered, //Messages with the \Answered flag set.
- skBcc, //Messages that contain the specified string in the envelope structure's BCC field.
- skBefore, //Messages whose internal date is earlier than the specified date.
- skBody, //Messages that contain the specified string in the body of the message.
- skCc, //Messages that contain the specified string in the envelope structure's CC field.
- skDeleted, //Messages with the \Deleted flag set.
- skDraft, //Messages with the \Draft flag set.
- skFlagged, //Messages with the \Flagged flag set.
- skFrom, //Messages that contain the specified string in the envelope structure's FROM field.
- skHeader, //Messages that have a header with the specified field-name (as defined in [RFC-822])
- //and that contains the specified string in the [RFC-822] field-body.
- skKeyword, //Messages with the specified keyword set.
- skLarger, //Messages with an [RFC-822] size larger than the specified number of octets.
- skNew, //Messages that have the \Recent flag set but not the \Seen flag.
- //This is functionally equivalent to "(RECENT UNSEEN)".
- skNot, //Messages that do not match the specified search key.
- skOld, //Messages that do not have the \Recent flag set. This is functionally
- //equivalent to "NOT RECENT" (as opposed to "NOT NEW").
- skOn, //Messages whose internal date is within the specified date.
- skOr, //Messages that match either search key.
- skRecent, //Messages that have the \Recent flag set.
- skSeen, //Messages that have the \Seen flag set.
- skSentBefore,//Messages whose [RFC-822] Date: header is earlier than the specified date.
- skSentOn, //Messages whose [RFC-822] Date: header is within the specified date.
- skSentSince, //Messages whose [RFC-822] Date: header is within or later than the specified date.
- skSince, //Messages whose internal date is within or later than the specified date.
- skSmaller, //Messages with an [RFC-822] size smaller than the specified number of octets.
- skSubject, //Messages that contain the specified string in the envelope structure's SUBJECT field.
- skText, //Messages that contain the specified string in the header or body of the message.
- skTo, //Messages that contain the specified string in the envelope structure's TO field.
- skUID, //Messages with unique identifiers corresponding to the specified unique identifier set.
- skUnanswered,//Messages that do not have the \Answered flag set.
- skUndeleted, //Messages that do not have the \Deleted flag set.
- skUndraft, //Messages that do not have the \Draft flag set.
- skUnflagged, //Messages that do not have the \Flagged flag set.
- skUnKeyWord, //Messages that do not have the specified keyword set.
- skUnseen );
- TIdIMAP4SearchKeyArray = array of TIdIMAP4SearchKey;
- TIdIMAP4SearchRec = record
- Date: TDateTime;
- Size: Integer;
- Text: String;
- SearchKey : TIdIMAP4SearchKey;
- end;
- TIdIMAP4SearchRecArray = array of TIdIMAP4SearchRec;
- TIdIMAP4StatusDataItem = ( mdMessages, mdRecent, mdUIDNext, mdUIDValidity, mdUnseen );
- TIdIMAP4StoreDataItem = ( sdReplace, sdReplaceSilent, sdAdd, sdAddSilent, sdRemove, sdRemoveSilent );
- TIdRetrieveOnSelect = ( rsDisabled, rsHeaders, rsMessages );
- TIdAlertEvent = procedure(ASender: TObject; const AAlertMsg: String) of object;
- TIdIMAP4 = class(TIdMessageClient)
- private
- procedure SetMailBox(const Value: TIdMailBox);
- protected
- FCmdCounter : Integer;
- FConnectionState : TIdIMAP4ConnectionState;
- FMailBox : TIdMailBox;
- FMailBoxSeparator: Char;
- FOnAlert: TIdAlertEvent;
- FRetrieveOnSelect: TIdRetrieveOnSelect;
- FMilliSecsToWaitToClearBuffer: integer;
- FMUTF7: TIdMUTF7;
- FOnWorkForPart: TWorkEvent;
- FOnWorkBeginForPart: TWorkBeginEvent;
- FOnWorkEndForPart: TWorkEndEvent;
- FGreetingBanner : String; {CC7: Added because it may help identify the server}
- FHasCapa : Boolean;
- {CC7: FSASLMechanisms and FAuthType added when LoginSASL moved from TIdMessageSASLClient to TIdSASLList...}
- FSASLMechanisms : TIdSASLEntries;
- FAuthType : TIdIMAP4AuthenticationType;
- FCapabilities: TIdStringList;
- FLineStruct: TIdIMAPLineStruct;
- function GetReplyClass:TIdReplyClass; override;
- //The following call FMUTF7 but do exception-handling on invalid strings...
- function DoMUTFEncode(aString : string):string;
- function DoMUTFDecode(aString : string):string;
- function GetCmdCounter: String;
- function GetConnectionStateName: String;
- function GetNewCmdCounter: String;
- property LastCmdCounter: String read GetCmdCounter;
- property NewCmdCounter: String read GetNewCmdCounter;
- { General Functions }
- function ArrayToNumberStr (const AMsgNumList: array of Integer): String;
- function MessageFlagSetToStr (const AFlags: TIdMessageFlagsSet): String;
- //This function is needed because when using the regular DateToStr with dd/MMM/yyyy
- //(which is the IMAP needed convension) may give the month as the local language
- //three letter month instead of the English month needed.
- function DateToIMAPDateStr (const ADate: TDateTime): String;
- procedure StripCRLFs(var AText: string); overload; virtual; //Allow users to optimise
- procedure StripCRLFs(ASourceStream, ADestStream: TStringStream); overload;
- { General Functions }
- { Parser Functions }
- {CCC: new attempt...}
- procedure ParseImapPart(ABodyStructure: string;
- AImapParts: TIdImapMessageParts; AThisImapPart: TIdImapMessagePart; AParentImapPart: TIdImapMessagePart;
- APartNumber: integer);
- procedure ParseMessagePart(ABodyStructure: string;
- AMessageParts: TIdMessageParts; AThisMessagePart: TIdMessagePart; AParentMessagePart: TIdMessagePart;
- APartNumber: integer);
- {CC2: ParseBodyStructureResult added to support individual part retreival...}
- procedure ParseBodyStructureResult(ABodyStructure: string; ATheParts: TIdMessageParts; AImapParts: TIdImapMessageParts);
- {CC3: ParseBodyStructurePart added to support individual part retreival...}
- {CC7: TIdImapSubSection added to ParseBodyStructurePart to support multisection parts...}
- procedure ParseBodyStructurePart(APartString: string; AThePart: TIdMessagePart; AImapPart: TIdImapMessagePart{; AImapSubSection: TIdImapSubSection});
- procedure ParseTheLine(ALine: string; APartsList: TIdStringList);
- procedure ParseIntoParts(APartString: string; AParams: TIdStringList);
- procedure ParseIntoBrackettedQuotedAndUnquotedParts(APartString: string; AParams: TIdStringList; AKeepBrackets: Boolean);
- procedure BreakApartParamsInQuotes(const AParam: string; var AParsedList: TIdStringList);
- function GetNextWord(AParam: string): string;
- function GetNextQuotedParam(AParam: string; ARemoveQuotes: Boolean): string;
- procedure ParseExpungeResult (AMB: TIdMailBox; ACmdResultDetails: TIdStrings);
- procedure ParseListResult (AMBList: TIdStringList; ACmdResultDetails: TIdStrings);
- procedure ParseLSubResult(AMBList: TIdStringList; ACmdResultDetails: TIdStrings);
- {CCA: InternalParseListResult added to resolve NIL mailbox separator and
- rationalise code between ParseLisTresult and ParseLSubResult}
- procedure InternalParseListResult(ACmd: string; AMBList: TIdStringList; ACmdResultDetails: TIdStrings);
- procedure ParseMailBoxAttributeString(AAttributesList: String; var AAttributes: TIdMailBoxAttributesSet);
- procedure ParseMessageFlagString (AFlagsList: String; var AFlags: TIdMessageFlagsSet);
- procedure ParseSelectResult (AMB: TIdMailBox; ACmdResultDetails: TIdStrings);
- procedure ParseStatusResult (AMB: TIdMailBox; ACmdResultDetails: TIdStrings);
- procedure ParseSearchResult (AMB: TIdMailBox; ACmdResultDetails: TIdStrings);
- procedure ParseEnvelopeResult (AMsg: TIdMessage; ACmdResultStr: String);
- function ParseLastCmdResult(ALine: string; AExpectedCommand: string; AExpectedIMAPFunction: array of string): Boolean;
- procedure ParseLastCmdResultButAppendInfo(ALine: string);
- {CC8: Following added to combine the (UID)Retrieve(Peek) functions...}
- function InternalRetrieve(const AMsgNum: Integer; AUseUID: Boolean; AUsePeek: Boolean; ANoDecode: Boolean; AMsg: TIdMessage): Boolean;
- {CC2: Following added for retrieving individual parts of a message...}
- function InternalRetrievePart(const AMsgNum: Integer; const APartNum: {Integer} string;
- AUseUID: Boolean; AUsePeek: Boolean;
- {$IFDEF DOTNET}
- var ABuffer: TIdBytes;
- {$ELSE}
- var ABuffer: PChar;
- {$ENDIF}
- var ABufferLength: Integer; {NOTE: var args cannot have default params}
- ADestFileNameAndPath: string = ''; {Do not Localize}
- AContentTransferEncoding: string = 'text'): Boolean; {Do not Localize}
- function ParseBodyStructureSectionAsEquates(AParam: string): string;
- function ParseBodyStructureSectionAsEquates2(AParam: string): string;
- {CC3: Following added for retrieving the text-only part of a message...}
- function InternalRetrieveText(const AMsgNum: Integer; var AText: string;
- AUseUID: Boolean; AUsePeek: Boolean; AUseFirstPartInsteadOfText: Boolean): Boolean;
- {CC3: Following added for TLS support..}
- function IsCapabilityListed(ACapability: string):Boolean;
- {CC6: Added to support RetrieveEnvelopeRaw...}
- function InternalRetrieveEnvelope(const AMsgNum: Integer; AMsg: TIdMessage; ADestList: TIdStringList): Boolean;
- {CC6: Added to support UIDRetrieveEnvelopeRaw...}
- function UIDInternalRetrieveEnvelope(const AMsgUID: String; AMsg: TIdMessage; ADestList: TIdStringList): Boolean;
- {CCD: For getting the header of a part...}
- function InternalRetrievePartHeader(const AMsgNum: Integer; const APartNum: string; const AUseUID: Boolean; AHeaders: TIdHeaderList): Boolean;
- {CC: ReceiveHeader in IdMessageClient seems to have a very rare bug, maybe it
- is missing the end marker occassionally. Moved up to here to add
- debugging code, plus it can be converted to an IMAP byte-count retrieval
- method if necessary.}
- function ReceiveHeader(AMsg: TIdMessage; const AAltTerm: string = ''): string; override;
- {CC3: Need to validate message numbers (relative and UIDs) and part numbers, because otherwise
- the routines wait for a response that never arrives and so functions never return.
- Also used for validating part numbers.}
- function IsNumberValid(const ANumber: Integer): Boolean;
- function IsUIDValid(const AUID: string): Boolean;
- function IsImapPartNumberValid(const AUID: string): Boolean;
- function IsItDigitsAndOptionallyPeriod(const AStr: string; AAllowPeriod: Boolean): Boolean;
- {CC6: Override IdMessageClient's ReceiveBody due to the responses from some
- servers...}
- procedure ReceiveBody(AMsg: TIdMessage; const ADelim: string = '.'); override; {Do not Localize}
- procedure InitComponent; override;
- public
- { TIdIMAP4 Commands }
- //Requests a listing of capabilities that the server supports.
- function Capability(ASlCapability: TIdStrings): Boolean; overload;
- function FindHowServerCreatesFolders: TIdIMAP4FolderTreatment;
- procedure DoAlert (const AMsg: String);
- property ConnectionState: TIdIMAP4ConnectionState read FConnectionState;
- property MailBox: TIdMailBox read FMailBox write SetMailBox;
- {CC7: Two versions of AppendMsg are provided. The first is the normal one you
- would use. The second allows you to specify an alternative header list which
- will be used in place of AMsg.Headers.
- An email client may need the second type if it sends an email via IdSMTP and wants
- to copy it to a "Sent" IMAP folder. In Indy 9, IdSMTP internally generates and
- transmits the headers but does not keep them, so what you may need to do is to
- subclass IdSMTP, override SendHeader so that the TIdHeaderList is returned (and
- also override both SendMsg and Send to get it back to you), then use the
- second version of AppendMsg to use the returned TIdHeaderList. In Indy 10,
- IdSMTP puts the generated headers in the LastGeneratedHeaders field, so you
- can use the second version of AppendMsg, passing it AMsg.LastGeneratedHeaders as
- the AAlternativeHeaders field. Note that IdSMTP puts both the Headers and
- the ExtraHeaders fields in LastGeneratedHeaders.}
- function AppendMsg (const AMBName: String; AMsg: TIdMessage; const AFlags: TIdMessageFlagsSet = []): Boolean; overload;
- function AppendMsg (const AMBName: String; AMsg: TIdMessage; AAlternativeHeaders: TIdHeaderList; const AFlags: TIdMessageFlagsSet = []): Boolean; overload;
- function AppendMsgNoEncodeFromFile (const AMBName: String; ASourceFile: string; const AFlags: TIdMessageFlagsSet = []): Boolean;
- function AppendMsgNoEncodeFromStream (const AMBName: String; AStream: TStream; const AFlags: TIdMessageFlagsSet = []): Boolean;
- //The following are used for raw (unparsed) messages in a file or stream...
- //Requests a checkpoint of the currently selected mailbox. Does NOTHING on most servers.
- function CheckMailBox: Boolean;
- //Checks if the message was read or not.
- function CheckMsgSeen (const AMsgNum: Integer): Boolean;
- //Method for logging in manually if you didn't login at connect
- procedure Login; virtual;
- //Connects and logins to the IMAP4 account.
- procedure Connect(const AAndLogin: boolean = true); reintroduce; virtual;
- //Closes the current selected mailbox in the account. {Do not Localize}
- function CloseMailBox: Boolean;
- //Creates a new mailbox with the specified name in the account. {Do not Localize}
- function CreateMailBox (const AMBName: String): Boolean;
- //Deletes the specified mailbox from the account. {Do not Localize}
- function DeleteMailBox (const AMBName: String): Boolean;
- //Marks messages for deletion, it will be deleted when the mailbox will be purged.
- function DeleteMsgs(const AMsgNumList: array of Integer): Boolean;
- destructor Destroy; override;
- //Logouts and disconnects from the IMAP account.
- procedure Disconnect; overload;
- //Disconnect with a parameter for raising a Not Connected exception
- procedure Disconnect(AImmediate: Boolean; const ARaiseExceptionIfNotCon : Boolean); reintroduce; overload;
- //Examines the specified mailbox and inserts the results to the TIdMailBox provided. {Do not Localize}
- function ExamineMailBox (const AMBName: String; AMB: TIdMailBox): Boolean;
- //Expunges (deletes the marked files) the current selected mailbox in the account. {Do not Localize}
- function ExpungeMailBox: Boolean;
- //Sends a NOOP (No Operation) to keep the account connection with the server alive.
- procedure KeepAlive;
- //Returns a list of all the child mailboxes (one level down) to the mailbox supplied.
- //This should be used when you fear that there are too many mailboxes and the listing of
- //all of them could be time consuming, so this should be used to retrieve specific mailboxes.
- function ListInferiorMailBoxes (AMailBoxList, AInferiorMailBoxList: TIdStringList): Boolean;
- //Returns a list of all the mailboxes in the user account.
- function ListMailBoxes (AMailBoxList: TIdStringList): Boolean;
- //Returns a list of all the subscribed mailboxes in the user account.
- function ListSubscribedMailBoxes (AMailBoxList: TIdStringList): Boolean;
- //Renames the specified mailbox in the account. {Do not Localize}
- function RenameMailBox (const AOldMBName, ANewMBName: String): Boolean;
- //Searches the current selected mailbox for messages matching the SearchRec and
- //returnes the results to the mailbox SearchResults array.
- function SearchMailBox (const ASearchInfo: array of TIdIMAP4SearchRec): Boolean;
- //Selects the current a mailbox in the account. {Do not Localize}
- function SelectMailBox (const AMBName: String): Boolean;
- //Retrieves the status of the indicated mailbox.
- {CC2: It is pointless calling StatusMailBox with AStatusDataItems set to []
- because you are asking the IMAP server to update none of the status flags.
- Instead, if called with no AStatusDataItems specified, use the standard flags
- returned by SelectMailBox, which allows the user to easily check if the mailbox
- has changed. Overload the functions, since AStatusDataItems cannot be set
- to nil.}
- function StatusMailBox (const AMBName: String; AMB: TIdMailBox): Boolean; overload;
- function StatusMailBox (const AMBName: String; AMB: TIdMailBox; const AStatusDataItems: array of TIdIMAP4StatusDataItem): Boolean; overload;
- //Changes (adds or removes) message flags.
- function StoreFlags (const AMsgNumList: array of Integer;
- const AStoreMethod: TIdIMAP4StoreDataItem; const AFlags: TIdMessageFlagsSet): Boolean;
- //Adds the specified mailbox name to the server's set of "active" or "subscribed" {Do not Localize}
- //mailboxes as returned by the LSUB command.
- function SubscribeMailBox (const AMBName: String): Boolean;
- {CC8: Added CopyMsg, should have always been there...}
- function CopyMsg (const AMsgNum: Integer; const AMBName: String): Boolean;
- //Copies a message from the current selected mailbox to the specified mailbox. {Do not Localize}
- function CopyMsgs (const AMsgNumList: array of Integer; const AMBName: String): Boolean;
- //Retrieves a whole message while marking it read.
- function Retrieve (const AMsgNum: Integer; AMsg: TIdMessage): Boolean;
- //Retrieves a whole message "raw" and saves it to file, while marking it read.
- function RetrieveNoDecodeToFile (const AMsgNum: Integer; ADestFile: string): Boolean;
- function RetrieveNoDecodeToStream (const AMsgNum: Integer; AStream: TStream): Boolean;
- //Retrieves all envelope of the selected mailbox to the specified TIdMessageCollection.
- function RetrieveAllEnvelopes (AMsgList: TIdMessageCollection): Boolean;
- //Retrieves all headers of the selected mailbox to the specified TIdMessageCollection.
- function RetrieveAllHeaders (AMsgList: TIdMessageCollection): Boolean;
- //Retrieves all messages of the selected mailbox to the specified TIdMessageCollection.
- function RetrieveAllMsgs (AMsgList: TIdMessageCollection): Boolean;
- //Retrieves the message envelope, parses it, and discards the envelope.
- function RetrieveEnvelope (const AMsgNum: Integer; AMsg: TIdMessage): Boolean;
- //Retrieves the message envelope into a TIdStringList but does NOT parse it.
- function RetrieveEnvelopeRaw(const AMsgNum: Integer; ADestList: TIdStringList): Boolean;
- //Returnes the message flag values.
- function RetrieveFlags (const AMsgNum: Integer; var AFlags: TIdMessageFlagsSet): Boolean;
- {CC2: Following added for retrieving individual parts of a message...}
- function InternalRetrieveStructure(const AMsgNum: Integer; AMsg: TIdMessage; AParts: TIdImapMessageParts): Boolean;
- //Retrieve only the message structure (this tells you what parts are in the message).
- function RetrieveStructure(const AMsgNum: Integer; AMsg: TIdMessage): Boolean; overload;
- function RetrieveStructure(const AMsgNum: Integer; AParts: TIdImapMessageParts): Boolean; overload;
- {CC2: Following added for retrieving individual parts of a message...}
- {Retrieve a specific individual part of a message where part is an integer (for backward compatibility)...}
- function RetrievePart(const AMsgNum: Integer; const APartNum: Integer;
- {$IFDEF DOTNET}
- var ABuffer: TIdBytes;
- {$ELSE}
- var ABuffer: PChar;
- {$ENDIF}
- var ABufferLength: Integer; AContentTransferEncoding: string = 'text'): Boolean; overload; {Do not Localize}
- {Retrieve a specific individual part of a message where part is an integer or sub-part like '2.3'...}
- function RetrievePart(const AMsgNum: Integer; const APartNum: string;
- {$IFDEF DOTNET}
- var ABuffer: TIdBytes;
- {$ELSE}
- var ABuffer: PChar;
- {$ENDIF}
- var ABufferLength: Integer; AContentTransferEncoding: string = 'text'): Boolean; overload; {Do not Localize}
- {CC2: Following added for retrieving individual parts of a message...}
- {Retrieve a specific individual part of a message where part is an integer (for backward compatibility)...}
- function RetrievePartPeek(const AMsgNum: Integer; const APartNum: Integer;
- {$IFDEF DOTNET}
- var ABuffer: TIdBytes;
- {$ELSE}
- var ABuffer: PChar;
- {$ENDIF}
- var ABufferLength: Integer; AContentTransferEncoding: string = 'text'): Boolean; overload; {Do not Localize}
- {Retrieve a specific individual part of a message where part is an integer or sub-part like '2.3'...}
- function RetrievePartPeek(const AMsgNum: Integer; const APartNum: string;
- {$IFDEF DOTNET}
- var ABuffer: TIdBytes;
- {$ELSE}
- var ABuffer: PChar;
- {$ENDIF}
- var ABufferLength: Integer; AContentTransferEncoding: string = 'text'): Boolean; overload; {Do not Localize}
- {CC2: Following added for retrieving individual parts of a message...}
- {Retrieve a specific individual part of a message where part is an integer (for backward compatibility)...}
- function RetrievePartToFile(const AMsgNum: Integer; const APartNum: Integer;
- ALength: Integer; ADestFileNameAndPath: string; AContentTransferEncoding: string): Boolean; overload;
- {Retrieve a specific individual part of a message where part is an integer or sub-part like '2.3'...}
- function RetrievePartToFile(const AMsgNum: Integer; const APartNum: string;
- ALength: Integer; ADestFileNameAndPath: string; AContentTransferEncoding: string): Boolean; overload;
- {CC2: Following added for retrieving individual parts of a message...}
- {Retrieve a specific individual part of a message where part is an integer (for backward compatibility)...}
- function RetrievePartToFilePeek(const AMsgNum: Integer; const APartNum: Integer;
- ALength: Integer; ADestFileNameAndPath: string; AContentTransferEncoding: string): Boolean; overload;
- {Retrieve a specific individual part of a message where part is an integer or sub-part like '2.3'...}
- function RetrievePartToFilePeek(const AMsgNum: Integer; const APartNum: string;
- ALength: Integer; ADestFileNameAndPath: string; AContentTransferEncoding: string): Boolean; overload;
- {CC3: Following added for retrieving the text-only part of a message...}
- function RetrieveText(const AMsgNum: Integer; var AText: string): Boolean;
- {CC4: An alternative for retrieving the text-only part of a message which
- may give a better response from some IMAP implementations...}
- function RetrieveText2(const AMsgNum: Integer; var AText: string): Boolean;
- {CC3: Following added for retrieving the text-only part of a message...}
- function RetrieveTextPeek(const AMsgNum: Integer; var AText: string): Boolean;
- function RetrieveTextPeek2(const AMsgNum: Integer; var AText: string): Boolean;
- //Retrieves only the message header.
- function RetrieveHeader (const AMsgNum: Integer; AMsg: TIdMessage): Boolean;
- //CCD: Retrieve the header for a particular part...
- function RetrievePartHeader(const AMsgNum: Integer; const APartNum: string…
Large files files are truncated, but you can click here to view the full file