【发布时间】:2014-10-25 01:48:23
【问题描述】:
我正在构建一个多租户 MVC5 应用程序,该应用程序非常遵循示例指南:https://github.com/AzureADSamples/WebApp-MultiTenant-OpenIdConnect-DotNet/
我正在针对 Azure Active Directory 进行身份验证,并拥有自己的角色名称,我在 SecurityTokenvalidated 事件期间将其作为角色声明注入:
SecurityTokenValidated = (context) =>
{
// retriever caller data from the incoming principal
string upn = context.AuthenticationTicket.Identity.FindFirst(ClaimTypes.Name).Value;
string tenantId = context.AuthenticationTicket.Identity.FindFirst("http://schemas.microsoft.com/identity/claims/tenantid").Value;
var databaseConnectionString = RoleEnvironment.GetConfigurationSettingValue("DatabaseConnectionString");
AppAnalyzerUser appAnalyzerUser = null;
using (CloudContext dbContext = new CloudContext(databaseConnectionString))
{
if (dbContext.Office365Accounts.FirstOrDefault(x => x.AzureTokenId == tenantId) == null)
throw new GeneralErrorException("Account not found", "The domain that you used to authenticate has not registered.");
appAnalyzerUser = (from au in dbContext.AppAnalyzerUsers
.Include(x => x.Roles)
where au.UserPrincipalName == upn && au.AzureTokenId == tenantId
select au).FirstOrDefault();
if (appAnalyzerUser == null)
throw new AccountNotFoundException();
}
foreach (var role in appAnalyzerUser.Roles)
{
Claim roleClaim = new Claim(ClaimTypes.Role, role.RoleName);
context.AuthenticationTicket.Identity.AddClaim(roleClaim);
}
return Task.FromResult(0);
},
我已经用 Authorize 属性修饰了一些方法,如下所示:
[Authorize(Roles = "SystemAdministrator"), HttpGet]
public ActionResult Index()
{
return View();
}
并且 authorize 属性正确检测到用户不在该角色中,并将其发送回 Azure 进行身份验证。
但是我看到的是用户已经通过 Azure AD 的身份验证并登录到应用程序。他们没有机会在 Azure 屏幕上选择新的用户帐户进行登录。因此,当它将他们退回到 Azure AD 时,Azure AD 会说“您已经登录”并将他们直接发送回应用程序. SecurityTokenValidated 事件反复触发。
但是用户仍然没有该方法所需的角色,所以他们被退回到 Azure 进行身份验证,显然我们陷入了一个循环。
除了自己编写 Authorize 属性的实现,还有其他方法可以解决这个问题吗?
【问题讨论】:
标签: azure asp.net-mvc-5 authorization owin azure-active-directory