Tutorial: como lidar com fluxos de autenticação em um SPA do Angular
Este tutorial é a parte 3 de uma série que demonstra a criação de um SPA (aplicativo de página única) do Angular e a preparação para autenticação. Na Parte 2 desta série, você criou um SPA do Angular e preparou-o para autenticação com seu locatário externo. Nesse tutorial, você aprenderá a lidar com fluxos de autenticação no seu aplicativo adicionando componentes da Biblioteca de Autenticação da Microsoft (MSAL).
Neste tutorial;
- Adicionar fluxos de autenticação ao seu aplicativo
- Importar componentes MSAL
- Adicione rotas para componentes domésticos e protegidos do aplicativo.
Pré-requisitos
Criar o arquivo de configuração de autenticação, auth-config.ts
Crie um novo arquivo chamado auth-config.ts na pasta src/app/ e adicione o trecho de código a seguir. Esse arquivo contém parâmetros de autenticação. Esses parâmetros são usados para inicializar as configurações Angular e MSAL Angular.
/** * This file contains authentication parameters. Contents of this file * is roughly the same across other MSAL.js libraries. These parameters * are used to initialize Angular and MSAL Angular configurations in * in app.module.ts file. */ import { LogLevel, Configuration, BrowserCacheLocation, } from '@azure/msal-browser'; /** * Configuration object to be passed to MSAL instance on creation. * For a full list of MSAL.js configuration parameters, visit: * https://github.com/AzureAD/microsoft-authentication-library-for-js/blob/dev/lib/msal-browser/docs/configuration.md */ export const msalConfig: Configuration = { auth: { clientId: 'Enter_the_Application_Id_Here', // This is the ONLY mandatory field that you need to supply. authority: 'https://Enter_the_Tenant_Subdomain_Here.ciamlogin.com/', // Replace the placeholder with your tenant subdomain redirectUri: '/', // Points to window.location.origin by default. You must register this URI on Azure portal/App Registration. postLogoutRedirectUri: '/', // Points to window.location.origin by default. }, cache: { cacheLocation: BrowserCacheLocation.LocalStorage, // Configures cache location. "sessionStorage" is more secure, but "localStorage" gives you SSO between tabs. }, system: { loggerOptions: { loggerCallback(logLevel: LogLevel, message: string) { console.log(message); }, logLevel: LogLevel.Verbose, piiLoggingEnabled: false, }, }, }; /** * Scopes you add here will be prompted for user consent during sign-in. * By default, MSAL.js will add OIDC scopes (openid, profile, email) to any login request. * For more information about OIDC scopes, visit: * https://learn.microsoft.com/entra/identity-platform/permissions-consent-overview#openid-connect-scopes */ export const loginRequest = { scopes: [], };
Substitua os seguintes valores pelos valores do Centro de administração do Microsoft Entra:
- Localize o valor
Enter_the_Application_Id_Here
e substitua-o pela ID do aplicativo (clientId) do aplicativo registrado no centro de administração do Microsoft Entra. - Em autoridade, localize
Enter_the_Tenant_Subdomain_Here
e substitua-o pelo subdomínio do seu locatário. Por exemplo, se o domínio primário do locatário forcontoso.onmicrosoft.com
, usecontoso
. Se você não tiver o nome do locatário, saiba como ler os detalhes do locatário.
- Localize o valor
Salve o arquivo.
Usar um domínio de URL personalizado (opcional)
Use um domínio personalizado para marcar totalmente a URL de autenticação. Do ponto de vista do usuário, os usuários permanecem no seu domínio durante o processo de autenticação, em vez de serem redirecionados para o nome de domínio ciamlogin.com.
Use as etapas a seguir para usar um domínio personalizado:
Use as etapas em Habilitar domínios de URL personalizados para aplicativos em locatários externos para habilitar domínio de URL personalizado para seu locatário externo.
Em seu arquivo authConfig.js, localize o objeto
auth
e, em seguida:- Atualize o valor da propriedade
authority
para https://Enter_the_Custom_Domain_Here/Enter_the_Tenant_ID_Here. SubstituaEnter_the_Custom_Domain_Here
pelo domínio de URL personalizado eEnter_the_Tenant_ID_Here
pela ID do locatário. Se você não tiver o nome do locatário, saiba como ler os detalhes do locatário. - Adicione a propriedade
knownAuthorities
com um valor [Insira_o_Domínio_Personalizado_Aqui].
- Atualize o valor da propriedade
Depois de fazer as alterações no arquivo authConfig.js, se o domínio de URL personalizado for login.contoso.com e a ID de locatário for aaaabbbb-0000-cccc-1111-dddd2222eeee, o arquivo deverá ser semelhante ao seguinte snippet:
//...
const msalConfig = {
auth: {
authority: process.env.AUTHORITY || 'https://login.contoso.com/aaaabbbb-0000-cccc-1111-dddd2222eeee',
knownAuthorities: ["login.contoso.com"],
//Other properties
},
//...
};
Importar componentes MSAL
Abra src/app/app.module.ts e adicione o trecho de código a seguir.
import { NgModule } from '@angular/core'; import { BrowserModule } from '@angular/platform-browser'; import { HTTP_INTERCEPTORS, HttpClientModule } from '@angular/common/http'; import { MatToolbarModule } from "@angular/material/toolbar"; import { MatButtonModule } from '@angular/material/button'; import { MatCardModule } from '@angular/material/card'; import { MatTableModule } from '@angular/material/table'; import { MatMenuModule } from '@angular/material/menu'; import { MatDialogModule } from '@angular/material/dialog'; import { BrowserAnimationsModule } from '@angular/platform-browser/animations'; import { MatIconModule } from '@angular/material/icon'; import { AppRoutingModule } from './app-routing.module'; import { AppComponent } from './app.component'; import { HomeComponent } from './home/home.component'; import { GuardedComponent } from './guarded/guarded.component'; import { IPublicClientApplication, PublicClientApplication, InteractionType, } from '@azure/msal-browser'; import { MSAL_INSTANCE, MsalGuardConfiguration, MSAL_GUARD_CONFIG, MsalService, MsalBroadcastService, MsalGuard, MsalRedirectComponent, MsalInterceptor, MsalModule, } from '@azure/msal-angular'; import { msalConfig, loginRequest } from './auth-config'; /** * Here we pass the configuration parameters to create an MSAL instance. * For more info, visit: https://github.com/AzureAD/microsoft-authentication-library-for-js/blob/dev/lib/msal-angular/docs/v2-docs/configuration.md */ export function MSALInstanceFactory(): IPublicClientApplication { return new PublicClientApplication(msalConfig); } /** * Set your default interaction type for MSALGuard here. If you have any * additional scopes you want the user to consent upon login, add them here as well. */ export function MsalGuardConfigurationFactory(): MsalGuardConfiguration { return { interactionType: InteractionType.Redirect, authRequest: loginRequest }; } @NgModule({ declarations: [ AppComponent, HomeComponent, GuardedComponent, ], imports: [ BrowserModule, BrowserAnimationsModule, AppRoutingModule, MatToolbarModule, MatButtonModule, MatCardModule, MatTableModule, MatMenuModule, HttpClientModule, BrowserAnimationsModule, MatDialogModule, MatIconModule, MsalModule, ], providers: [ { provide: HTTP_INTERCEPTORS, useClass: MsalInterceptor, multi: true, }, { provide: MSAL_INSTANCE, useFactory: MSALInstanceFactory, }, { provide: MSAL_GUARD_CONFIG, useFactory: MsalGuardConfigurationFactory, }, MsalService, MsalBroadcastService, MsalGuard, ], bootstrap: [AppComponent, MsalRedirectComponent], }) export class AppModule { }
Abra src/app/app-routing.module.ts e substitua todo o conteúdo do arquivo pelo trecho a seguir. Isso adicionará rotas aos componentes
home
eguarded
.import { NgModule } from '@angular/core'; import { RouterModule, Routes } from '@angular/router'; import { BrowserUtils } from '@azure/msal-browser'; import { MsalGuard } from '@azure/msal-angular'; import { HomeComponent } from './home/home.component'; import { GuardedComponent } from './guarded/guarded.component'; /** * MSAL Angular can protect routes in your application * using MsalGuard. For more info, visit: * https://github.com/AzureAD/microsoft-authentication-library-for-js/blob/dev/lib/msal-angular/docs/v2-docs/initialization.md#secure-the-routes-in-your-application */ const routes: Routes = [ { path: 'guarded', component: GuardedComponent, canActivate: [ MsalGuard ] }, { path: '', component: HomeComponent, }, ]; @NgModule({ imports: [ RouterModule.forRoot(routes, { // Don't perform initial navigation in iframes or popups initialNavigation: !BrowserUtils.isInIframe() && !BrowserUtils.isInPopup() ? 'enabledNonBlocking' : 'disabled', // Set to enabledBlocking to use Angular Universal }), ], exports: [RouterModule], }) export class AppRoutingModule { }