Errore Microsoft B2C Azure Demo non autorizzato

Errore Microsoft B2C Azure Demo non autorizzato

La soluzione per Microsoft B2C Azure Demo Not Authorized Error
è indicata di seguito:

Sto cercando di imparare ASP.Net con il flusso di accesso/registrazione di Azure AD B2C. Sto eseguendo la demo qui:

https://docs.microsoft.com/en-us/azure/active-directory-b2c/tutorial-web-api-dotnet?tabs=app-reg-ga

Il codice C# per la demo può essere scaricato da https://github.com/Azure-Samples/active-directory-b2c-dotnet-webapp-and-webapi/archive/master.zip

Ho completato la demo dall'inizio e ho completato tutti i prerequisiti.

Sono arrivato al punto in cui ho eseguito l'accesso correttamente e quando faccio clic sul collegamento Elenco attività durante il debug dell'applicazione, viene visualizzato un errore Utente non autorizzato (404).

Mi scuso in anticipo se non spiego cosa penso di vedere molto bene, poiché sono molto nuovo in Azure e nella programmazione web. Sono più a mio agio con le applicazioni desktop di Windows che si interfacciano con SQL Server, ma sto cercando di ampliare le mie conoscenze, quindi per favore abbiate pazienza.

Come ho affermato prima, posso accedere con successo all'applicazione, cosa che credo avvenga nel progetto TaskWebApp.

Ecco il codice in cui si verifica l'errore, che si trova in TasksController.cs nel progetto TaskWebApp:

namespace TaskWebApp.Controllers
{
    [Authorize]
    public class TasksController : Controller
    {
        private readonly string apiEndpoint = Globals.ServiceUrl + "/api/tasks/";

        // GET: Makes a call to the API and retrieves the list of tasks
        public async Task<ActionResult> Index()
        {
            try
            {
                // Retrieve the token with the specified scopes
                var scope = new string[] { Globals.ReadTasksScope };
                
                IConfidentialClientApplication cca = MsalAppBuilder.BuildConfidentialClientApplication();
                var accounts = await cca.GetAccountsAsync();
                AuthenticationResult result = await cca.AcquireTokenSilent(scope, accounts.FirstOrDefault()).ExecuteAsync();
                
                HttpClient client = new HttpClient();
                HttpRequestMessage request = new HttpRequestMessage(HttpMethod.Get, apiEndpoint);

                // Add token to the Authorization header and make the request
                request.Headers.Authorization = new AuthenticationHeaderValue("Bearer", result.AccessToken);
                HttpResponseMessage response = await client.SendAsync(request);

                // Handle the response
                switch (response.StatusCode)
                {
                    case HttpStatusCode.OK:
                        string responseString = await response.Content.ReadAsStringAsync();
                        JArray tasks = JArray.Parse(responseString);
                        ViewBag.Tasks = tasks;
                        return View();
                    case HttpStatusCode.Unauthorized:
                        return ErrorAction("Please sign in again. " + response.ReasonPhrase);
                    default:
                        return ErrorAction("Error. Status code = " + response.StatusCode + ": " + response.ReasonPhrase);
                }
            }
            catch (MsalUiRequiredException ex)
            {
                /*
                    If the tokens have expired or become invalid for any reason, ask the user to sign in again.
                    Another cause of this exception is when you restart the app using InMemory cache.
                    It will get wiped out while the user will be authenticated still because of their cookies, requiring the TokenCache to be initialized again
                    through the sign in flow.
                */
                return new RedirectResult("/Account/SignUpSignIn?redirectUrl=/Tasks");
            }
            catch (Exception ex)
            {
                return ErrorAction("Error reading to do list: " + ex.Message);
            }
        }

Il codice di stato della risposta nell'istruzione Switch è 404.

Quando eseguo il debug, ecco cosa vedo:

var scope restituisce https://ShoppingCartB2C.onmicrosoft.com/tasks/demo.read

cca restituisce (sto mettendo in dubbio il formato della proprietà Authority):

conti non restituisce nulla. Un conteggio di 0.

Credo che 0 account siano il problema.

Quando provo a ottenere il risultato, va al blocco catch.

Ecco il Web.config per il progetto TaskWebApp:

<configuration>
  <appSettings>
    <add key="webpages:Version" value="3.0.0.0" />
    <add key="webpages:Enabled" value="false" />
    <add key="ClientValidationEnabled" value="true" />
    <add key="UnobtrusiveJavaScriptEnabled" value="true" />
    <add key="ida:Tenant" value="ShoppingCartB2C.onmicrosoft.com" />
    <!--MSAL cache needs a tenantId along with the user's objectId to function. It retrieves these two from the claims returned in the id_token. 
        As tenantId is not guaranteed to be present in id_tokens issued by B2C unless the steps listed in this 
        document (https://github.com/AzureAD/microsoft-authentication-library-for-dotnet/wiki/AAD-B2C-specifics#caching-with-b2c-in-msalnet). 
        If you are following the workarounds listed in the doc and tenantId claim (tid) is available in the user's token, then please change the 
        code in <ClaimsPrincipalsExtension.cs GetB2CMsalAccountId()> to let MSAL pick this from the claims instead -->
    <add key="ida:TenantId" value="db1b052a-415c-4604-887c-e27b59860001" />
    <add key="ida:ClientId" value="975f1457-e3e2-4cb8-b069-6b0b6b46611d" />
    <add key="ida:ClientSecret" value="Gw4.3o-DRDr.j_828H-JMfsk_Jd1d-jQ5p" />
    <add key="ida:AadInstance" value="https://ShoppingCartB2C.b2clogin.com/tfp/{0}/{1}" />
    <add key="ida:RedirectUri" value="https://localhost:44316/" />
    <add key="ida:SignUpSignInPolicyId" value="B2C_1_signupsignin1" />
    <add key="ida:EditProfilePolicyId" value="b2c_1_profileediting1" />
    <add key="ida:ResetPasswordPolicyId" value="b2c_1_passwordreset1" />
    <add key="api:TaskServiceUrl" value="https://localhost:44332/" />
    <!-- The following settings is used for requesting access tokens -->
    <add key="api:ApiIdentifier" value="https://ShoppingCartB2C.onmicrosoft.com/tasks/" />
    <add key="api:ReadScope" value="demo.read" />
    <add key="api:WriteScope" value="demo.write" />
  </appSettings>

E per il progetto TaskService:

<configuration>
  <configSections>
    <section name="entityFramework" type="System.Data.Entity.Internal.ConfigFile.EntityFrameworkSection, EntityFramework, Version=6.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" requirePermission="false" />
  </configSections>
  <appSettings>
    <add key="webpages:Version" value="3.0.0.0" />
    <add key="webpages:Enabled" value="false" />
    <add key="ClientValidationEnabled" value="true" />
    <add key="UnobtrusiveJavaScriptEnabled" value="true" />
    <add key="ida:AadInstance" value="https://ShoppingCartB2C.b2clogin.com/{0}/{1}/v2.0/.well-known/openid-configuration" />
    <add key="ida:Tenant" value="ShoppingCartB2C.onmicrosoft.com" />
    <add key="ida:ClientId" value="975f1457-e3e2-4cb8-b069-6b0b6b46611d" />
    <add key="ida:SignUpSignInPolicyId" value="B2C_1_signupsignin1" />
    <!-- The following settings is used for requesting access tokens -->
    <add key="api:ReadScope" value="demo.read" />
    <add key="api:WriteScope" value="demo.write" />
  </appSettings>

Se desideri schermate da Azure o hai domande su come è configurato, non esitare a chiedere.

Non mi preoccupo di esporre i segreti dei clienti o gli AppId perché sto solo seguendo una demo. Questa non sarà mai un'app di produzione.

Non ho apportato modifiche al codice alla demo. Grazie per il tuo aiuto.

Modifica:visualizzazione delle autorizzazioni API