Aplicación de página única: inicio de sesión y cierre de sesión
Artículo
Antes de obtener tokens para acceder a las API de la aplicación, necesita un contexto de usuario autenticado. Para autenticar a un usuario, puede usar un método de inicio de sesión de ventana emergente o de redireccionamiento.
Si su aplicación tiene acceso a un contexto de usuario autenticado o un token de identificación, puede omitir el paso de inicio de sesión y adquirir los tokens directamente. Para detalles, consulte Inicio de sesión único (SSO) con sugerencia de usuario.
Elegir entre una experiencia de elemento emergente o redireccionamiento
La elección entre una experiencia de elemento emergente o redireccionamiento depende de su flujo de la aplicación.
Use una ventana emergente si no quiere que los usuarios salgan de la página principal de la aplicación durante la autenticación. Dado que la redirección de la autenticación tiene lugar en una ventana emergente, se conserva el estado de la aplicación principal.
Para invocar una experiencia de inicio de sesión para una ruta específica, importe @angular/router y agregue MsalGuard a la definición de ruta.
// In app-routing.module.ts
import { NgModule } from "@angular/core";
import { Routes, RouterModule } from "@angular/router";
import { ProfileComponent } from "./profile/profile.component";
import { MsalGuard } from "@azure/msal-angular";
import { HomeComponent } from "./home/home.component";
const routes: Routes = [
{
path: "profile",
component: ProfileComponent,
canActivate: [MsalGuard],
},
{
path: "",
component: HomeComponent,
},
];
@NgModule({
imports: [RouterModule.forRoot(routes, { useHash: false })],
exports: [RouterModule],
})
export class AppRoutingModule {}
Para habilitar una experiencia de ventana emergente, establezca la configuración de interactionType en InteractionType.Popup en MsalGuardConfiguration. También puede pasar los ámbitos que requieren el consentimiento.
Para invocar una experiencia de inicio de sesión cuando un usuario aún no ha iniciado sesión, use la función MsalAuthenticationTemplate de @azure/msal-react. El contenedor React de MSAL protege componentes específicos al encapsularlos en el componente MsalAuthenticationTemplate.
import { InteractionType } from "@azure/msal-browser";
import { MsalAuthenticationTemplate, useMsal } from "@azure/msal-react";
function WelcomeUser() {
const { accounts } = useMsal();
const username = accounts[0].username;
return <p>Welcome, {username}</p>;
}
// Remember that MsalProvider must be rendered somewhere higher up in the component tree
function App() {
return (
<MsalAuthenticationTemplate interactionType={InteractionType.Popup}>
<p>This will only render if a user is not signed-in.</p>
<WelcomeUser />
</MsalAuthenticationTemplate>
);
}
Para invocar una experiencia de inicio de sesión específica basada en la interacción del usuario (por ejemplo, la selección de un botón), use la función AuthenticatedTemplate o UnauthenticatedTemplate de @azure/msal-react.
import {
useMsal,
AuthenticatedTemplate,
UnauthenticatedTemplate,
} from "@azure/msal-react";
function signInClickHandler(instance) {
instance.loginPopup();
}
// SignInButton Component returns a button that invokes a popup sign in when clicked
function SignInButton() {
// useMsal hook will return the PublicClientApplication instance you provided to MsalProvider
const { instance } = useMsal();
return <button onClick={() => signInClickHandler(instance)}>Sign In</button>;
}
function WelcomeUser() {
const { accounts } = useMsal();
const username = accounts[0].username;
return <p>Welcome, {username}</p>;
}
// Remember that MsalProvider must be rendered somewhere higher up in the component tree
function App() {
return (
<>
<AuthenticatedTemplate>
<p>This will only render if a user is signed-in.</p>
<WelcomeUser />
</AuthenticatedTemplate>
<UnauthenticatedTemplate>
<p>This will only render if a user is not signed-in.</p>
<SignInButton />
</UnauthenticatedTemplate>
</>
);
}
const config = {
auth: {
clientId: "your_app_id",
redirectUri: "your_app_redirect_uri", //defaults to application start page
postLogoutRedirectUri: "your_app_logout_redirect_uri",
},
};
const loginRequest = {
scopes: ["User.ReadWrite"],
};
let accountId = "";
const myMsal = new PublicClientApplication(config);
function handleResponse(response) {
if (response !== null) {
accountId = response.account.homeAccountId;
// Display signed-in user content, call API, etc.
} else {
// In case multiple accounts exist, you can select
const currentAccounts = myMsal.getAllAccounts();
if (currentAccounts.length === 0) {
// no accounts signed-in, attempt to sign a user in
myMsal.loginRedirect(loginRequest);
} else if (currentAccounts.length > 1) {
// Add choose account code here
} else if (currentAccounts.length === 1) {
accountId = currentAccounts[0].homeAccountId;
}
}
}
myMsal.handleRedirectPromise().then(handleResponse);
Para habilitar una experiencia de redireccionamiento, establezca la configuración de interactionType en InteractionType.Redirect en MsalGuardConfiguration y, después, arranque MsalRedirectComponent para controlar los redireccionamientos.
Para invocar una experiencia de inicio de sesión cuando un usuario no ha iniciado sesión, use la función MsalAuthenticationTemplate de @azure/msal-react.
import { InteractionType } from "@azure/msal-browser";
import { MsalAuthenticationTemplate, useMsal } from "@azure/msal-react";
function WelcomeUser() {
const { accounts } = useMsal();
const username = accounts[0].username;
return <p>Welcome, {username}</p>;
}
// Remember that MsalProvider must be rendered somewhere higher up in the component tree
function App() {
return (
<MsalAuthenticationTemplate interactionType={InteractionType.Redirect}>
<p>This will only render if a user is not signed-in.</p>
<WelcomeUser />
</MsalAuthenticationTemplate>
);
}
Para invocar una experiencia de inicio de sesión específica basada en la interacción del usuario (por ejemplo, la selección de un botón), use la función AuthenticatedTemplate o UnauthenticatedTemplate de @azure/msal-react.
import {
useMsal,
AuthenticatedTemplate,
UnauthenticatedTemplate,
} from "@azure/msal-react";
function signInClickHandler(instance) {
instance.loginRedirect();
}
// SignInButton Component returns a button that invokes a popup login when clicked
function SignInButton() {
// useMsal hook will return the PublicClientApplication instance you provided to MsalProvider
const { instance } = useMsal();
return <button onClick={() => signInClickHandler(instance)}>Sign In</button>;
}
function WelcomeUser() {
const { accounts } = useMsal();
const username = accounts[0].username;
return <p>Welcome, {username}</p>;
}
// Remember that MsalProvider must be rendered somewhere higher up in the component tree
function App() {
return (
<>
<AuthenticatedTemplate>
<p>This will only render if a user is signed-in.</p>
<WelcomeUser />
</AuthenticatedTemplate>
<UnauthenticatedTemplate>
<p>This will only render if a user is not signed-in.</p>
<SignInButton />
</UnauthenticatedTemplate>
</>
);
}
Comportamiento de cierre de sesión en exploradores
Para garantizar el cierre de sesión seguro de una o varias aplicaciones, se recomiendan los métodos siguientes:
En los dispositivos compartidos, los usuarios deben usar el modo privado o incógnito de un explorador y cerrar todas las ventanas del explorador antes de alejarse del dispositivo.
En los dispositivos que no se comparten, los usuarios deben usar una pantalla de bloqueo del sistema operativo para bloquear cerrar la sesión de su sistema operativo completo en el dispositivo. Microsoft usa su página de cierre de sesión para recordar a los usuarios estos procedimientos recomendados de privacidad y seguridad.
Si un usuario decide no cerrar sesión siguiendo las recomendaciones, estos son otros métodos para habilitar la funcionalidad de cierre de sesión:
Cierre de sesión del canal frontal de OpenID Connect de Microsoft para el cierre de sesión federado. Puede usar esta opción cuando una aplicación comparte un estado de inicio de sesión con una nueva aplicación, pero administra sus propios tokens o cookies de sesión. Hay algunas limitaciones en esta implementación en las que el contenido está bloqueado, como cuando los exploradores bloquean cookies de terceros.
Una ventana emergente o un redireccionamiento para cerrar la sesión de la aplicación local. Los métodos de ventana emergente y redireccionamiento finalizan la sesión del usuario en el punto de conexión y para la aplicación local. Sin embargo, es posible que estos métodos no cierren inmediatamente la sesión de otras aplicaciones federadas si se bloquea la comunicación del canal frontal.
Cierre de sesión con una ventana emergente
MSAL.js v2 y versiones posteriores proporciona un método logoutPopup que limpia la caché en el almacenamiento del explorador y abre una ventana emergente a la página de cierre de sesión de Microsoft Entra. Después de cerrar la sesión, se redirige a la página de inicio de sesión de forma predeterminada y se cierra la ventana emergente.
Para la experiencia de cierre de sesión posterior, puede establecer postLogoutRedirectUri para redirigir al usuario a un URI específico. Este URI se debe registrar como un URI de redirección en el registro de la aplicación. También puede configurar logoutPopup para redirigir la ventana principal a otra página, como la página principal o la página de inicio de sesión, pasando mainWindowRedirectUri como parte de la solicitud.
import {
useMsal,
AuthenticatedTemplate,
UnauthenticatedTemplate,
} from "@azure/msal-react";
function signOutClickHandler(instance) {
const logoutRequest = {
account: instance.getAccountByHomeId(homeAccountId),
mainWindowRedirectUri: "your_app_main_window_redirect_uri",
postLogoutRedirectUri: "your_app_logout_redirect_uri",
};
instance.logoutPopup(logoutRequest);
}
// SignOutButton component returns a button that invokes a pop-up sign out when clicked
function SignOutButton() {
// useMsal hook will return the PublicClientApplication instance you provided to MsalProvider
const { instance } = useMsal();
return (
<button onClick={() => signOutClickHandler(instance)}>Sign Out</button>
);
}
// Remember that MsalProvider must be rendered somewhere higher up in the component tree
function App() {
return (
<>
<AuthenticatedTemplate>
<p>This will only render if a user is signed-in.</p>
<SignOutButton />
</AuthenticatedTemplate>
<UnauthenticatedTemplate>
<p>This will only render if a user is not signed-in.</p>
</UnauthenticatedTemplate>
</>
);
}
Cierre de sesión con un redireccionamiento
MSAL.js proporciona un método logout en la v1, y un método logoutRedirect en la v2 que limpia la caché en el almacenamiento del explorador y redirige a la página de cierre de sesión de Microsoft Entra. Después de cerrar la sesión, se redirige a la página de inicio de sesión de forma predeterminada.
Para la experiencia de cierre de sesión posterior, puede establecer postLogoutRedirectUri para redirigir al usuario a un URI específico. Este URI se debe registrar como un URI de redirección en el registro de la aplicación.
Dado que el recordatorio de Microsoft de los procedimientos recomendados de privacidad en Internet sobre el uso de un explorador privado y una pantalla de bloqueo no se muestra con este método, es posible que quiera describir los procedimientos recomendados y recordar a los usuarios que cierren todas las ventanas del explorador.
const config = {
auth: {
clientId: "your_app_id",
redirectUri: "your_app_redirect_uri", //defaults to application start page
postLogoutRedirectUri: "your_app_logout_redirect_uri",
},
};
const myMsal = new PublicClientApplication(config);
// you can select which account application should sign out
const logoutRequest = {
account: myMsal.getAccountByHomeId(homeAccountId),
};
myMsal.logoutRedirect(logoutRequest);
// In app.module.ts
@NgModule({
imports: [
MsalModule.forRoot( new PublicClientApplication({
auth: {
clientId: 'your_app_id',
postLogoutRedirectUri: 'your_app_logout_redirect_uri'
}
}), null, null)
]
})
// In app.component.ts
logout() {
this.authService.logoutRedirect();
}
import {
useMsal,
AuthenticatedTemplate,
UnauthenticatedTemplate,
} from "@azure/msal-react";
function signOutClickHandler(instance) {
const logoutRequest = {
account: instance.getAccountByHomeId(homeAccountId),
postLogoutRedirectUri: "your_app_logout_redirect_uri",
};
instance.logoutRedirect(logoutRequest);
}
// SignOutButton Component returns a button that invokes a redirect logout when clicked
function SignOutButton() {
// useMsal hook will return the PublicClientApplication instance you provided to MsalProvider
const { instance } = useMsal();
return (
<button onClick={() => signOutClickHandler(instance)}>Sign Out</button>
);
}
// Remember that MsalProvider must be rendered somewhere higher up in the component tree
function App() {
return (
<>
<AuthenticatedTemplate>
<p>This will only render if a user is signed-in.</p>
<SignOutButton />
</AuthenticatedTemplate>
<UnauthenticatedTemplate>
<p>This will only render if a user is not signed-in.</p>
</UnauthenticatedTemplate>
</>
);
}