Exchange Development: Finding Rooms and Busy/Free status with Suggestions for Meeting

In this article, let’s develop a sample program to find out the rooms available and suggestions for organizing a meeting. We will use Exchange Server 2010 installed along with some rooms configured in it.


1. To start with, let's create a Console application in Visual studio 2010 by navigating to File->New project. Then, add a Service Reference to the Exchange web service. To do this, right click the application in the Solution Explorer->Add Service Reference. Type the URL of your Exchange Service reference.
 
2. Then, open Program.cs. In the main() function, create an object of the ExchangeService class and pass the ExchangeVersion you are going to use. Here  is Exchange 2010.
 
ExchangeService service =newExchangeService(ExchangeVersion.Exchange2010);
 
3. Set the credentials of the Exchange Server user. Pass the email, password and
domain name.

service.Credentials = new NetworkCredential(EmailID, EmailPassword, DomainName);
 
4. Then, call the AutoDiscoverUrl() method, and pass the email ID in it. This will get
the URL of the Exchange server with the passed email address.

service.AutodiscoverUrl(EmailID);

 
5. Now, to get the Room mailbox information, we need to set the filter to get only the
RoomMailbox recipient details. This is done using the following filter string:
//-RecipientTypeDetails RoomMailbox

string filter = "(&(objectClass=*)(msExchRecipientDisplayType=7))";

 
6. Next, create an object of the DirectorySearcher class and pass in the filter string as a
parameter to it. This will create search in Active Directory.

DirectorySearcher search = new DirectorySearcher(filter);

 
7. Then, create a List<T> of type AttendeeInfo. Let's name it rooms.

List<AttendeeInfo> rooms = new List<AttendeeInfo>();
 
8. Now, call the FindAll() method of the DirectorySearcher class created earlier. This
will search the rooms as we have specified the filter string in it earlier.
Then, also start a foreach loop to traverse the SearchResult.

foreach (SearchResult result in search.FindAll())
{
 
9. Then, in the foreach loop, create an object of ResultPropertyCollection and get the results using result.Properties.
 
ResultPropertyCollection r = result.Properties;
 
10. Now, get each address' details by creating an instance of the DirectoryEntry class. Call the GetdirectoryEntry() method.

// Do work with data returned for each address entry
DirectoryEntry entry =result.GetDirectoryEntry();
 
11. The, add the mail property value to the list of AttendeeInfo created earlier.

rooms.Add(new AttendeeInfo(entry.Properties["mail"].Value.ToString().Trim()));
}
 
12. Now, use this list to find the availability information for the rooms. Here, we will find availability information for all the rooms.
//Create a list of attendees for which to request availability
// information and meeting time suggestions.

List<AttendeeInfo> attendees= rooms;
 
13. Now, create a list of AttendeeInfo which we will use in further steps.

List<AttendeeInfo> attend =new List<AttendeeInfo>();

 
14. Next, start a foreach loop to traverse the list of attendees. In this loop, clear the newly created list of AttendeeInfo and add the email address of the room. This is done through the SmtpAddress property.

foreach (AttendeeInfo inf in attendees)
{
attend.Clear();
attend.Add(inf.SmtpAddress);
 
15. Next, create an instance of the AvailabilityOptions class. Set the MaximumSuggestionsPerDay property to 48. This will generate 48 suggestions per day.
 
AvailabilityOptions options = new AvailabilityOptions();
options.MaximumSuggestionsPerDay = 48;
 
16. Then, create an instance of GetUserAvailabilityResults  and call the GetUserAvailability() method. Also, pass the list of rooms for which we need to find the availability information, the TimeWindow in which the information is needed
and the options object created. Set the AvaialabilityData as FreeBusyAndSuggestions.

GetUserAvailabilityResults results = service.GetUserAvailability(
attend,
new TimeWindow(DateTime.Now,
DateTime.Now.AddDays(2)),
AvailabilityData.FreeBusyAndSuggestions,options);
 
17. Then, for each Attendee Availability information in the results, get the Calendar Event of the attendee availability and output the start time, end time and subject of the meeting.

foreach (AttendeeAvailability
attendeeAvailability in results.AttendeesAvailability)
{
Console.WriteLine();
Console.WriteLine("===========================================================================");
Console.WriteLine();
Console.WriteLine("Room " + attendees[i].SmtpAddress + "Busy Hours");
if(attendeeAvailability.ErrorCode == ServiceError.NoError)
{
foreach(Microsoft.Exchange.WebServices.Data.CalendarEvent calendarEvent in
attendeeAvailability.CalendarEvents)
{
Console.WriteLine("Calendar event");
Console.WriteLine(" Starttime: " + calendarEvent.StartTime.ToString());
Console.WriteLine(" Endtime: " + calendarEvent.EndTime.ToString());
if(calendarEvent.Details != null)
{
Console.WriteLine(" Subject:" + calendarEvent.Details.Subject);
// Output additional properties.
}
}
}
}
 
18. Now, Lets output the suggestions for the room availability. For each suggestion in the results, get the Suggestion class object and output the suggested day, and suggestion quality. Similary, output the Time suggestions for the meeting.

Console.WriteLine("Suggestions:");
Console.WriteLine();
// Output suggested meeting times.
foreach (Microsoft.Exchange.WebServices.Data.Suggestion suggestion in results.Suggestions)
{
Console.WriteLine("Suggested day: " +suggestion.Date.ToString());
Console.WriteLine("Overall quality of the suggested day: " +suggestion.Quality.ToString());
foreach (TimeSuggestion timeSuggestion in suggestion.TimeSuggestions)
{
Console.WriteLine(" Suggested time: " + timeSuggestion.MeetingTime.ToString());
Console.WriteLine(" Suggested time quality: " + timeSuggestion.Quality.ToString());
// Output additonal properties.
}
}
}