No ASP.NET Core, para aplicativos da plataforma de identidade da Microsoft, o botão Entrar é exposto em Views\Shared\_LoginPartial.cshtml (para um aplicativo MVC) ou Pages\Shared\_LoginPartial.cshtm (para um aplicativo Razor). Ele é exibido somente quando o usuário não está autenticado. Ou seja, ele é exibido quando o usuário ainda não entrou ou saiu. Pelo contrário, o botão Sair é exibido quando o usuário já está conectado. Observe que o controlador de conta é definido no pacote NuGet Microsoft.Identity.Web.UI , na área chamada MicrosoftIdentity
No ASP.NET MVC, o botão Entrar é exposto em Views\Shared\_LoginPartial.cshtml. Ele é exibido somente quando o usuário não está autenticado. Ou seja, ele é exibido quando o usuário ainda não entrou ou saiu.
Quando um usuário não autenticado visita a página inicial, a index rota no app.py redireciona o usuário para a login rota.
@app.route("/")
def index():
if not (app.config["CLIENT_ID"] and app.config["CLIENT_SECRET"]):
# This check is not strictly necessary.
# You can remove this check from your production code.
return render_template('config_error.html')
if not auth.get_user():
return redirect(url_for("login"))
return render_template('index.html', user=auth.get_user(), version=identity.__version__)
A login rota descobre o apropriado auth_uri e renderiza o modelo login.html .
@app.route("/login")
def login():
return render_template("login.html", version=identity.__version__, **auth.log_in(
scopes=app_config.SCOPE, # Have user consent to scopes during log-in
redirect_uri=url_for("auth_response", _external=True), # Optional. If present, this absolute URL must match your app's redirect_uri registered in Azure Portal
))
No ASP.NET, selecionar o botão Entrar no aplicativo Web dispara a SignIn ação no AccountController controlador. Em versões anteriores dos modelos ASP.NET Core, o Account controlador era incorporado ao aplicativo Web. Isso não é mais o caso porque o controlador agora faz parte do pacote NuGet Microsoft.Identity.Web.UI . Consulte AccountController.cs para obter detalhes.
Este controlador também lida com os aplicativos do Azure AD B2C.
No ASP.NET, o login é acionado a partir do SignIn() método em um controlador (por exemplo, AccountController.cs#L16-L23). Este método não faz parte do .NET Framework (ao contrário do que acontece no ASP.NET Core). Ele envia um desafio de login OpenID depois de propor um URI de redirecionamento.
public void SignIn()
{
// Send an OpenID Connect sign-in request.
if (!Request.IsAuthenticated)
{
HttpContext.GetOwinContext().Authentication.Challenge(new AuthenticationProperties { RedirectUri = "/" }, OpenIdConnectAuthenticationDefaults.AuthenticationType);
}
}
Em Java, a saída é tratada chamando o ponto de extremidade da plataforma logout de identidade da Microsoft diretamente e fornecendo o post_logout_redirect_uri valor. Para obter detalhes, consulte AuthPageController.java#L30-L48.
@Controller
public class AuthPageController {
@Autowired
AuthHelper authHelper;
@RequestMapping("/msal4jsample")
public String homepage(){
return "index";
}
@RequestMapping("/msal4jsample/secure/aad")
public ModelAndView securePage(HttpServletRequest httpRequest) throws ParseException {
ModelAndView mav = new ModelAndView("auth_page");
setAccountInfo(mav, httpRequest);
return mav;
}
// More code omitted for simplicity
Quando o usuário seleciona o link Entrar , que aciona a /auth/signin rota, o controlador de entrada assume o controle para autenticar o usuário com a plataforma de identidade da Microsoft.
login(options = {}) {
return async (req, res, next) => {
/**
* MSAL Node library allows you to pass your custom state as state parameter in the Request object.
* The state parameter can also be used to encode information of the app's state before redirect.
* You can pass the user's state in the app, such as the page or view they were on, as input to this parameter.
*/
const state = this.cryptoProvider.base64Encode(
JSON.stringify({
successRedirect: options.successRedirect || '/',
})
);
const authCodeUrlRequestParams = {
state: state,
/**
* By default, MSAL Node will add OIDC scopes to the auth code url request. For more information, visit:
* https://docs.microsoft.com/azure/active-directory/develop/v2-permissions-and-consent#openid-connect-scopes
*/
scopes: options.scopes || [],
redirectUri: options.redirectUri,
};
const authCodeRequestParams = {
state: state,
/**
* By default, MSAL Node will add OIDC scopes to the auth code request. For more information, visit:
* https://docs.microsoft.com/azure/active-directory/develop/v2-permissions-and-consent#openid-connect-scopes
*/
scopes: options.scopes || [],
redirectUri: options.redirectUri,
};
/**
* If the current msal configuration does not have cloudDiscoveryMetadata or authorityMetadata, we will
* make a request to the relevant endpoints to retrieve the metadata. This allows MSAL to avoid making
* metadata discovery calls, thereby improving performance of token acquisition process. For more, see:
* https://github.com/AzureAD/microsoft-authentication-library-for-js/blob/dev/lib/msal-node/docs/performance.md
*/
if (!this.msalConfig.auth.cloudDiscoveryMetadata || !this.msalConfig.auth.authorityMetadata) {
const [cloudDiscoveryMetadata, authorityMetadata] = await Promise.all([
this.getCloudDiscoveryMetadata(this.msalConfig.auth.authority),
this.getAuthorityMetadata(this.msalConfig.auth.authority)
]);
this.msalConfig.auth.cloudDiscoveryMetadata = JSON.stringify(cloudDiscoveryMetadata);
this.msalConfig.auth.authorityMetadata = JSON.stringify(authorityMetadata);
}
const msalInstance = this.getMsalInstance(this.msalConfig);
// trigger the first leg of auth code flow
return this.redirectToAuthCodeUrl(
authCodeUrlRequestParams,
authCodeRequestParams,
msalInstance
)(req, res, next);
};
}
redirectToAuthCodeUrl(authCodeUrlRequestParams, authCodeRequestParams, msalInstance) {
return async (req, res, next) => {
// Generate PKCE Codes before starting the authorization flow
const { verifier, challenge } = await this.cryptoProvider.generatePkceCodes();
// Set generated PKCE codes and method as session vars
req.session.pkceCodes = {
challengeMethod: 'S256',
verifier: verifier,
challenge: challenge,
};
/**
* By manipulating the request objects below before each request, we can obtain
* auth artifacts with desired claims. For more information, visit:
* https://azuread.github.io/microsoft-authentication-library-for-js/ref/modules/_azure_msal_node.html#authorizationurlrequest
* https://azuread.github.io/microsoft-authentication-library-for-js/ref/modules/_azure_msal_node.html#authorizationcoderequest
**/
req.session.authCodeUrlRequest = {
...authCodeUrlRequestParams,
responseMode: msal.ResponseMode.FORM_POST, // recommended for confidential clients
codeChallenge: req.session.pkceCodes.challenge,
codeChallengeMethod: req.session.pkceCodes.challengeMethod,
};
req.session.authCodeRequest = {
...authCodeRequestParams,
code: '',
};
try {
const authCodeUrlResponse = await msalInstance.getAuthCodeUrl(req.session.authCodeUrlRequest);
res.redirect(authCodeUrlResponse);
} catch (error) {
next(error);
}
};
}
/**
* Retrieves cloud discovery metadata from the /discovery/instance endpoint
* @returns
*/
async getCloudDiscoveryMetadata(authority) {
const endpoint = 'https://login.microsoftonline.com/common/discovery/instance';
try {
const response = await axios.get(endpoint, {
params: {
'api-version': '1.1',
'authorization_endpoint': `${authority}/oauth2/v2.0/authorize`
}
});
return await response.data;
} catch (error) {
throw error;
}
}
Quando o usuário seleciona o link Entrar , ele é levado ao ponto de extremidade de autorização da plataforma de identidade da Microsoft.
Uma entrada bem-sucedida redireciona o usuário para a auth_response rota, que conclui o processo de entrada usando auth.complete_login, processa erros, se houver, e redireciona o usuário agora autenticado para a página inicial.
@app.route(app_config.REDIRECT_PATH)
def auth_response():
result = auth.complete_log_in(request.args)
if "error" in result:
return render_template("auth_error.html", result=result)
return redirect(url_for("index"))
Depois que o usuário entrar no seu aplicativo, você desejará habilitá-lo para sair.
Terminar sessão
Sair de um aplicativo Web envolve mais do que remover as informações sobre a conta conectada do estado do aplicativo Web.
O aplicativo Web também deve redirecionar o usuário para o ponto de extremidade da plataforma logout de identidade da Microsoft para sair.
Quando seu aplicativo Web redireciona o usuário para o logout ponto de extremidade, esse ponto de extremidade limpa a sessão do usuário do navegador. Se seu aplicativo não foi para o logout ponto de extremidade, o usuário se autenticará novamente no aplicativo sem inserir suas credenciais novamente. O motivo é que eles terão uma sessão de logon único válida com a plataforma de identidade da Microsoft.
Durante o registro do aplicativo, você registra uma URL de logout do canal frontal. Em nosso tutorial, você se registrou https://localhost:44321/signout-oidc no campo URL de logout do canal frontal na página Autenticação. Para obter detalhes, consulte Registrar o aplicativo webApp.
Durante o registro do aplicativo, você não precisa registrar uma URL de logout extra do canal frontal. O aplicativo será chamado de volta em sua URL principal.
Nenhum URL de logout do canal frontal é necessário no registro do aplicativo.
Nenhum URL de logout do canal frontal é necessário no registro do aplicativo.
Durante o registro do aplicativo, você não precisa registrar uma URL de logout extra do canal frontal. O aplicativo será chamado de volta em sua URL principal.
No MVC ASP.NET, o botão de saída é exposto em Views\Shared\_LoginPartial.cshtml. Ele é exibido somente quando há uma conta autenticada. Ou seja, ele é exibido quando o usuário fez login anteriormente.
Em versões anteriores dos modelos ASP.NET Core, o Account controlador era incorporado ao aplicativo Web. Isso não é mais o caso porque o controlador agora faz parte do pacote NuGet Microsoft.Identity.Web.UI . Consulte AccountController.cs para obter detalhes.
Define um URI de redirecionamento OpenID para /Account/SignedOut que o controlador seja chamado de volta quando o Microsoft Entra ID tiver concluído a saída.
Chamadas Signout(), que permite que o middleware OpenID Connect entre em contato com o ponto de extremidade da plataforma logout de identidade da Microsoft. O ponto final, então:
Limpa o cookie de sessão do navegador.
Chama de volta o URI de redirecionamento pós-logout. Por padrão, o URI de redirecionamento pós-logout exibe a página de exibição desconectada SignedOut.cshtml.cs. Esta página também é fornecida como parte do Microsoft.Identity.Web.
No ASP.NET, a saída é acionada a partir do SignOut() método em um controlador (por exemplo, AccountController.cs#L25-L31). Esse método não faz parte do .NET Framework, ao contrário do que acontece no ASP.NET Core. Isso:
Envia um desafio de saída do OpenID.
Limpa o cache.
Redireciona para a página desejada.
/// <summary>
/// Send an OpenID Connect sign-out request.
/// </summary>
public void SignOut()
{
HttpContext.GetOwinContext()
.Authentication
.SignOut(CookieAuthenticationDefaults.AuthenticationType);
Response.Redirect("/");
}
Em Java, a saída é tratada chamando o ponto de extremidade da plataforma logout de identidade da Microsoft diretamente e fornecendo o post_logout_redirect_uri valor. Para obter detalhes, consulte AuthPageController.java#L50-L60.
Quando o usuário seleciona o botão Sair , o aplicativo dispara a /auth/signout rota, o que destrói a sessão e redireciona o navegador para o ponto de extremidade de saída da plataforma de identidade da Microsoft.
logout(options = {}) {
return (req, res, next) => {
/**
* Construct a logout URI and redirect the user to end the
* session with Azure AD. For more information, visit:
* https://docs.microsoft.com/azure/active-directory/develop/v2-protocols-oidc#send-a-sign-out-request
*/
let logoutUri = `${this.msalConfig.auth.authority}/oauth2/v2.0/`;
if (options.postLogoutRedirectUri) {
logoutUri += `logout?post_logout_redirect_uri=${options.postLogoutRedirectUri}`;
}
req.session.destroy(() => {
res.redirect(logoutUri);
});
}
}
Quando o usuário seleciona Logout, o aplicativo dispara a logout rota, que redireciona o navegador para o ponto de extremidade de saída da plataforma de identidade da Microsoft.
O middleware ASP.NET Core OpenID Connect permite que seu aplicativo intercete a chamada para o ponto de extremidade da plataforma logout de identidade da Microsoft fornecendo um evento OpenID Connect chamado OnRedirectToIdentityProviderForSignOut. Isso é tratado automaticamente pelo Microsoft.Identity.Web (que limpa contas no caso em que seu aplicativo Web chama APIs da Web)
No ASP.NET, você delega ao middleware para executar a saída, limpando o cookie de sessão:
public class AccountController : Controller
{
...
public void EndSession()
{
Request.GetOwinContext().Authentication.SignOut();
Request.GetOwinContext().Authentication.SignOut(Microsoft.AspNet.Identity.DefaultAuthenticationTypes.ApplicationCookie);
this.HttpContext.GetOwinContext().Authentication.SignOut(CookieAuthenticationDefaults.AuthenticationType);
}
}
No início rápido do Java, o URI de redirecionamento pós-logout exibe apenas a página index.html.
No início rápido do Nó, o URI de redirecionamento pós-logout é usado para redirecionar o navegador de volta para a página inicial de exemplo depois que o usuário conclui o processo de logout com a plataforma de identidade da Microsoft.
No início rápido do Python, o URI de redirecionamento pós-logout exibe apenas a página index.html .
Protocolo
Se quiser saber mais sobre a saída, leia a documentação do protocolo disponível no OpenID Connect.
Próximos passos
Saiba mais criando um aplicativo Web ASP.NET Core que inicia sessão nos utilizadores na seguinte série de tutoriais com várias partes