首页 文章

Web Api OWIN - 如何在每个请求上验证令牌

提问于
浏览
8

我有两个申请

  • 客户端应用程序构建在ASP.NET MVC上

  • 在Web API OWIN上构建身份验证服务器

计划身份验证如下

  • 对于用户登录,客户端应用程序将向具有登录凭据的身份验证服务器发出请求 .

  • Authication服务器将生成令牌并将发送回客户端应用程序 .

  • 客户端应用程序将该令牌存储在本地存储中 .

  • 为每个后续请求客户端应用程序将附加的令牌保存在请求标头中的本地存储中 .

NOW, ON SERVER SIDE OF CLEINT APP I NEED TO VALIDATE THAT TOKEN COMES WITH EACH REQUEST IS NOT TEMPERED.

  • 请建议我如何在每个请求中验证令牌,因为我不知道OWIN用于生成令牌的密钥 .

  • 编写代码以在客户端应用程序上验证令牌是正确的,或者它应该在身份验证服务器上 .

  • 我打算转移所有用户管理代码,如注册用户,将密码更改为认证服务器,以便我们可以将其重新用于不同的客户端应用程序 - 这是正确的设计实践吗?

到目前为止,我已经编写了下面的代码来创建一个POC .

========================= OWIN配置========

[assembly: OwinStartup(typeof(WebApi.App_Start.Startup))]
    namespace WebApi.App_Start
    {
        public class Startup
        {
            public void Configuration(IAppBuilder app)
            {
                HttpConfiguration config = new HttpConfiguration();

                ConfigureOAuth(app);

                WebApiConfig.Register(config);
                app.UseCors(Microsoft.Owin.Cors.CorsOptions.AllowAll);
                app.UseWebApi(config);
            }

            public void ConfigureOAuth(IAppBuilder app)
            {
                OAuthAuthorizationServerOptions OAuthServerOptions = new OAuthAuthorizationServerOptions()
                {
                    AllowInsecureHttp = false,
                    TokenEndpointPath = new PathString("/token"),
                    AccessTokenExpireTimeSpan = TimeSpan.FromDays(1),
                    Provider = new SimpleAuthorizationServerProvider(),

         };

         // Token Generation

                app.UseOAuthAuthorizationServer(OAuthServerOptions);
                app.UseOAuthBearerAuthentication(new 
 OAuthBearerAuthenticationOptions());

            }
        }
    }

==============================oAuth Provided========================

 public class SimpleAuthorizationServerProvider: OAuthAuthorizationServerProvider
    {
        public override async Task ValidateClientAuthentication(OAuthValidateClientAuthenticationContext context)
        {
            context.Validated(); 
        }

        public override async Task GrantResourceOwnerCredentials(OAuthGrantResourceOwnerCredentialsContext context)
        {


            context.OwinContext.Response.Headers.Add("Access-Control-Allow-Origin", new[] { "*" });

            using (AuthRepository _repo = new AuthRepository())
            {
                IdentityUser user =  _repo.FindUser(context.UserName, context.Password);

                if (user == null)
                {
                    context.SetError("invalid_grant", "The user name or password is incorrect.");
                    return;
                }
            }

            var identity = new ClaimsIdentity(context.Options.AuthenticationType);
            identity.AddClaim(new Claim("sub", context.UserName));
            identity.AddClaim(new Claim("role", "user"));

            context.Validated(identity);

        }
    }

请帮忙,

谢谢,

@保罗

4 回答

  • 2

    使用JSON Web Tokens(JWT)和 claims identities ,而不是需要跟踪已发布令牌的随机令牌 .

    JWT就像是由受信任的机构颁发的护照 . 护照已签名/盖章,您可以验证该护照是由该受信任的机构颁发的,并且未被篡改 . 这意味着,可以验证令牌中存在的访问权限声明的完整性,而无需将状态保持在任何位置 . 在信任应用程序和权限之间需要进行的唯一通信是权限的公钥(用于签署令牌)的初始(安全)下载 .

    建议您使用标准声明架构,例如OpenID Connect(http://openid.net/specs/openid-connect-core-1_0.html#StandardClaims

    一本关于这个主题的好书帮助我理解了所有这些概念,可以在这里找到:A Guide to Claims-Based Identity and Access Control .

  • 0

    请建议我如何在每个请求中验证令牌,因为我不知道OWIN用于生成令牌的密钥 .

    您当前的设置,如果您已将 app.UseOAuthBearerAuthentication() 添加到owin管道,将根据每个请求传递的承载令牌对用户进行身份验证 . 然后可以通过 HttpContext.Current.User 找到当前用户 .

    使用 Authorize 属性然后决定在某些 endpoints 上授权哪些用户 . 这是一个允许具有"user"角色的用户访问的示例

    [Authorize(Roles="user")]
    public class ValuesController : ApiController
    {
    }
    

    编写代码以验证客户端应用程序上的令牌是正确的,还是应该在身份验证服务器上 .

    NO ,你不需要知道所有这些 . 而且,为什么要在客户端验证令牌?

    我打算转移所有用户管理代码,如注册用户,将密码更改为认证服务器,以便我们可以将其重新用于不同的客户端应用程序 - 这是正确的设计实践吗?

    重用令牌提供程序很常见 . 为什么要为每种应用发明轮子? Build 一个伟大的,或使用第三方,并在您的应用程序中重用它 .

  • 1

    验证令牌未被篡改的一种方法是使用非对称密钥对对其进行签名,Identity Server使用此方法,如here所示 .

    在您的情况下,如果要滚动自己的身份验证,则需要自己实现此功能,并检查可能在自定义中间件中的令牌有效的每个请求 .

  • 0

    如果您在 localStoragecreatesendbacksave 并且 JWT 令牌的所有内容都是正确的,您必须知道 .Net 中有许多方法可以控制每个请求 .

    服务器端控制:

    • 如果您正在使用 Web API Core ,在核心中您可以创建在运行时作为pipline运行的 Middleware ,并且您可以提供请求的上下文和检查令牌,以获取更多信息检查:This .

    • 如果你使用 Asp.net MVC ,你可以在MVC中使用 ActionFilter (Asp.Net-Core也有更多的预先ActionFilter),每个请求都会通过,你可以检查每个thisng的abount请求,有关更多信息,请查看:This .

    ClientSide Conftolling:

    • 之后你从服务器端登录后给你令牌,你必须保存 localstorage 中的数据,你的浏览器会根据请求检查数据,他们的优势是 Expireation ,并且 token 中的每个都喜欢这个问题保存在 localstorage 中你和浏览器都可以使用这个更多信息检查:This .

    祝好运 .

相关问题