Nota:
El acceso a esta página requiere autorización. Puede intentar iniciar sesión o cambiar directorios.
El acceso a esta página requiere autorización. Puede intentar cambiar los directorios.
Este artículo le guiará a través de cómo empezar a trabajar con @azure/msal-react. Abordaremos la inicialización, cómo determinar si un usuario está autenticado, cómo proteger componentes, cómo iniciar la sesión de un usuario y cómo obtener un token de acceso.
Prerequisites
Inicialización
@azure/msal-react se basa en la API de contexto de React y todas las partes de la aplicación que requieren autenticación se deben encapsular en el MsalProvider componente. En primer lugar, deberá inicializar una instancia de PublicClientApplication y, a continuación, pasarla a MsalProvider como prop.
import React from "react";
import { createRoot } from "react-dom/client";
import { MsalProvider } from "@azure/msal-react";
import { Configuration, PublicClientApplication } from "@azure/msal-browser";
import App from "./app.jsx";
// MSAL configuration
const configuration: Configuration = {
auth: {
clientId: "client-id"
}
};
const pca = new PublicClientApplication(configuration);
// Component
const AppProvider = () => (
<MsalProvider instance={pca}>
<App />
</MsalProvider>
);
const root = createRoot(document.getElementById("root"));
root.render(<AppProvider />);
Todos los componentes debajo de MsalProvider tendrán acceso a la instancia mediante el contexto de PublicClientApplication, así como a todos los hooks y componentes que proporciona @azure/msal-react.
Determinar si un usuario está autenticado
La mayoría de las aplicaciones tendrán que representar condicionalmente determinados componentes en función de si un usuario ha iniciado sesión o no.
@azure/msal-react proporciona 2 formas fáciles de hacerlo.
AuthenticatedTemplate y UnauthenticatedTemplate
Los componentes AuthenticatedTemplate y UnauthenticatedTemplate solo mostrarán su contenido si el usuario está autenticado o no lo está, respectivamente.
import React from 'react';
import { AuthenticatedTemplate, UnauthenticatedTemplate } from "@azure/msal-react";
export function App() {
return (
<React.Fragment>
<p>Anyone can see this paragraph.</p>
<AuthenticatedTemplate>
<p>At least one account is signed in!</p>
</AuthenticatedTemplate>
<UnauthenticatedTemplate>
<p>No users are signed in!</p>
</UnauthenticatedTemplate>
</React.Fragment>
);
}
useIsAuthenticated enlace
Como alternativa a los componentes contenedores situados por encima de su aplicación, esta puede usar el hook useIsAuthenticated. Puede leer más sobre esto en Hooks en MSAL React.
import React from 'react';
import { useIsAuthenticated } from "@azure/msal-react";
export function App() {
const isAuthenticated = useIsAuthenticated();
return (
<React.Fragment>
<p>Anyone can see this paragraph.</p>
{isAuthenticated && (
<p>At least one account is signed in!</p>
)}
{!isAuthenticated && (
<p>No users are signed in!</p>
)}
</React.Fragment>
);
}
Protección de componentes
Si tiene componentes que solo desea mostrar a los usuarios autenticados, puede usar cualquiera de los métodos anteriores. Pero, ¿qué ocurre si desea invocar automáticamente un inicio de sesión si un usuario aún no está autenticado?
@azure/msal-react proporciona dos formas de hacer esto con el MsalAuthenticationTemplate o el hook useMsalAuthentication.
Componente MsalAuthenticationTemplate
El componente MsalAuthenticationTemplate elementos secundarios si un usuario está autenticado o intenta iniciar sesión. Solo tiene que proporcionarlo con el tipo de interacción que desea usar (redireccionamiento o ventana emergente) y, opcionalmente, un objeto de solicitud que se va a pasar a la API de inicio de sesión, un componente para mostrar mientras la autenticación está en curso o un componente para mostrar si se produce un error.
Puede encontrar un ejemplo de trabajo de esto en cualquiera de nuestros ejemplos en la /profile página.
import React from "react";
import { MsalAuthenticationTemplate } from "@azure/msal-react";
import { InteractionType } from "@azure/msal-browser";
function ErrorComponent({error}) {
return <p>An Error Occurred: {error}</p>;
}
function LoadingComponent() {
return <p>Authentication in progress...</p>;
}
export function Example() {
const authRequest = {
scopes: ["openid", "profile"]
};
return (
// authenticationRequest, errorComponent and loadingComponent props are optional
<MsalAuthenticationTemplate
interactionType={InteractionType.Popup}
authenticationRequest={authRequest}
errorComponent={ErrorComponent}
loadingComponent={LoadingComponent}
>
<p>At least one account is signed in!</p>
</MsalAuthenticationTemplate>
)
};
useMsalAuthentication enlace
El hook useMsalAuthentication comprobará primero si hay un usuario que haya iniciado sesión y, a continuación, intentará iniciar la sesión de un usuario si no hay ningún usuario con la sesión iniciada. Deberá proporcionar el tipo de interacción que desea usar (redireccionamiento o elemento emergente).
Devolverá el resultado de la operación de inicio de sesión, cualquier error que se haya producido y la función de inicio de sesión que puede usar si necesita volver a intentarlo.
Puede leer más sobre este hook en la documentación sobre hooks.
import React from 'react';
import { useMsalAuthentication } from "@azure/msal-react";
import { InteractionType } from '@azure/msal-browser';
export function App() {
const {login, result, error} = useMsalAuthentication(InteractionType.Popup);
return (
<React.Fragment>
<p>Anyone can see this paragraph.</p>
<AuthenticatedTemplate>
<p>At least one account is signed in!</p>
</AuthenticatedTemplate>
<UnauthenticatedTemplate>
<p>No users are signed in!</p>
</UnauthenticatedTemplate>
</React.Fragment>
);
}
Inicio de sesión de un usuario mediante las API de inicio de sesión proporcionadas por @azure/msal-browser
Otra manera de invocar un inicio de sesión es usar @azure/msal-browser API directamente desde la PublicClientApplication instancia en contexto. Hay tres maneras de acceder a la instancia desde el contexto.
useMsal enlace
Un hook que devuelve la instancia PublicClientApplication, una lista de todas las cuentas con sesión iniciada actualmente y un valor inProgress que indica qué está haciendo msal en ese momento.
Puede leer más sobre este hook en la documentación sobre hooks.
import React from 'react';
import { useMsal } from "@azure/msal-react";
export function App() {
const { instance, accounts, inProgress } = useMsal();
if (accounts.length > 0) {
return <span>There are currently {accounts.length} users signed in!</span>
} else if (inProgress === "login") {
return <span>Login is currently in progress!</span>
} else {
return (
<>
<span>There are currently no users signed in!</span>
<button onClick={() => instance.loginPopup()}>Login</button>
</>
);
}
}
Consumo del contexto sin procesar
Si usa un componente de clase y no puede usar hooks, puede consumir el contexto raw de MSAL a través de MsalContext.
Puede obtener más información sobre cómo usar @azure/msal-react en componentes de clase aquí.
import React from "react";
import { MsalContext } from "@azure/msal-react";
class App extends React.Component {
static contextType = MsalContext;
render() {
if (this.context.accounts.length > 0) {
return <span>There are currently {this.context.accounts.length} users signed in!</span>
} else if (this.context.inProgress === "login") {
return <span>Login is currently in progress!</span>
} else {
return (
<>
<span>There are currently no users signed in!</span>
<button onClick={() => this.context.instance.loginPopup()}>Login</button>
</>
);
}
}
}
Encapsular tu componente con el withMsalcomponente de orden superior
Otra forma de consumir el contexto de MSAL tanto en componentes de clase como en componentes funcionales es envolver el componente con el HOC withMsal, que inyectará el contexto en las propiedades de su componente.
import React from "react";
import { withMsal } from "@azure/msal-react";
class LoginButton extends React.Component {
render() {
const isAuthenticated = this.props.msalContext.accounts.length > 0;
const msalInstance = this.props.msalContext.instance;
if (isAuthenticated) {
return <button onClick={() => msalInstance.logout()}>Logout</button>
} else {
return <button onClick={() => msalInstance.loginPopup()}>Login</button>
}
}
}
export default YourWrappedComponent = withMsal(LoginButton);
Adquisición de un token de acceso
Recomendamos que su aplicación llame a la API acquireTokenSilent de su objeto PublicClientApplication cada vez que necesite un token de acceso para acceder a una API. Esto puede hacerse de forma similar a las formas que se describen en la sección anterior.
import React, { useState, useEffect } from "react"
import { useMsal, useAccount } from "@azure/msal-react";
export function App() {
const { instance, accounts, inProgress } = useMsal();
const account = useAccount(accounts[0] || {});
const [apiData, setApiData] = useState(null);
useEffect(() => {
if (account) {
instance.acquireTokenSilent({
scopes: ["User.Read"],
account: account
}).then((response) => {
if(response) {
callMsGraph(response.accessToken).then((result) => setApiData(result));
}
});
}
}, [account, instance]);
if (accounts.length > 0) {
return (
<>
<span>There are currently {accounts.length} users signed in!</span>
{apiData && (<span>Data retreived from API: {JSON.stringify(apiData)}</span>)}
</>
);
} else if (inProgress === "login") {
return <span>Login is currently in progress!</span>
} else {
return <span>There are currently no users signed in!</span>
}
}
Adquisición de un token de acceso fuera de un componente de React
Si necesitas un token de acceso fuera de un componente de React, puedes llamar directamente a la función acquireTokenSilent en el PublicClientApplication.
No se recomienda llamar a funciones que cambien el estado autenticado del usuario (inicio de sesión, cierre de sesión) fuera del contexto de reacción proporcionado por MsalProvider , ya que es posible que los componentes dentro del contexto no se actualicen correctamente.
Tenga en cuenta que el usuario debe iniciar sesión antes de poder adquirir un token.
import { PublicClientApplication } from "@azure/msal-browser";
// This should be the same instance you pass to MsalProvider
const msalInstance = new PublicClientApplication(config);
const acquireAccessToken = async (msalInstance) => {
const activeAccount = msalInstance.getActiveAccount(); // This will only return a non-null value if you have logic somewhere else that calls the setActiveAccount API
const accounts = msalInstance.getAllAccounts();
if (!activeAccount && accounts.length === 0) {
/*
* User is not signed in. Throw error or wait for user to login.
* Do not attempt to log a user in outside of the context of MsalProvider
*/
}
const request = {
scopes: ["User.Read"],
account: activeAccount || accounts[0]
};
const authResult = await msalInstance.acquireTokenSilent(request);
return authResult.accessToken
};
Consulte también
- Consulte nuestro ejemplo de enrutador react para obtener un ejemplo de trabajo.
- Uso de MSAL React con componentes de clase