Index for the series:
Exchange ActiveSync Building Blocks – Intro
Background reading (not a pre-requisite):
[MS-ASHTTP] – ActiveSync HTTP Protocol – OPTIONS
[MS-ASCMD] – ActiveSync Command Reference – FolderSync
Digging Into The Exchange ActiveSync Protocol
If you followed along with the Autodiscover coding session you have now passed the initial hurdle of locating an ActiveSync-enabled Exchange Server. So how about we try to make a connection with that server and fetch some information from it?
There are three steps you can take in this process, where the last one will also establish a synchronization partnership with Exchange:
– HTTP GET
– HTTP OPTIONS
– HTTP POST
Yes, that’s a very generic description, so let’s describe them further.
This step is technically not required at all, and no harm will be done if you skip it completely. It is however a nice test to perform if you’re building a diagnostic utility, (like I do), or just want to separate sync issues from connectivity issues. A common Exchange admin troubleshooting step when verifying ActiveSync connectivity is to open https://fqdn/Microsoft-Server-ActiveSync in your browser. You’ll hopefully be prompted to provide credentials, and then be greeted with a 501 or 505 error. The purpose of doing so is to verify that Exchange handles your request properly even though you’re not getting any low-level diagnostic output. Doing the same in code is of course entirely feasible to do. I use it to troubleshoot the basic connectivity issues:
– Is the Exchange Server responding to requests?
– Are DNS lookups working, or do you see a different result using the IP address?
– Are you using a trusted SSL certificate? (And if so, is the chain correct?)
– Does your authentication mechanism work properly?
All those basic things really.
Yes, I have chosen to make separate apps for the different methods covered here – not because you wouldn’t be able follow along if I did it all in one app, but to focus on one test at a time.
The code is pretty straightforward too:
Technically this step is not required either, but it comes highly recommended if you want a decent Exchange ActiveSync client. (Both Microsoft and Apple do it in their implementations.) The OPTIONS command should be performed before attempting to sync as it is this step that will tell you things about the Exchange Server; most importantly which version the server happens to be running. I have seen EAS clients skipping this, and just opting for a default of 12.0 (Exchange 2007 RTM.) Even if your client does not implement higher level protocols this is just not a clean way of doing it.
If your client does happen to support all the latest and greatest features of Exchange Server you should not assume that all servers out in the wild are running the service pack that was released a week before your client. If you run an OPTIONS and the server returns 12.1 (Exchange 2007 with Service Pack) you should adjust the behavior of your client accordingly.
Another purpose of this method is that you will be able to handle more complex scenarios cleanly as well. Let’s say you connect to an Exchange 2007 Server initially. The Exchange infrastructure is then upgraded to Exchange 2010, and the mailbox is moved to a new server. The new server informs you of this as you connect after the move (through HTTP 302/451), and you do an Autodiscover to make sure you’re connecting to the correct server. As part of this you also think it might make sense to issue the OPTIONS command once more as well, (hey, it is a new server), and you learn that you’re no longer stuck with the old school stuff. You update your relationship with the server, and “magically” your client can do new things. There might be other obstacles, and things you need to consider to make this work entirely smooth client side, but do keep in it mind. You’re not being held back by the Exchange Server at least.
Made the output windows slightly larger to allow for more text in the result area:
There are of course a few lines of code that have changed as well:
You’ll notice that all the info is returned as headers that we in this case just pipe directly to the output view:
Up until now we’ve been doing preparatory work, but this would be where the actual action starts taking place. If we performed the first step successfully we know that all network level connectivity issues are sorted, and the second step told us what we needed about the Exchange Server we will be establishing a relationship with.
This means we can start building up an initial FolderSync command. This command will tell us things like the localized name of your inbox, your subfolders, calendar name, etc. It does not pull down any contents of these folders, but it will let you learn the folder structure, receive initial security policies, and just as important – let Exchange know who you are.
At this point an entry will be created, (if you don’t run into other issues), in Active Directory for your client (attached to the user account you authenticate with).
This is also where you start talking the ActiveSync language known as AS-WBXML. (Full name ActiveSync WAP Binary XML – I usually just shorten it to WBXML much like we often say English generically and just add US or UK where it’s necessary to be specific.) I will do a walkthrough of WBXML later, so for the time being you can just trust me that the static byte array I define is what you need for this initial FolderSync.
For this test you should ensure that you are not forcing any security policies, or requiring provisionable devices.
Your “Exchange ActiveSync Mailbox Policy” should look roughly like this on the “General” tab.
You’ll be familiar with the look-and-feel of the UI by now:
Let me type out the entire response for you:
This might look like something that comes out of a random text generator, (especially since it’s a liberal mix of Norwegian and English as well as a garbled Scandinavian character), but it tells me I have an Inbox (named “Innboks”), Tasks (“Oppgaver”), and a couple of other item types. And most importantly it confirms that I am able to read out actual mailbox data from an Exchange Server. Which is of course a good thing, and means we would be able to move forward performing an actual synchronization.
Any code to back it up? Why, yes, of course I have (he said in a cocky tone that is bound to backfire later on):
I don’t think there’s much comment to append to the code snippet at the moment. As I said just accept the contents of the WBXML for now. Be aware that I have hard-coded 14.1 (Exchange 2010 SP1) as the ActiveSync version. If you are running some other server version you will need to change this accordingly. (If you set it to 12.0 it’ll still work with newer versions as well mind you. I’m not doing anything specific to any server version here.) Feel free to play around with changing the other variables too if you like.
If all goes well, you should also see a new device in your “inventory” view in Outlook Web Access/App after doing this:
A lot of the info is missing there, but that’s because we haven’t provided Exchange with the necessary details, but we’ll get back to this in a later post like so many other missing pieces of the puzzle
If you have access to ADSI Edit you’ll find it in Active Directory by now as well just like I hinted a few paragraphs earlier:
Feeling dizzy yet? I believe we have covered some ground in this article, and it’s at this point that we’re starting to wrap up the basic stuff, and actually start doing something. Since we haven’t covered any error/exception handling yet you might be stuck at this point though – perhaps your lab environment is less forgiving than mine. I intend to be tackling that in the next post if nothing unforeseen occurs. In the meantime you are of course free to shoot out what kind of error you’re seeing if it fails horribly, and I might be able to help you out.
C# Source – HTTP_GET.cs
C# Source – HTTP_OPTIONS.cs
C# Source – HTTP_POST.cs
Visual Studio Solution – EAS_BB_Part-02_01.zip
Visual Studio Solution – EAS_BB_Part-02_02.zip
Visual Studio Solution – EAS_BB_Part-02_03.zip