private async Task <Subscription> CreateSubscription(string userId, string tenantId, string clientState, GraphServiceClient graphClient) { string encryptionCertificate = subscriptionOptions.Value.IncludeResourceData ? await keyVaultManager.GetEncryptionCertificate().ConfigureAwait(false) : null; string encryptionCertificateId = subscriptionOptions.Value.IncludeResourceData ? await keyVaultManager.GetEncryptionCertificateId().ConfigureAwait(false) : null; var newSubscription = await graphClient.Subscriptions.Request().AddAsync(new Subscription { Resource = subscriptionOptions.Value.Resource, ChangeType = subscriptionOptions.Value.ChangeType, NotificationUrl = subscriptionOptions.Value.NotificationUrl, ClientState = clientState, ExpirationDateTime = DateTime.UtcNow + new TimeSpan(0, 0, 15, 0), // 4230 minutes is the current max lifetime, shorter duration useful for testing EncryptionCertificate = encryptionCertificate, EncryptionCertificateId = encryptionCertificateId, IncludeResourceData = subscriptionOptions.Value.IncludeResourceData }); // This sample temporarily stores the subscription data, but production apps will likely use some method of persistent storage. // This sample stores the client state to validate the subscription, the tenant ID to reuse tokens, and the user ID to filter // messages to display by user. subscriptionStore.SaveSubscriptionInfo(Guid.Parse(newSubscription.Id), newSubscription.ClientState, userId, tenantId); return(newSubscription); }
public async Task <IActionResult> Create() { string userId = User.FindFirst("http://schemas.microsoft.com/identity/claims/objectidentifier")?.Value; string tenantId = User.FindFirst("http://schemas.microsoft.com/identity/claims/tenantid")?.Value; string clientState = Guid.NewGuid().ToString(); // Initialize the GraphServiceClient. var graphClient = await GraphServiceClientFactory.GetAuthenticatedGraphClient(async() => { string result = await tokenAcquisition.GetAccessTokenOnBehalfOfUser( HttpContext, new[] { Infrastructure.Constants.ScopeMailRead }); return(result); }); Subscription newSubscription = new Subscription(); try { // Create a subscription. // The `Resource` property targets the `users/{user-id}` or `users/{user-principal-name}` path (not `me`) when using application permissions. // The NotificationUrl requires the `https` protocol and supports custom query parameters. newSubscription = await graphClient.Subscriptions.Request().AddAsync(new Subscription { Resource = $"users/{userId}/mailFolders('Inbox')/messages", ChangeType = "created", NotificationUrl = appSettings.NotificationUrl, ClientState = clientState, //ExpirationDateTime = DateTime.UtcNow + new TimeSpan(0, 0, 4230, 0) // current maximum lifespan for messages ExpirationDateTime = DateTime.UtcNow + new TimeSpan(0, 0, 15, 0) // shorter duration useful for testing }); // Verify client state, then store the subscription ID and client state to validate incoming notifications. if (newSubscription.ClientState == clientState) { // This sample temporarily stores the subscription data, but production apps will likely use some method of persistent storage. // This sample stores the client state to validate the subscription, the tenant ID to reuse tokens, and the user ID to filter // messages to display by user. subscriptionStore.SaveSubscriptionInfo(newSubscription.Id, newSubscription.ClientState, userId, tenantId); } else { ViewBag.Message = "Warning! Mismatched client state."; } } catch (Exception e) { // If a tenant admin hasn't granted consent, this operation returns an Unauthorized error. // This sample caches the initial unauthorized token, so you'll need to start a new browser session. ViewBag.Message = BuildErrorMessage(e); return(View("Error")); } return(View("Subscription", newSubscription)); }