Home > Software engineering >  how to connect to outlook calendar using graph Api in Asp.net core web api
how to connect to outlook calendar using graph Api in Asp.net core web api

Time:07-24

I have created asp.net core web api application to connect to Microsoft Outlook calendar and add new event using graph api. I have created Microsoft office 365 E3 business account(trial). I have registered my application in active directory on Azure portal using same account. Set

my authentication class is

    using System.Net.Http;
using System.Net.Http.Headers;
using System.Security;
using System.Threading.Tasks;
using Microsoft.Identity.Client;
using Microsoft.Graph;

namespace Helpers
{
    public class MsalAuthenticationProvider : IAuthenticationProvider
    {
        private static MsalAuthenticationProvider _singleton;
        private IPublicClientApplication _clientApplication;
        private string[] _scopes;
        private string _username;
        private SecureString _password;
        private string _userId;

        private MsalAuthenticationProvider(IPublicClientApplication clientApplication, string[] scopes, string username, SecureString password)
        {
            _clientApplication = clientApplication;
            _scopes = scopes;
            _username = username;
            _password = password;
            _userId = null;
        }

        public static MsalAuthenticationProvider GetInstance(IPublicClientApplication clientApplication, string[] scopes, string username, SecureString password)
        {
            if (_singleton == null)
            {
                _singleton = new MsalAuthenticationProvider(clientApplication, scopes, username, password);
            }

            return _singleton;
        }

        public async Task AuthenticateRequestAsync(HttpRequestMessage request)
        {
            var accessToken = await GetTokenAsync();

            request.Headers.Authorization = new AuthenticationHeaderValue("bearer", accessToken);
        }

        public async Task<string> GetTokenAsync()
        {
            if (!string.IsNullOrEmpty(_userId))
            {
                try
                {
                    var account = await _clientApplication.GetAccountAsync(_userId);

                    if (account != null)
                    {
                        var silentResult = await _clientApplication.AcquireTokenSilent(_scopes, account).ExecuteAsync();
                        return silentResult.AccessToken;
                    }
                }
                catch (MsalUiRequiredException) { }
            }

            var result = await _clientApplication.AcquireTokenByUsernamePassword(_scopes, _username, _password).ExecuteAsync();
            _userId = result.Account.HomeAccountId.Identifier;
            return result.AccessToken;
        }
    }
}

and my controller is

    using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net.Http;
using System.Runtime.Versioning;
using System.Security;
using System.Threading.Tasks;
using Helpers;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Configuration;
using Microsoft.Graph;
using Microsoft.Identity.Client;
using WebAPI_OneDrive.Models;

namespace WebAPI_OneDrive.Controllers
{
    //[Route("api/[controller]")]
    [ApiController]
    public class OutlookController : ControllerBase
    {
        [HttpPost]
        [Route("Outlook/CreateEvent")]
        public async Task<string> CreateEventAsync(/*CredentialsModel model*/)
        {
            CredentialsModel model = new CredentialsModel();

            model.applicationId = "9403804b-f9b6-4bb0-b8dd-2f40b4347ef1";
            model.tenantId = "926349b9-42cb-46c0-bb34-970256de5c41";
            model.userName = "[email protected]";
            model.password = "p@ssw0rd";

            var userName = model.userName;
            var stringPassword = model.password;
            var applicationId = model.applicationId;
            var tenantId = model.tenantId;
            var userPassword = new SecureString();
            foreach (char c in stringPassword)
            {
                userPassword.AppendChar(c);
            }

            var config = LoadAppSettings(applicationId, tenantId);

            var graphClient = GetAuthenticatedGraphClient(config, userName, userPassword);


            //Create Event

            var @event = new Event
            {
                Subject = "Let's go for lunch",
                Body = new ItemBody
                {
                    ContentType = BodyType.Html,
                    Content = "Does noon work for you?"
                },
                Start = new DateTimeTimeZone
                {
                    DateTime = "2022-07-19T12:00:00",
                    TimeZone = "Pacific Standard Time"
                },
                End = new DateTimeTimeZone
                {
                    DateTime = "2022-07-19T14:00:00",
                    TimeZone = "Pacific Standard Time"
                },
                Location = new Location
                {
                    DisplayName = "Harry's Bar"
                },
                Attendees = new List<Attendee>()
    {
        new Attendee
        {
            EmailAddress = new EmailAddress
            {
                Address = "[email protected]",
                Name = "Samantha Booth"
            },
            Type = AttendeeType.Required
        }
    },
                AllowNewTimeProposals = true,
                TransactionId = "7E163156-7762-4BEB-A1C6-729EA81755A7"
            };


            var Event = await graphClient.Me.Calendar.Events
    .Request()
    .AddAsync(@event);
            var EventId = Event.Id;
            return EventId;
        }
        private static IConfigurationRoot LoadAppSettings(string applicationId, string tenantId)
        {
            try
            {
                var config = new ConfigurationBuilder()
                                  .SetBasePath(System.IO.Directory.GetCurrentDirectory())
                                  .AddJsonFile("appsettings.json", false, true)
                                  .Build();
                config["applicationId"] = applicationId;
                config["tenantId"] = tenantId;
                if (string.IsNullOrEmpty(config["applicationId"]) ||
                    string.IsNullOrEmpty(config["tenantId"]))
                {
                    return null;
                }

                return config;
            }
            catch (System.IO.FileNotFoundException)
            {
                return null;
            }
        }

        private static IAuthenticationProvider CreateAuthorizationProvider(IConfigurationRoot config, string userName, SecureString userPassword)
        {
            var clientId = config["applicationId"];
            var authority = $"https://login.microsoftonline.com/{config["tenantId"]}/v2.0";

            List<string> scopes = new List<string>();
            scopes.Add("User.Read");
            scopes.Add("Calendars.Read");
            scopes.Add("Calendars.Read.Shared");
            scopes.Add("Calendars.ReadWrite");
            scopes.Add("Calendars.Read.Shared");
            //scopes.Add("Files.Read");
            //scopes.Add("Files.ReadWrite");
            //scopes.Add("Files.Read.All");
            //scopes.Add("Files.ReadWrite.All");
            //scopes.Add("Files.Read.Selected");
            //scopes.Add("Files.ReadWrite.Selected");
            //scopes.Add("Files.ReadWrite.AppFolder");
            var cca = PublicClientApplicationBuilder.Create(clientId)
                                                    .WithAuthority(authority)
                                                    .Build();
            return MsalAuthenticationProvider.GetInstance(cca, scopes.ToArray(), userName, userPassword);
        }

        private static GraphServiceClient GetAuthenticatedGraphClient(IConfigurationRoot config, string userName, SecureString userPassword)
        {
            var authenticationProvider = CreateAuthorizationProvider(config, userName, userPassword);
            var graphClient = new GraphServiceClient(authenticationProvider);
            return graphClient;
        }



        //Model

        public class CredentialsModel
        {
            ///credentials
            public string password { get; set; }
            public string userName { get; set; }
            public string applicationId { get; set; }
            public string tenantId { get; set; }
        }
    }
}

when I call Outlook/CreateEvent I am getting the following error enter image description here

Please guide me how to fix this error, thanks in advance enter image description here

CodePudding user response:

To resolve this issue, try to grant Application permission as below and and grant admin consent:

enter image description here

After adding application permission try to get a bearer token as below

enter image description here

Please check this reference List events - Microsoft Graph v1.0 | Microsoft Docs as per document Finally, I am getting list of calendar events successfully:

enter image description here

  • Related