0

I'm using asp.net MVC with Owin middleware to integrate with Azure B2C using authorization code flow.

I need to somehow retain the returnUrl so that upon successful login, user is redirected to requested page per returnURL.

I've tried below but SecurityTokenValidatedNotification.ProtocolMessage.State is NULL on OnSecurityTokenValidated notification.

enter image description here

  private Task OnRedirectToIdentityProvider(RedirectToIdentityProviderNotification<OpenIdConnectMessage, OpenIdConnectAuthenticationOptions> notification)
    {
        // only modify requests to the authorization endpoint
        if (notification.ProtocolMessage.RequestType == OpenIdConnectRequestType.Authentication)
        {
            var stateQueryString = notification.ProtocolMessage.State.Split('=');
            var protectedState = stateQueryString[1];
            var state = notification.Options.StateDataFormat.Unprotect(protectedState);
            state.Dictionary.Add("mycustomparameter", "myvalue");
            notification.ProtocolMessage.State = stateQueryString[0] + "=" + notification.Options.StateDataFormat.Protect(state);
        }

        return Task.FromResult(0);
    }
private async Task OnAuthorizationCodeReceived(AuthorizationCodeReceivedNotification nofication)
    {
        // only when authorization code is being swapped for tokens
        if (nofication.TokenEndpointRequest?.GrantType == OpenIdConnectGrantTypes.AuthorizationCode)
        {
            
            var authority = "xxx";
            try
            {
                var confidentialClient = ConfidentialClientApplicationBuilder.Create(ConfigurationManager.AppSettings["ClientId"].ToString())
                .WithClientSecret("xxxx")
                .WithB2CAuthority(authority)
                .WithRedirectUri(ConfigurationManager.AppSettings["redirectUri"].ToString())
                .Build();

                var result = await confidentialClient.AcquireTokenByAuthorizationCode(new[] { string.Format("{0} {1}",clientId,OpenIdConnectScope.OfflineAccess) }, code)
                .WithSpaAuthorizationCode()
                .WithPkceCodeVerifier("ff38b3685b613c1d461ac0c5624baddf3d4243cf0d61f135abfa164c")
                .ExecuteAsync();

               
               
                nofication.HandleCodeRedemption(result.AccessToken, result.IdToken);

            }
            catch (Exception ex)
            {
               // Log.Error("Azure B2C Authorization Code Received Method. " + ex, nameof(bla));
                throw ex;
            }
        }



 private Task OnSecurityTokenValidated(SecurityTokenValidatedNotification<OpenIdConnectMessage, OpenIdConnectAuthenticationOptions> notification)
    {
        string mycustomparameter;
        //THIS LINE THROWS NULL EXCEPTION GIVEN ProtocolMessage.State is NULL
        var protectedState = notification.ProtocolMessage.State.Split('=')[1];
        var state = notification.Options.StateDataFormat.Unprotect(protectedState);
        state.Dictionary.TryGetValue("mycustomparameter", out mycustomparameter);
     
        return Task.CompletedTask;

    }

Observations:

I can only get ProtocolMessage.State value if I use ResponseType idtoken or CodeIdToken

Any idea on how to pass returnUrl to azure b2c and get it back when using authorization code flow with OWIN.

Nil Pun
  • 17,035
  • 39
  • 172
  • 294

0 Answers0