C# MVC 5通过仅使用用户名来反向代理身份验证和使用角色
我有一个MVC5网络应用程序。目前,应用程序正在使用个人帐户登录。还存在用于授权的角色。用户使用其用户名和密码登录 问题是这样的。我需要对通过反向代理发出的用户请求进行身份验证和授权C# MVC 5通过仅使用用户名来反向代理身份验证和使用角色,c#,asp.net,authentication,asp.net-mvc-5,asp.net-identity-2,C#,Asp.net,Authentication,Asp.net Mvc 5,Asp.net Identity 2,我有一个MVC5网络应用程序。目前,应用程序正在使用个人帐户登录。还存在用于授权的角色。用户使用其用户名和密码登录 问题是这样的。我需要对通过反向代理发出的用户请求进行身份验证和授权 用户向应用程序发出请求(反向代理url)http://myapp.domain.com 反向代理将进行额外呼叫,并验证用户是否有权访问应用程序内容。(为了简单起见,图中缺少) 如果用户一切正常,调用将重定向到实际的MVC应用程序,其中请求将包含一个带有用户名的头 MVC必须检查请求是否来自反向代理(这样做没有问
- 用户向应用程序发出请求(反向代理url)
http://myapp.domain.com
- 反向代理将进行额外呼叫,并验证用户是否有权访问应用程序内容。(为了简单起见,图中缺少)
- 如果用户一切正常,调用将重定向到实际的MVC应用程序,其中请求将包含一个带有用户名的头
- MVC必须检查请求是否来自反向代理(这样做没有问题,IP检查,加上一些作为头发送的密钥)
- MVC应该读取请求头,获取用户名,对其进行身份验证,并根据其拥有的一个或多个角色对其进行授权
- 如果请求不是来自反向代理,则拒绝请求;如果用户没有适当的角色,则拒绝请求。示例用户是角色访问者,但他正在尝试访问管理员角色内容
- 反向代理将向发送请求
- 在从帐户控制器登录的操作中,我可以实现读取请求的逻辑,并从标题中获取用户名
- 此时,我们知道用户X已通过身份验证,因为反向代理和其他系统将对此进行检查。因此,基本上所有到达的请求都被认为是安全的(来自反向代理服务器)
- 如果数据库中不存在用户名(首次调用应用程序),MVC应用程序将使用伪密码(Password123)创建用户
- 如果数据库中存在用户名,则使用用户名和伪密码Password123
var result=wait SignInManager.PasswordSignInAsync(“用户名”,“密码123”,false,shouldllockout:false)将其登录代码>
- 用户已通过身份验证和授权
你怎么看?因为身份是基于声明的。您不需要任何密码,甚至不需要任何用户对象来验证用户。因此,在Identity中使用存储也是完全可选的。您只需要创建一些声明并根据这些声明授权您的用户。把这个简单的例子当作一个线索:
// imaging this action is called by proxy
public ActionResoult Login()
{
// this custom method extract username from header and check IP and more
var username=_myUserManager.GetUserName();
if(username!=null)
{
// optionally you have own user manager which returns roles from username
// no matter how you store users and roles
string[] roles=_myUserManager.GetUserRoles(username);
// user is valid, going to authenticate user for my App
var ident = new ClaimsIdentity(
new[]
{
// adding following 2 claim just for supporting default antiforgery provider
new Claim(ClaimTypes.NameIdentifier, username),
new Claim("http://schemas.microsoft.com/accesscontrolservice/2010/07/claims/identityprovider", "ASP.NET Identity", "http://www.w3.org/2001/XMLSchema#string"),
// an optional claim you could omit this
new Claim(ClaimTypes.Name, username),
// populate assigned user's role form your DB
// and add each one as a claim
new Claim(ClaimTypes.Role, roles[0]),
new Claim(ClaimTypes.Role, roles[1]),
// and so on
},
DefaultAuthenticationTypes.ApplicationCookie);
// Identity is sign in user based on claim don't matter
// how you generated it
HttpContext.GetOwinContext().Authentication.SignIn(
new AuthenticationProperties { IsPersistent = false }, ident);
// auth is succeed, without needing any password just claim based
return RedirectToAction("MyAction");
}
// invalid user
ModelState.AddModelError("", "We could not authorize you :(");
return View();
}
现在,我们在没有任何密码的情况下对用户进行了授权,因此我们还可以使用Authorize
过滤器:
[Authorize]
public ActionResult Foo()
{
}
// since we injected user roles to Identity we could do this as well
[Authorize(Roles="admin")]
public ActionResult Foo()
{
// since we injected our authentication mechanism to Identity pipeline
// we have access current user principal by calling also
// HttpContext.User
}
注意:您的代理必须处理您的应用程序生成的cookie,并将它们正确地交付给您的用户。因为你的应用程序基于cookie
您可以从my Github repo下载,也可以阅读与您的场景接近的内容 验证后用户如何与您的应用交互?又是代理?或直接访问您的应用程序?身份验证后,用户可以直接访问应用程序
PasswordSignInAsync
将处理该问题。当会话过期或cookie过期时,用户将被重定向到代理并重复该循环。因此,请参阅我的答案。谢谢,听起来不错。但是有一件事,代理不会向MVC应用程序传递任何信息,在对登录用户(windows auth)进行身份验证后,代理只会调用/将用户重定向到应用程序,并添加用户名作为标题。就这样。它从来没有提供任何饼干。因此,现在MVC应用程序拥有一个有效/经过身份验证的用户。它必须让他登录,设置cookie并分配正确的角色。。。。当cookie/会话过期时,通常MVC应用程序会将您重定向到Accoun/Login,而现在您被重定向到代理,循环重复。如果只是一个带有附加头的简单重定向。一切都很好。我们不需要任何额外的东西从代理。身份负责制作饼干。我说过,如果用户总是在代理之后,那么代理服务器必须将生成的cookie传递给用户。