This sample project shows how to load events (appointments) for Microsoft Exchange Server and display them in an ASP.NET web application using DayPilot ASP.NET event calendar. It supports drag and drop operations for event creating and moving. Changes are stored in the Exchange Server.
Features
- Accessing Microsoft Exchange Server 2007+ (including hosted Exchange and Office 365)
- Uses Exchange Web Services Managed API
- C# and VB.NET source code
- Includes open-source DayPilot Lite for ASP.NET WebForms
- Loading appointments
- Updating appointments
- Creating appointments
- Sample Visual Studio 2017 solution available for download
License
- The source code of this sample project is licensed under Apache License 2.0.
- DayPilot Lite for ASP.NET WebForms (open-source version) is licensed under Apache License 2.0.
DayPilot Installation
You can install DayPilot Lite for ASP.NET WebForms (open-source version) from NuGet:
Another option is to download the DayPilot package and add a reference to DayPilot.dll.
Microsoft EWS Managed API Installation
You can install Microsoft Exchange WebSerices Managed API from NuGet:
Since 2014 Microsoft EWS Managed API is open-source (MIT license). You can download the source code at GitHub.
- You can use EWS to connect to Microsoft Exchange Server 2007 or later.
- It works with Office 365 mail accounts as well.
Loading Appointments from Exchange Server
The following code loads appointments for the current week from the default calendar of the specified user
C#
// Exchange connection ExchangeService service = new ExchangeService(ExchangeVersion.Exchange2010); service.Credentials = new WebCredentials("user@yourcompany.com", "password"); // replace with proper username and password service.Url = new Uri("https://outlook.office365.com/ews/exchange.asmx"); // Office 365 Exchange API URL (replace it with a local server URL if you are using a local Exchange installation) // this week DateTime startDate = DayPilot.Utils.Week.FirstDayOfWeek(); DateTime endDate = startDate.AddDays(7); // load the default calendar CalendarFolder calendar = CalendarFolder.Bind(Service, WellKnownFolderName.Calendar, new PropertySet()); // load events CalendarView cView = new CalendarView(startDate, endDate, 50); cView.PropertySet = new PropertySet(AppointmentSchema.Subject, AppointmentSchema.Start, AppointmentSchema.End, AppointmentSchema.Id); FindItemsResults<Appointment> appointments = calendar.FindAppointments(cView);
VB
Dim svc As New ExchangeService(ExchangeVersion.Exchange2010) svc.Credentials = New WebCredentials("user@yourcompany.com", "password") svc.Url = New Uri("https://outlook.office365.com/ews/exchange.asmx") Dim startDate As Date = DayPilot.Utils.Week.FirstDayOfWeek() Dim endDate As Date = startDate.AddDays(7) Dim calendar As CalendarFolder = CalendarFolder.Bind(svc, WellKnownFolderName.Calendar, New PropertySet()) Dim cView As New CalendarView(startDate, endDate, 50) cView.PropertySet = New PropertySet(AppointmentSchema.Subject, AppointmentSchema.Start, AppointmentSchema.End, AppointmentSchema.Id) Dim appointments As FindItemsResults(Of Appointment) = calendar.FindAppointments(cView)
Displaying Exchange Appointments in DayPilot Event Calendar
You can assign the appointments variable directly to DayPilotCalendar.DataSource property to load it:
C#
// assign appointments DayPilotCalendar1.DataSource = appointments; // map item properties DayPilotCalendar1.DataStartField = "Start"; DayPilotCalendar1.DataEndField = "End"; DayPilotCalendar1.DataIdField = "Id"; DayPilotCalendar1.DataTextField = "Subject"; // load and display appointments in DayPilot Calendar DayPilotCalendar1.DataBind();
VB
' assign appointments DayPilotCalendar1.DataSource = appointments ' map item properties DayPilotCalendar1.DataStartField = "Start" DayPilotCalendar1.DataEndField = "End" DayPilotCalendar1.DataIdField = "Id" DayPilotCalendar1.DataTextField = "Subject" ' load and display appointments in DayPilot Calendar DayPilotCalendar1.DataBind()
Loading a Custom Exchange Calendar
You can also load a custom calendar instead of the default one (WellKnownFolderName.Calendar).
C#
// Exchange connection ExchangeService service = new ExchangeService(ExchangeVersion.Exchange2010); service.Credentials = new WebCredentials("user@yourcompany.com", "password"); // replace with proper username and password service.Url = new Uri("https://outlook.office365.com/ews/exchange.asmx"); // Office 365 Exchange API URL (replace it with a local server URL if you are using a local Exchange installation) // this week DateTime startDate = DayPilot.Utils.Week.FirstDayOfWeek(); DateTime endDate = startDate.AddDays(7); // load a calendar by name string name = "Testing Calendar"; FolderView view = new FolderView(100); view.PropertySet = new PropertySet(BasePropertySet.IdOnly); view.PropertySet.Add(FolderSchema.DisplayName); view.Traversal = FolderTraversal.Deep; SearchFilter sfSearchFilter = new SearchFilter.IsEqualTo(FolderSchema.FolderClass, "IPF.Appointment"); FindFoldersResults findFolderResults = service.FindFolders(WellKnownFolderName.Root, sfSearchFilter, view); CalendarFolder calendar = findFolderResults.Where(f => f.DisplayName == name).Cast<CalendarFolder>().FirstOrDefault(); // load events CalendarView cView = new CalendarView(startDate, endDate, 50); cView.PropertySet = new PropertySet(AppointmentSchema.Subject, AppointmentSchema.Start, AppointmentSchema.End, AppointmentSchema.Id); FindItemsResults<Appointment> appointments = calendar.FindAppointments(cView);
VB
Dim svc As New ExchangeService(ExchangeVersion.Exchange2010) svc.Credentials = New WebCredentials("user@yourcompany.com", "password") svc.Url = New Uri("https://outlook.office365.com/ews/exchange.asmx") Dim startDate As Date = DayPilot.Utils.Week.FirstDayOfWeek() Dim endDate As Date = startDate.AddDays(7) Dim name As String = "Testing Calendar" Dim view As New FolderView(100) view.PropertySet = New PropertySet(BasePropertySet.IdOnly) view.PropertySet.Add(FolderSchema.DisplayName) view.Traversal = FolderTraversal.Deep Dim sfSearchFilter As SearchFilter = New SearchFilter.IsEqualTo(FolderSchema.FolderClass, "IPF.Appointment") Dim findFolderResults As FindFoldersResults = svc.FindFolders(WellKnownFolderName.Root, sfSearchFilter, view) Dim calendar As CalendarFolder = findFolderResults.Where(Function(f) f.DisplayName = name).Cast(Of CalendarFolder)().FirstOrDefault() Dim cView As New CalendarView(startDate, endDate, 50) cView.PropertySet = New PropertySet(AppointmentSchema.Subject, AppointmentSchema.Start, AppointmentSchema.End, AppointmentSchema.Id) Dim appointments As FindItemsResults(Of Appointment) = calendar.FindAppointments(cView)
Full Calendar Loading Page
Default.aspx
<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="Default.aspx.cs" Inherits="TestExchange.Default" %> <%@ Register Assembly="DayPilot" Namespace="DayPilot.Web.Ui" TagPrefix="DayPilot" %> <!DOCTYPE html> <html> <head runat="server"> <title></title> </head> <body> <form id="form1" runat="server"> <div> <DayPilot:DayPilotCalendar runat="server" id="DayPilotCalendar1"></DayPilot:DayPilotCalendar> </div> </form> </body> </html>
Default.aspx.cs
using System; using System.Linq; using DayPilot.Web.Ui.Enums.Calendar; using DayPilot.Web.Ui.Events; using Microsoft.Exchange.WebServices.Data; namespace TutorialCS { public partial class Default : System.Web.UI.Page { protected void Page_Load(object sender, EventArgs e) { LoadAppointments(); } private ExchangeService Service { get { ExchangeService service = new ExchangeService(ExchangeVersion.Exchange2010); service.Credentials = new WebCredentials("user@yourcompany.com", "password"); service.Url = new Uri("https://outlook.office365.com/ews/exchange.asmx"); return service; } } private CalendarFolder FindDefaultCalendarFolder() { return CalendarFolder.Bind(Service, WellKnownFolderName.Calendar, new PropertySet()); } private CalendarFolder FindNamedCalendarFolder(string name) { FolderView view = new FolderView(100); view.PropertySet = new PropertySet(BasePropertySet.IdOnly); view.PropertySet.Add(FolderSchema.DisplayName); view.Traversal = FolderTraversal.Deep; SearchFilter sfSearchFilter = new SearchFilter.IsEqualTo(FolderSchema.FolderClass, "IPF.Appointment"); FindFoldersResults findFolderResults = Service.FindFolders(WellKnownFolderName.Root, sfSearchFilter, view); return findFolderResults.Where(f => f.DisplayName == name).Cast<CalendarFolder>().FirstOrDefault(); } private void LoadAppointments() { DateTime startDate = DayPilot.Utils.Week.FirstDayOfWeek(); DateTime endDate = startDate.AddDays(7); CalendarFolder calendar = FindNamedCalendarFolder("Testing Calendar"); // or FindDefaultCalendarFolder() CalendarView cView = new CalendarView(startDate, endDate, 50); cView.PropertySet = new PropertySet(AppointmentSchema.Subject, AppointmentSchema.Start, AppointmentSchema.End, AppointmentSchema.Id); FindItemsResults<Appointment> appointments = calendar.FindAppointments(cView); DayPilotCalendar1.ViewType = ViewTypeEnum.Week; DayPilotCalendar1.DataStartField = "Start"; DayPilotCalendar1.DataEndField = "End"; DayPilotCalendar1.DataIdField = "Id"; DayPilotCalendar1.DataTextField = "Subject"; DayPilotCalendar1.DataSource = appointments; DayPilotCalendar1.DataBind(); DayPilotCalendar1.Update(); } } }
Default.aspx.vb
Imports System Imports System.Linq Imports DayPilot.Web.Ui.Enums.Calendar Imports DayPilot.Web.Ui.Events Imports Microsoft.Exchange.WebServices.Data Namespace TutorialVB Partial Public Class [Default] Inherits System.Web.UI.Page Protected Sub Page_Load(ByVal sender As Object, ByVal e As EventArgs) LoadAppointments() End Sub Private ReadOnly Property Service() As ExchangeService Get Dim svc As New ExchangeService(ExchangeVersion.Exchange2010) svc.Credentials = New WebCredentials("user@yourcompany.com", "password") svc.Url = New Uri("https://outlook.office365.com/ews/exchange.asmx") Return svc End Get End Property Private Function FindDefaultCalendarFolder() As CalendarFolder Return CalendarFolder.Bind(Service, WellKnownFolderName.Calendar, New PropertySet()) End Function Private Function FindNamedCalendarFolder(ByVal name As String) As CalendarFolder Dim view As New FolderView(100) view.PropertySet = New PropertySet(BasePropertySet.IdOnly) view.PropertySet.Add(FolderSchema.DisplayName) view.Traversal = FolderTraversal.Deep Dim sfSearchFilter As SearchFilter = New SearchFilter.IsEqualTo(FolderSchema.FolderClass, "IPF.Appointment") Dim findFolderResults As FindFoldersResults = Service.FindFolders(WellKnownFolderName.Root, sfSearchFilter, view) Return findFolderResults.Where(Function(f) f.DisplayName = name).Cast(Of CalendarFolder)().FirstOrDefault() End Function Private Sub LoadAppointments() Dim startDate As Date = DayPilot.Utils.Week.FirstDayOfWeek() Dim endDate As Date = startDate.AddDays(7) Dim calendar As CalendarFolder = FindNamedCalendarFolder("Testing Calendar") ' or FindDefaultCalendarFolder() Dim cView As New CalendarView(startDate, endDate, 50) cView.PropertySet = New PropertySet(AppointmentSchema.Subject, AppointmentSchema.Start, AppointmentSchema.End, AppointmentSchema.Id) Dim appointments As FindItemsResults(Of Appointment) = calendar.FindAppointments(cView) DayPilotCalendar1.ViewType = ViewTypeEnum.Week DayPilotCalendar1.DataStartField = "Start" DayPilotCalendar1.DataEndField = "End" DayPilotCalendar1.DataIdField = "Id" DayPilotCalendar1.DataTextField = "Subject" DayPilotCalendar1.DataSource = appointments DayPilotCalendar1.DataBind() DayPilotCalendar1.Update() End Sub End Class End Namespace
Creating New Appointments in Exchange Server using EWS
Now we will let users create a new event using drag and drop.
The new appointment will be stored in our Exchange Server account.
Default.aspx
<DayPilot:DayPilotCalendar runat="server" id="DayPilotCalendar1" ... TimeRangeSelectedHandling="CallBack" OnTimeRangeSelected="DayPilotCalendar1_OnTimeRangeSelected" > </DayPilot:DayPilotCalendar>
Default.aspx.cs
// ... protected void DayPilotCalendar1_OnTimeRangeSelected(object sender, TimeRangeSelectedEventArgs e) { Appointment appointment = new Appointment(Service); appointment.Subject = "New Event"; appointment.Start = e.Start; appointment.End = e.End; CalendarFolder folder = FindNamedCalendarFolder("Testing Calendar"); appointment.Save(folder.Id, SendInvitationsMode.SendToNone); LoadAppointments(); }
Default.aspx.vb
' ... Protected Sub DayPilotCalendar1_OnTimeRangeSelected(ByVal sender As Object, ByVal e As TimeRangeSelectedEventArgs) Dim appointment As New Appointment(Service) appointment.Subject = "New Event" appointment.Start = e.Start appointment.End = e.End Dim folder As CalendarFolder = FindNamedCalendarFolder("Testing Calendar") appointment.Save(folder.Id, SendInvitationsMode.SendToNone) LoadAppointments() End Sub
Updating Appointments in Exchange Server using EWS
We will also implement drag and drop event moving and update the event record in the Exchange Server.
Default.aspx
<DayPilot:DayPilotCalendar runat="server" id="DayPilotCalendar1" ... EventMoveHandling = "CallBack" OnEventMove="DayPilotCalendar1_OnEventMove" > </DayPilot:DayPilotCalendar>
Default.aspx.cs
protected void DayPilotCalendar1_OnEventMove(object sender, EventMoveEventArgs e) { Appointment appointment = Appointment.Bind(Service, new ItemId(e.Id)); appointment.Start = e.NewStart; appointment.End = e.NewEnd; appointment.StartTimeZone = TimeZoneInfo.Local; appointment.EndTimeZone = TimeZoneInfo.Local; appointment.Update(ConflictResolutionMode.AlwaysOverwrite); LoadAppointments(); }
Default.aspx.vb
Protected Sub DayPilotCalendar1_OnEventMove(ByVal sender As Object, ByVal e As EventMoveEventArgs) Dim appointment As Appointment = Microsoft.Exchange.WebServices.Data.Appointment.Bind(Service, New ItemId(e.Id)) appointment.Start = e.NewStart appointment.End = e.NewEnd appointment.StartTimeZone = TimeZoneInfo.Local appointment.EndTimeZone = TimeZoneInfo.Local appointment.Update(ConflictResolutionMode.AlwaysOverwrite) LoadAppointments() End Sub