public CalendarItem CreateAppointment(HackExchangeContext context, string subject, string description, DateTime startTime, DateTime endTime, Room room, List<string> requiredAttendees) { var url = context.Endpoint; var request = new HttpRequestMessage(HttpMethod.Post, url); var postBodyTemplate = LoadXml("CreateAppointment"); var attendeeTemplate = LoadXml("AttendeeTemplate"); var roomAttendeeBody = string.Format(attendeeTemplate, room.EmailAddress); string requiredAttendeesBody = ""; if (requiredAttendees != null) { var attendeesBuilder = new StringBuilder(); foreach (var attendee in requiredAttendees) { attendeesBuilder.AppendFormat(attendeeTemplate, attendee); attendeesBuilder.AppendLine(); } requiredAttendeesBody = attendeesBuilder.Length > 0 ? attendeesBuilder.ToString() : ""; } var startTimeBody = string.Format("{0:yyyy-MM-ddTHH:mm:ssZ}", startTime.ToUniversalTime()); var endTimeBody = string.Format("{0:yyyy-MM-ddTHH:mm:ssZ}", endTime.ToUniversalTime()); var postBody = string.Format(postBodyTemplate, subject, description, startTimeBody, endTimeBody, room.Name, requiredAttendeesBody, roomAttendeeBody); request.Content = new StringContent(postBody, Encoding.UTF8, "text/xml"); var clientHandler = new HttpClientHandler() { Credentials = context.Credentials }; using (var client = new HttpClient(clientHandler)) { var response = client.SendAsync(request).Result; var responseBody = response.Content.ReadAsStringAsync().Result; var doc = new XPathDocument(new StringReader(responseBody)); var nav = doc.CreateNavigator(); var nsManager = new XmlNamespaceManager(nav.NameTable); nsManager.AddNamespace("m", "http://schemas.microsoft.com/exchange/services/2006/messages"); nsManager.AddNamespace("t", "http://schemas.microsoft.com/exchange/services/2006/types"); CalendarItem calendarItem = null; var calendarItemNode = nav.SelectSingleNode("//t:CalendarItem/t:ItemId", nsManager); if (calendarItemNode != null) { var id = EvaluateXPath(calendarItemNode, nsManager, "@Id"); var changeKey = EvaluateXPath(calendarItemNode, nsManager, "@ChangeKey"); if (id != null && changeKey != null) { calendarItem = new CalendarItem() { Id = id, ChangeKey = changeKey }; } } return calendarItem; } }
public bool CancelAppointment(HackExchangeContext context, CalendarItem appointment) { var url = context.Endpoint; var request = new HttpRequestMessage(HttpMethod.Post, url); var postBodyTemplate = LoadXml("CancelAppointment"); var postBody = string.Format(postBodyTemplate, appointment.Id, appointment.ChangeKey); request.Content = new StringContent(postBody, Encoding.UTF8, "text/xml"); var clientHandler = new HttpClientHandler() { Credentials = context.Credentials }; using (var client = new HttpClient(clientHandler)) { var response = client.SendAsync(request).Result; var responseBody = response.Content.ReadAsStringAsync().Result; var doc = new XPathDocument(new StringReader(responseBody)); var nav = doc.CreateNavigator(); var nsManager = new XmlNamespaceManager(nav.NameTable); nsManager.AddNamespace("m", "http://schemas.microsoft.com/exchange/services/2006/messages"); nsManager.AddNamespace("t", "http://schemas.microsoft.com/exchange/services/2006/types"); var responseClass = EvaluateXPath(nav, nsManager, "//m:DeleteItemResponseMessage/@ResponseClass"); return responseClass == "Success"; } }
public string Login(NetworkCredential credentials, out HackExchangeContext context) { var postBody = "<?xml version=\"1.0\" encoding=\"utf-8\"?> " + "<Autodiscover xmlns=\"http://schemas.microsoft.com/exchange/autodiscover/outlook/requestschema/2006\"> " + "<Request> " + "<EMailAddress>" + credentials.UserName + "</EMailAddress> " + "<AcceptableResponseSchema>http://schemas.microsoft.com/exchange/autodiscover/outlook/responseschema/2006a</AcceptableResponseSchema> " + "</Request> " + "</Autodiscover>"; var url = "https://autodiscover-s.outlook.com/autodiscover/autodiscover.xml"; var request = new HttpRequestMessage(HttpMethod.Post, url); request.Content = new StringContent(postBody, Encoding.UTF8, "text/xml"); var clientHandler = new HttpClientHandler() { Credentials = credentials }; using (var client = new HttpClient(clientHandler)) { var response = client.SendAsync(request).Result; var responseBody = response.Content.ReadAsStringAsync().Result; //var xmlDoc = new XmlDocument(); //xmlDoc.Load(new StringReader(responseBody)); //var nodeList = xmlDoc.GetElementsByTagName("DisplayName"); //if (nodeList.Count > 0) //{ // var element = nodeList[0] as XmlElement; // if (element != null) // { // Console.WriteLine("DisplayName: " + element.InnerText); // } //} //nodeList = xmlDoc.GetElementsByTagName("ASUrl"); //if (nodeList.Count > 0) //{ // var element = nodeList[0] as XmlElement; // if (element != null) // { // Console.WriteLine("ASUrl: " + element.InnerText); // } //} var doc = new XPathDocument(new StringReader(responseBody)); var nav = doc.CreateNavigator(); var nsManager = new XmlNamespaceManager(nav.NameTable); nsManager.AddNamespace("r", "http://schemas.microsoft.com/exchange/autodiscover/outlook/responseschema/2006a"); var value = nav.SelectSingleNode("//r:DisplayName", nsManager); string displayName = null; if (value != null) { Console.WriteLine("DisplayName: " + value.Value); displayName = value.Value; } var urlNode = nav.SelectSingleNode("//r:ASUrl", nsManager); string asUrl = null; if (urlNode != null) { Console.WriteLine("ASUrl: " + urlNode.Value); asUrl = urlNode.Value; } Console.WriteLine("Status: " + response.StatusCode); context = new HackExchangeContext() { Credentials = credentials, Endpoint = asUrl }; return displayName; } }
public IList<Room> GetRooms(HackExchangeContext context) { var url = context.Endpoint; var request = new HttpRequestMessage(HttpMethod.Post, url); var postBody = LoadXml("GetRooms"); request.Content = new StringContent(postBody, Encoding.UTF8, "text/xml"); var clientHandler = new HttpClientHandler() { Credentials = context.Credentials }; using (var client = new HttpClient(clientHandler)) { var response = client.SendAsync(request).Result; var responseBody = response.Content.ReadAsStringAsync().Result; var doc = new XPathDocument(new StringReader(responseBody)); var nav = doc.CreateNavigator(); var nsManager = new XmlNamespaceManager(nav.NameTable); nsManager.AddNamespace("m", "http://schemas.microsoft.com/exchange/services/2006/messages"); nsManager.AddNamespace("t", "http://schemas.microsoft.com/exchange/services/2006/types"); IList<Room> result = new List<Room>(); var roomIterator = nav.Select("//t:Persona[t:PersonaType='Room']", nsManager); foreach (XPathNavigator roomNav in roomIterator) { var displayName = EvaluateXPath(roomNav, nsManager, "./t:DisplayName"); var roomId = EvaluateXPath(roomNav, nsManager, "./t:PersonaId/@Id"); var location = EvaluateXPath(roomNav, nsManager, "./t:OfficeLocations/t:StringAttributedValue/t:Value"); var emailAddress = EvaluateXPath(roomNav, nsManager, "./t:EmailAddress/t:EmailAddress"); Room r = new Room() { Name = displayName, Location = location, Id = roomId, EmailAddress = emailAddress }; result.Add(r); } return result; } }
public RoomAvailability GetRoomAvailability(HackExchangeContext context, string emailAddress, List<string> attendees, int meetingDuration, bool includeSuggestions) { var url = context.Endpoint; var request = new HttpRequestMessage(HttpMethod.Post, url); var postBodyTemplate = LoadXml("GetRoomAvailability"); var mailboxTemplate = LoadXml("MailboxDataTemplate"); var mailboxDataBuilder = new StringBuilder(); mailboxDataBuilder.AppendFormat(mailboxTemplate, emailAddress); if (attendees != null) { foreach (var attendee in attendees) { mailboxDataBuilder.AppendLine(); mailboxDataBuilder.AppendFormat(mailboxTemplate, attendee); } } var mailboxData = mailboxDataBuilder.ToString(); var now = DateTime.Now; var startTime = string.Format("{0:yyyy-MM-ddTHH:mm:ss}", now.Date); var endTime = string.Format("{0:yyyy-MM-ddTHH:mm:ss}", now.AddDays(1).Date); var postBody = string.Format(postBodyTemplate, mailboxData, startTime, endTime, meetingDuration); request.Content = new StringContent(postBody, Encoding.UTF8, "text/xml"); var clientHandler = new HttpClientHandler() { Credentials = context.Credentials }; using (var client = new HttpClient(clientHandler)) { var response = client.SendAsync(request).Result; var responseBody = response.Content.ReadAsStringAsync().Result; var doc = new XPathDocument(new StringReader(responseBody)); var nav = doc.CreateNavigator(); var nsManager = new XmlNamespaceManager(nav.NameTable); nsManager.AddNamespace("m", "http://schemas.microsoft.com/exchange/services/2006/messages"); nsManager.AddNamespace("t", "http://schemas.microsoft.com/exchange/services/2006/types"); var roomBusyPeriods = new List<BusyTimeWindow>(); var attendeesBusyPeriods = new Dictionary<string, IList<BusyTimeWindow>>(); var suggestedTimes = includeSuggestions ? new List<DateTime>() : null; var pos = 0; var attendeeCalendarIterator = nav.Select("//m:FreeBusyView//t:CalendarEventArray", nsManager); foreach (XPathNavigator attendeeCalendarNav in attendeeCalendarIterator) { //pos == 0 means the availability is for the room bool roomAvailability = pos == 0; IList<BusyTimeWindow> busyPeriods; if (roomAvailability) { busyPeriods = roomBusyPeriods; } else { busyPeriods = new List<BusyTimeWindow>(); attendeesBusyPeriods[attendees[pos - 1]] = busyPeriods; } var eventIterator = attendeeCalendarNav.Select("./t:CalendarEvent[t:BusyType='Busy']", nsManager); foreach (XPathNavigator eventNav in eventIterator) { var eventStartTimeStr = EvaluateXPath(eventNav, nsManager, "./t:StartTime"); var eventEndTimeStr = EvaluateXPath(eventNav, nsManager, "./t:EndTime"); if (eventStartTimeStr == null || eventEndTimeStr == null) { continue; } var eventStartTime = DateTime.ParseExact(eventStartTimeStr, "yyyy-MM-ddTHH:mm:ss", CultureInfo.InvariantCulture); var eventEndTime = DateTime.ParseExact(eventEndTimeStr, "yyyy-MM-ddTHH:mm:ss", CultureInfo.InvariantCulture); var owner = EvaluateXPath(eventNav, nsManager, "./t:CalendarEventDetails/t:Subject"); var location = EvaluateXPath(eventNav, nsManager, "./t:CalendarEventDetails/t:Location"); BusyTimeWindow busyWindow = new BusyTimeWindow() { StartTime = eventStartTime, EndTime = eventEndTime, Owner = owner, Location = location }; busyPeriods.Add(busyWindow); } pos++; } if (suggestedTimes != null) { var suggestedTimesIterator = nav.Select("//m:SuggestionsResponse//t:Suggestion", nsManager); foreach (XPathNavigator suggestedTimeNav in suggestedTimesIterator) { var meetingTimeStr = EvaluateXPath(suggestedTimeNav, nsManager, "./t:MeetingTime"); if (meetingTimeStr != null) { var meetingTime = DateTime.ParseExact(meetingTimeStr, "yyyy-MM-ddTHH:mm:ss", CultureInfo.InvariantCulture); suggestedTimes.Add(meetingTime); } } } return new RoomAvailability() { BusyPeriods = roomBusyPeriods, AttendeesBusyPeriods = attendeesBusyPeriods, SuggestedTimes = suggestedTimes }; } }
public CalendarItem GetCalendarFolder(HackExchangeContext context) { var url = context.Endpoint; var request = new HttpRequestMessage(HttpMethod.Post, url); var postBody = LoadXml("GetCalendarFolder"); request.Content = new StringContent(postBody, Encoding.UTF8, "text/xml"); var clientHandler = new HttpClientHandler() { Credentials = context.Credentials }; using (var client = new HttpClient(clientHandler)) { var response = client.SendAsync(request).Result; var responseBody = response.Content.ReadAsStringAsync().Result; var doc = new XPathDocument(new StringReader(responseBody)); var nav = doc.CreateNavigator(); var nsManager = new XmlNamespaceManager(nav.NameTable); nsManager.AddNamespace("m", "http://schemas.microsoft.com/exchange/services/2006/messages"); nsManager.AddNamespace("t", "http://schemas.microsoft.com/exchange/services/2006/types"); CalendarItem calendarFolder = null; var folderIdNode = nav.SelectSingleNode("//t:FolderId", nsManager); if (folderIdNode != null) { var id = EvaluateXPath(folderIdNode, nsManager, "@Id"); var changeKey = EvaluateXPath(folderIdNode, nsManager, "@ChangeKey"); if (id != null && changeKey != null) { calendarFolder = new CalendarItem() { Id = id, ChangeKey = changeKey }; } } return calendarFolder; } }
public IList<CalendarItem> GetAppointments(HackExchangeContext context) { var calendarFolder = GetCalendarFolder(context); var url = context.Endpoint; var request = new HttpRequestMessage(HttpMethod.Post, url); var postBodyTemplate = LoadXml("GetAppointments"); var now = DateTime.Now; var startTimeBody = string.Format("{0:yyyy-MM-ddTHH:mm:ssZ}", now.Date.ToUniversalTime()); var endTimeBody = string.Format("{0:yyyy-MM-ddTHH:mm:ssZ}", now.Date.AddDays(1).ToUniversalTime()); var postBody = string.Format(postBodyTemplate, startTimeBody, endTimeBody, calendarFolder.Id, calendarFolder.ChangeKey); request.Content = new StringContent(postBody, Encoding.UTF8, "text/xml"); var clientHandler = new HttpClientHandler() { Credentials = context.Credentials }; using (var client = new HttpClient(clientHandler)) { var response = client.SendAsync(request).Result; var responseBody = response.Content.ReadAsStringAsync().Result; var doc = new XPathDocument(new StringReader(responseBody)); var nav = doc.CreateNavigator(); var nsManager = new XmlNamespaceManager(nav.NameTable); nsManager.AddNamespace("m", "http://schemas.microsoft.com/exchange/services/2006/messages"); nsManager.AddNamespace("t", "http://schemas.microsoft.com/exchange/services/2006/types"); var calendarItems = new List<CalendarItem>(); var calendarItemsIterator = nav.Select("//t:CalendarItem", nsManager); foreach (XPathNavigator calendarItemNav in calendarItemsIterator) { var id = EvaluateXPath(calendarItemNav, nsManager, "t:ItemId/@Id"); var changeKey = EvaluateXPath(calendarItemNav, nsManager, "t:ItemId/@ChangeKey"); var subject = EvaluateXPath(calendarItemNav, nsManager, "t:Subject"); var location = EvaluateXPath(calendarItemNav, nsManager, "t:Location"); if (id != null && changeKey != null) { var calendarItem = new CalendarItem() { Id = id, ChangeKey = changeKey, Subject = subject, Location = location }; calendarItems.Add(calendarItem); } } return calendarItems; } }
public IHttpActionResult BookRoom(BookRoomParam param) { var service = new HackExchangeService(); HackExchangeContext context = new HackExchangeContext() { Credentials = new NetworkCredential("*****@*****.**", "%baG7cadence"), Endpoint = "https://outlook.office365.com/EWS/Exchange.asmx" }; var rooms = service.GetRooms(context).Where(r => r.Location == "Montevideo, Uruguay" || r.Location == "Montevideo"); RoomAvailability availability = service.GetRoomAvailability(context, "*****@*****.**", null, 60, true); // If there is room available var bookResult = new BookResult() { Booked = true, Room = rooms.First(), Start = DateTime.Now, End = DateTime.Now.AddMinutes(param.Time)}; // If there is not, then it will find a possible slot. var negativeResult = new BookResult() { Booked = false, Room = rooms.First(), Start = DateTime.Now.AddMinutes(10), End = DateTime.Now.AddMinutes(param.Time) }; return Ok(negativeResult); }