ASP Core 3.0 API令牌自定义令牌身份验证(不是jwt!)

斯科特·莫尼兹(Scott Moniz)

我们有一个ASP CORE 3 API项目,需要使用API​​令牌进行保护。这些API令牌将通过数据库进行配置和加载,但是作为概念证明,我们将对测试进行硬编码。我们为令牌授权而研究的所有内容均涉及JWT。我们不想使用JWT。我们只需提供允许访问我们的API的API密钥-然后用户可以通过在标头中传递令牌(例如X-CUSTOM-TOKEN:abcdefg)来调用API方法。

如何修改startup.cs和管道,以便在每次请求时都检查此X-CUSTOM-TOKEN标头?朝着正确方向的一个简单观点就很好。

编辑:好的,这似乎是一个不错的开始!非常感谢!

您的示例似乎表明用户API令牌是用户令牌。我们的要求是,我们需要一个API密钥才能使用该API,然后还需要一个用户令牌才能调用某些控制器。

示例:myapi.com/Auth/SSO(传递API令牌和用户信息以登录,返回用户信息+用户令牌)

myapi.com/Schedule/Create(同时需要API令牌标头和带有用户令牌的标头)

您能否建议如何修改代码以支持此操作?

负数

您可以为此场景创建自定义身份验证方案,因为已经有内置的Authentication中间件。另外,自定义身份验证方案允许您与内置的身份验证/授权子系统集成。您不必实现自己的挑战/禁止逻辑。

例如,创建如下的处理程序和选项:

public class MyCustomTokenAuthOptions : AuthenticationSchemeOptions
{
    public const string DefaultScemeName= "MyCustomTokenAuthenticationScheme";
    public string  TokenHeaderName{get;set;}= "X-CUSTOM-TOKEN";
}

public class MyCustomTokenAuthHandler : AuthenticationHandler<MyCustomTokenAuthOptions>
{
    public MyCustomTokenAuthHandler(IOptionsMonitor<MyCustomTokenAuthOptions> options, ILoggerFactory logger, UrlEncoder encoder, ISystemClock clock) 
        : base(options, logger, encoder, clock) { }

    protected override Task<AuthenticateResult> HandleAuthenticateAsync()
    {
        if (!Request.Headers.ContainsKey(Options.TokenHeaderName))
            return Task.FromResult(AuthenticateResult.Fail($"Missing Header For Token: {Options.TokenHeaderName}"));

        var token = Request.Headers[Options.TokenHeaderName];
        // get username from db or somewhere else accordining to this token
        var username= "Username-From-Somewhere-By-Token";
        var claims = new[] {
            new Claim(ClaimTypes.NameIdentifier, username),
            new Claim(ClaimTypes.Name, username),
            // add other claims/roles as you like
        };
        var id = new ClaimsIdentity(claims, Scheme.Name);
        var principal = new ClaimsPrincipal(id);
        var ticket = new AuthenticationTicket(principal, Scheme.Name);
        return Task.FromResult(AuthenticateResult.Success(ticket));
    }
}

然后在启动时配置此身份验证方案:

services.AddAuthentication(MyCustomTokenAuthOptions.DefaultScemeName)
    .AddScheme<MyCustomTokenAuthOptions,MyCustomTokenAuthHandler>(
        MyCustomTokenAuthOptions.DefaultScemeName,
        opts =>{
            // you can change the token header name here by :
            //     opts.TokenHeaderName = "X-Custom-Token-Header";
        }
    );

同样不要忘记AuthenticationConfigure(IApplicationBuilder app, IWebHostEnvironment env)方法中启用中间件

    app.UseRouting();

    app.UseAuthentication();       // add this line, the order is important
    app.UseAuthorization(); 

    app.UseEndpoints(endpoints =>{  ... });

最后,保护您的端点,例如:

[Authorize(AuthenticationSchemes=MyCustomTokenAuthOptions.DefaultScemeName)]
public IActionResult ScretApi()
{
    return new JsonResult(...);
}

或直接使用Authorize(),因为我们已将MyCustomTokenAuth Scheme设置为默认身份验证方案:

[Authorize()]
public IActionResult ScretApi()
{
    return new JsonResult(...);
}

[编辑]

我们的要求是,我们需要一个API密钥才能使用该API,然后还需要一个用户令牌才能调用某些控制器。

好。假设我们有一个TokenChecker检查api密钥和令牌正确的(由于我不知道具体的业务逻辑,所以我只true在这里返回):

public static class TokenChecker{
    public static Task<bool> CheckApiKey(StringValues apiKey) {
        return Task.FromResult(true);// ... return true/false according to the business
    }

    public static Task<bool> CheckToken(StringValues userToken) {
        return Task.FromResult(true);// ... return true/false according to the business
    }
}

并更改上述身份验证方案以检查ApiKey和UserToken标头,如下所示:

public class MyCustomTokenAuthOptions : AuthenticationSchemeOptions
{
    public const string DefaultScemeName= "MyCustomTokenAuthenticationScheme";
    public string  ApiKeyHeaderName{get;set;}= "X-Api-Key";
    public string  UserTokenHeaderName{get;set;}= "X-User-Token";
}

public class MyCustomTokenAuthHandler : AuthenticationHandler<MyCustomTokenAuthOptions>
{
    public MyCustomTokenAuthHandler(IOptionsMonitor<MyCustomTokenAuthOptions> options, ILoggerFactory logger, UrlEncoder encoder, ISystemClock clock) 
        : base(options, logger, encoder, clock) { }

    protected override async Task<AuthenticateResult> HandleAuthenticateAsync()
    {
        if (!Request.Headers.ContainsKey(Options.ApiKeyHeaderName))
            return AuthenticateResult.Fail($"Missing Header For Token: {Options.ApiKeyHeaderName}");
        if (!Request.Headers.ContainsKey(Options.UserTokenHeaderName))
            return AuthenticateResult.Fail($"Missing Header For Token: {Options.UserTokenHeaderName}");

        var apiKey= Request.Headers[Options.ApiKeyHeaderName];
        var userToken = Request.Headers[Options.UserTokenHeaderName];
        var succeeded= await TokenChecker.CheckToken(userToken) && await TokenChecker.CheckApiKey(apiKey);
        if(!succeeded ){ return AuthenticateResult.Fail("incorrect ApiKey or UserToken"); }

        var username = "the-username-from-user-token"; //e.g. decode the userToken header
        var claims = new[] {
            new Claim(ClaimTypes.NameIdentifier, username),
            new Claim(ClaimTypes.Name, username),
            // add other claims/roles as you like
        };
        var id = new ClaimsIdentity(claims, Scheme.Name);
        var principal = new ClaimsPrincipal(id);
        var ticket = new AuthenticationTicket(principal, Scheme.Name);
        return AuthenticateResult.Success(ticket);
    }
}

并更改您的Auth / SSO端点以返回用户令牌:

public class AuthController: Controller
{
    private readonly MyCustomTokenAuthOptions _myCustomAuthOpts;
    // inject the options so that we can know the actual header name
    public AuthController(IOptionsMonitor<MyCustomTokenAuthOptions> options)
    {
        this._myCustomAuthOpts= options.CurrentValue;
    }

    [HttpPost("/Auth/SSO")]
    public async System.Threading.Tasks.Task<IActionResult> CreateUserTokenAsync()
    {
        var apiKeyHeaderName =_myCustomAuthOpts.ApiKeyHeaderName ;
        if (!Request.Headers.ContainsKey(apiKeyHeaderName))
            return BadRequest($"Missing Header For Token: {apiKeyHeaderName}");

        // check key
        var succeeded = await TokenChecker.CheckApiKey(Request.Headers[apiKeyHeaderName]);
        if(!succeeded)
            return BadRequest($"Incorrect Api Key");
        return Json(... {userInfo, apiKey} ... );
    }
}

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章

来自分类Dev

将自定义验证添加到ASP.NET Core的JWT令牌中?

来自分类Dev

具有自定义身份验证类型的ASP.NET Core JWT

来自分类Dev

ASP.NET Core中的承载令牌身份验证

来自分类Dev

NET Core中如何使用自定义策略架构实现jwt令牌库身份验证以进行授权?

来自分类Dev

如何在ASP.NET Core(不是旧版本!)中实现自定义UserStore(或自定义身份验证)。

来自分类Dev

如何在ASP.NET Core(不是旧版本!)中实现自定义UserStore(或自定义身份验证)。

来自分类Dev

ASP.Net Core JWT令牌验证

来自分类Dev

在ASP.NET Core中使用Authorize属性和自定义Cookie身份验证

来自分类Dev

ASP.NET Core 3.1的自定义身份验证处理程序的授权失败?

来自分类Dev

ASP.Net Core中的自定义身份验证机制

来自分类Dev

在 Asp.Net Core 中实现自定义的 2 因素身份验证机制

来自分类Dev

ASP.NET CORE 中的自定义身份验证和更新声明

来自分类Dev

Firebase 3:使用.net和C#创建自定义身份验证令牌

来自分类Dev

Firebase自定义令牌身份验证(Firebase版本3)

来自分类Dev

.NET Core 3 Azure AD身份验证的自定义角色

来自分类Dev

如何通过特定用户的Bearer令牌访问与S3存储桶连接的AWS CloudFront(JWT自定义身份验证)

来自分类Dev

在.NET Core Web API中使用自定义属性进行JWT身份验证

来自分类Dev

在Asp.net core / 5中使用策略库进行令牌身份验证

来自分类Dev

在 ASP.NET Core 2 中使用令牌或 Open ID Connect 进行身份验证

来自分类Dev

Asp.Net Core 2 中基于令牌的身份验证

来自分类Dev

具有基于自定义角色的授权的ASP.Net Core 3.0 Windows身份验证

来自分类Dev

Auth0 与 .Net Core ASP MVC 到 WebAPI 身份验证

来自分类Dev

ASP Net Core Web API自定义模型验证

来自分类Dev

当使用ASP.NET Core Web API中没有身份的cookie身份验证时,如何在登录时刷新CSRF令牌

来自分类Dev

如何使用带有自定义身份验证的AWS Cognito创建临时的s3上传安全令牌

来自分类Dev

我的ASP.NET Core App Service Web API如何同时支持AAD承载令牌和客户端证书身份验证?

来自分类Dev

ASP.NET Core 1.0。不记名令牌,无法访问自定义声明

来自分类Dev

使用 ASP.NET Core Web API 的 Facebook JWT 身份验证

来自分类Dev

响应 JWT 错误的身份验证 Asp.Net Core Web Api

Related 相关文章

  1. 1

    将自定义验证添加到ASP.NET Core的JWT令牌中?

  2. 2

    具有自定义身份验证类型的ASP.NET Core JWT

  3. 3

    ASP.NET Core中的承载令牌身份验证

  4. 4

    NET Core中如何使用自定义策略架构实现jwt令牌库身份验证以进行授权?

  5. 5

    如何在ASP.NET Core(不是旧版本!)中实现自定义UserStore(或自定义身份验证)。

  6. 6

    如何在ASP.NET Core(不是旧版本!)中实现自定义UserStore(或自定义身份验证)。

  7. 7

    ASP.Net Core JWT令牌验证

  8. 8

    在ASP.NET Core中使用Authorize属性和自定义Cookie身份验证

  9. 9

    ASP.NET Core 3.1的自定义身份验证处理程序的授权失败?

  10. 10

    ASP.Net Core中的自定义身份验证机制

  11. 11

    在 Asp.Net Core 中实现自定义的 2 因素身份验证机制

  12. 12

    ASP.NET CORE 中的自定义身份验证和更新声明

  13. 13

    Firebase 3:使用.net和C#创建自定义身份验证令牌

  14. 14

    Firebase自定义令牌身份验证(Firebase版本3)

  15. 15

    .NET Core 3 Azure AD身份验证的自定义角色

  16. 16

    如何通过特定用户的Bearer令牌访问与S3存储桶连接的AWS CloudFront(JWT自定义身份验证)

  17. 17

    在.NET Core Web API中使用自定义属性进行JWT身份验证

  18. 18

    在Asp.net core / 5中使用策略库进行令牌身份验证

  19. 19

    在 ASP.NET Core 2 中使用令牌或 Open ID Connect 进行身份验证

  20. 20

    Asp.Net Core 2 中基于令牌的身份验证

  21. 21

    具有基于自定义角色的授权的ASP.Net Core 3.0 Windows身份验证

  22. 22

    Auth0 与 .Net Core ASP MVC 到 WebAPI 身份验证

  23. 23

    ASP Net Core Web API自定义模型验证

  24. 24

    当使用ASP.NET Core Web API中没有身份的cookie身份验证时,如何在登录时刷新CSRF令牌

  25. 25

    如何使用带有自定义身份验证的AWS Cognito创建临时的s3上传安全令牌

  26. 26

    我的ASP.NET Core App Service Web API如何同时支持AAD承载令牌和客户端证书身份验证?

  27. 27

    ASP.NET Core 1.0。不记名令牌,无法访问自定义声明

  28. 28

    使用 ASP.NET Core Web API 的 Facebook JWT 身份验证

  29. 29

    响应 JWT 错误的身份验证 Asp.Net Core Web Api

热门标签

归档