访问/保护休息服务oAuth2

时间:2018-01-03 20:10:37

标签: c# asp.net-web-api oauth-2.0 identityserver4

我正在尝试编写一个Restful服务,它有多个端点,如

假设每个端点呼叫都由角色担保。

  1. GetEmployees(Role / Claim = Employee.Readonly或Employee.Edit或Employee.Admin)
  2. AddEmployee(Role / Claim = Employee.Edit或Employee.Admin)
  3. UpdateEmployee(Role / Claim = Employee.Edit或Employee.Admin)
  4. DeleteEmployee(Role / Claim = Employee.Admin)
  5. 使用Implicit流程,只需检查角色声明就可以了。我们已经完成了 我的困惑是客户端凭据流,如何将范围映射到角色?

1 个答案:

答案 0 :(得分:0)

让我们假设客户端凭证方法存在以下情况:

var client = new TokenClient(
            BaseAddress + "/connect/token",
            "clientId",
            "clientSecret");

var result = client.RequestClientCredentialsAsync(scope: "my.api").Result;

var accessToken = result.AccessToken;

var client = new HttpClient();
client.SetBearerToken(accessToken);
var result = client.GetStringAsync("https://protectedapiaddress/api/data/getdata").Result;

其中BaseAddress是您的IDS地址。

当然,您必须使用适当的流程(Client Credentials)在IDS客户端列表中注册您的客户端,并且范围只是可选的,但我想您将需要一个。

然后在API方面,您可以使用新的Policy-based authorization

API方法:

[HttpGet]
[Authorize(Policy = "AdminUser")]
[Route("getdata")]
public Data GetData()
{
  // some code here
}

授权要求:

public class AdminUserRequirement : AuthorizationHandler<AdminUserRequirement>, IAuthorizationRequirement
{
    protected override Task HandleRequirementAsync(AuthorizationHandlerContext context, AdminUserRequirement requirement)
    {
        if (!context.User.HasClaim(<'Your rule'>))
        {
            context.Fail();
        }
        else
        {
            context.Succeed(requirement);
        }
        return Task.FromResult(0);
    }
}

在声明中你会有

    {
       "scope" : "my.api"
       "clientId" : "clientId"
    }

等等。然后你可以应用规则。

编辑:忘记提及 - 您必须在Startup.cs中注册政策

public void ConfigureServices(IServiceCollection services)
{
    services
            .AddMvcCore()
            .AddAuthorization(options =>
            {
                    options.AddPolicy("AdminUser",
                    policy => policy.Requirements.Add(new AdminUserRequirement()));
            });

    // More code here

}