tags:

views:

4468

answers:

8

Do you know if there's a way?

I've used this library to access a pop3 server, but it doesn't work with an exchange server.

Do you know of any other library or piece of code that'll show me how to do it?

I cannot change any settings on the server.

+1  A: 

You need to use the Exchange SDK if POP3 is not enabled in the Exchange Server. Another options is to use WebDAV.

Jose Basilio
A: 

You could use this library: http://www.dimastr.com/redemption/

Christian
That looks to access Outlook - not Exchange. Subtle (but important) difference.
Mark Brackett
Redemption has both a CDO wrapper called RDO and Safe*Item objects that work along side the OOM
76mel
No, it supports Exchange too. You could use ProfMan to build a temporary profile to access an Exchange store
Christian
+1  A: 

Another option is to configure Exchange to enable IMAP4. There exist 3rd party IMAP4 libraries for .NET, e.g. rebex.

Joe
I cannot change any settings on the server
Juan Manuel
+3  A: 

Depends on the Exchange version. WebDAV works with 2000+, but Web Services requires 2007.

Those are probably the easiest to get working. CDO is another option, but it's not supported from C# - so you'll have to go out of proc.

Exchange also has an OLEDB provider, but I've never used it - it is supported from .NET, however.

Mark Brackett
+1  A: 

You could use EWS (Exchange webservices) starting from Exchange 2007. They seem to be always installed and are better supported than Webdav.

You can just import the webservice from your Exchangeserver (Search for an asmx-file in the installation directory). You can download EML-files from your mails and do many more things!

Christian
+10  A: 

If you use Exchange 2007 and have web services enabled, this is pretty easy. I added a 2.0-style classic Web Reference to my VS2008 project, and I can get mail messages like this:

// exchange 2007 lets us use web services to check mailboxes.
using (ExchangeServiceBinding exchangeServer = new ExchangeServiceBinding())
{
    ICredentials creds = new NetworkCredential("user","password");
    exchangeServer.Credentials = creds;
    exchangeServer.Url = "https://myexchangeserver.com/EWS/Exchange.asmx";
    FindItemType findItemRequest = new FindItemType();
    findItemRequest.Traversal = ItemQueryTraversalType.Shallow;

    // define which item properties are returned in the response
    ItemResponseShapeType itemProperties = new ItemResponseShapeType();
    itemProperties.BaseShape = DefaultShapeNamesType.AllProperties;
    findItemRequest.ItemShape = itemProperties;

    // identify which folder to search
    DistinguishedFolderIdType[] folderIDArray = new DistinguishedFolderIdType[1];
    folderIDArray[0] = new DistinguishedFolderIdType();
    folderIDArray[0].Id = DistinguishedFolderIdNameType.inbox;

    // add folders to request
    findItemRequest.ParentFolderIds = folderIDArray;

    // find the messages
    FindItemResponseType findItemResponse = exchangeServer.FindItem(findItemRequest);

    // read returned
    FindItemResponseMessageType folder = (FindItemResponseMessageType)findItemResponse.ResponseMessages.Items[0];
    ArrayOfRealItemsType folderContents = new ArrayOfRealItemsType();
    folderContents = (ArrayOfRealItemsType)folder.RootFolder.Item;
    ItemType[] items = folderContents.Items;

    // if no messages were found, then return null -- we're done
    if (items == null || items.Count() <= 0)
        return null;

    // FindItem never gets "all" the properties, so now that we've found them all, we need to get them all.
    BaseItemIdType[] itemIds = new BaseItemIdType[items.Count()];
    for (int i = 0; i < items.Count(); i++)
        itemIds[i] = items[i].ItemId;

    GetItemType getItemType = new GetItemType();
    getItemType.ItemIds = itemIds;
    getItemType.ItemShape = new ItemResponseShapeType();
    getItemType.ItemShape.BaseShape = DefaultShapeNamesType.AllProperties;
    getItemType.ItemShape.BodyType = BodyTypeResponseType.Text;
    getItemType.ItemShape.BodyTypeSpecified = true;

    GetItemResponseType getItemResponse = exchangeServer.GetItem(getItemType);
    ItemType[] messages = new ItemType[getItemResponse.ResponseMessages.Items.Count()];

    for (int j = 0; j < messages.Count(); j++)
        messages[j] = ((ItemInfoResponseMessageType)getItemResponse.ResponseMessages.Items[j]).Items.Items[0];

    return messages;
}

The "messages" variable will be an array of ItemType objects returned from exchange that have all the properties you'd expect for a mail message (Body, Attachments, etc.). I hope this helps!

Scott Anderson
Great sample! Thanks :-)
Enrico Campidoglio
+3  A: 

I assume your issue is that your exchange server only support NTLM authentication and does not allow plain text authentication? Or you might not be using the proper username convention. For example you might try using the format username@domain where domain is the internal NT domain which might not be the same as your internet domain.

If that is the case then look for a library that supports NTLM.

Steps for testing via telnet

Go to command prompt type: telnet my.server.com 110 you should get a response from your exchange server like this +OK Microsoft Exchange Server 2003 POP3 server version 6.5.7638.1 (my.server.com) ready.

type: CAPA this should return the list of capabilities your exchange server supports. CAPA +OK Capability list follows TOP USER PIPELINING EXPIRE NEVER UIDL SASL NTLM .

Notice that mine does not show PLAIN

Here is a response from an email server that does+OK Dovecot ready. CAPA +OK CAPA TOP UIDL RESP-CODES PIPELINING STLS USER SASL PLAIN .

If your response does not include PLAIN then stop as you need a library that supports SPA

type: user myusername OR type: user [email protected] replacing domain.corp with your domain

You should then receive +OK

Type: pass mypass

You should get a response +OK

type: list

Should get a list of emails. This might help see if your issue is a username format issue.

Jim Scott
+1  A: 

Using EWS directly in managed code (VB.net / C#) is clumsy to say the best.

I've been fumbling around with it for a few days now, and have come to the conclusion that it's better to build my own wrapper classes around the API, making the services usable in a line or two of code, not the page with the current implementation.

Guess what? Microsoft have beaten me to it: Exchange Web Services Managed API's first Release Candidate is available for download here.

Install, register the dll reference (\Program Files\Microsoft\Exchange\Web Services\1.0\Micorosft.Exchange.WebServices.dll), and import the namespace (Microsoft.Exchange.WebServices.Data) and you're ready to roll.

Ryan Barrett