I'm a big believer in integration of pretty much everything. Not that big on mash ups (as most of them are terrible) but I believe that information should be easily used in various systems. That's part of the reason that I like Microsoft products now (during the 90s, I was on the other end of the spectrum though so I'm happy with the changes they've been making). I especially like Exchange because it is extremely easy to pull information from it for your own purposes.
In my instance, I had to create a personalized calendar that pulled information from exchange and displayed it on an intranet page. With the help of WebDAV, it took about 10 minutes to write (and since people only come here for the code, I figured I'd share):
public static List<VCalendar> GetCalendarItems(string UserName, string Password, string Directory,string Server,DateTime StartDate,DateTime EndDate)
{
try
{
List<VCalendar> ReturnArray = new List<VCalendar>();
NetworkCredential credentials = new NetworkCredential(UserName, Password);
string uri = string.Format("http://{0}/exchange/{1}/calendar/", Server, Directory);
string Query = "<?xml version=\"1.0\"?>"
+ "<g:searchrequest xmlns:g=\"DAV:\">"
+ "<g:sql>SELECT \"urn:schemas:calendar:location\", \"urn:schemas:httpmail:subject\", "
+ "\"urn:schemas:httpmail:htmldescription\", "
+ "\"urn:schemas:calendar:dtstart\", \"urn:schemas:calendar:dtend\", "
+ "FROM Scope('SHALLOW TRAVERSAL OF \"" + uri + "\"') "
+ "WHERE \"urn:schemas:calendar:dtstart\" >= '" + StartDate.ToString("yyyy/MM/dd hh:mm:ss") + "' "
+ "AND \"urn:schemas:calendar:dtstart\" <= '" + EndDate.ToString("yyyy/MM/dd hh:mm:ss") + "' "
+ "ORDER BY \"urn:schemas:calendar:dtstart\" ASC"
+ "</g:sql></g:searchrequest>";
byte[] contents = System.Text.Encoding.UTF8.GetBytes(Query);
HttpWebRequest request = HttpWebRequest.Create(uri) as HttpWebRequest;
request.Credentials = credentials;
request.Method = "SEARCH";
request.ContentLength = contents.Length;
request.ContentType = "text/xml";
using (System.IO.Stream requestStream = request.GetRequestStream())
requestStream.Write(contents, 0, contents.Length);
using (HttpWebResponse response = request.GetResponse() as HttpWebResponse)
{
using (System.IO.Stream responseStream = response.GetResponseStream())
{
XmlDocument document = new XmlDocument();
document.Load(responseStream);
foreach (XmlElement element in document.GetElementsByTagName("a:prop"))
{
VCalendar Cal = new VCalendar();
if (element["e:htmldescription"] != null)
{
Cal.Description = element["e:htmldescription"].InnerText;
}
if (element["e:subject"] != null)
{
Cal.Subject = element["e:subject"].InnerText;
}
if (element["d:location"] != null)
{
Cal.Location = element["d:location"].InnerText;
}
if (element["d:dtstart"] != null)
{
Cal.StartTime = DateTime.Parse(element["d:dtstart"].InnerText);
}
if (element["d:dtend"] != null)
{
Cal.EndTime = DateTime.Parse(element["d:dtend"].InnerText);
}
ReturnArray.Add(Cal);
}
}
}
return ReturnArray;
}
catch
{
return new List<VCalendar>();
}
}
So let's talk about the code a bit. First off, it's using my VCalendar code from my utility library. Well actually it's using a slightly different version that contains a GethCalendar function. I'll talk about hCalendar items in a different post though... So beyond that, you'll notice that there is a large section that sets up the Query string object. That's the actual WebDAV query. It's very similar to SQL but you call fields based on the schemas that were set up (I'm using the urn:schemas:calendar schema the most in this bit of code). We also ask it to only give us items within the start and end dates (you'll notice I use > and <. The reason for this is pretty simple... It's XML that we're sending. XML+ > or < = bad...).
After the query itself we simply set up an HttpWebRequest object with the proper user name/password, content (in bytes), etc. We make the call to the exchange server and it returns to us a nice big chunk of XML in return. If you want to look through the structure of what it returns, go ahead (it's very basic). But the items themselves are located within a:prop objects. So we just get the list of those items and iterate through grabbing the information that we want. That's all there is to the code really. Anyway, I hope this helps someone out. So give it a try, leave feedback, and happy coding.
d879c757-9fe4-4561-b7c7-4283da707cfb|2|2.5