Fork me on Gitee

OAuth2之IdentityServer4实现

OAuth2之IdentityServer4实现

OAuth2之介绍及授权方式中介绍了OAuth2中四种授权方式,这里主要介绍通过使用AspNetCore MVC和IdentityServer4组件构建授权服务器,文章中代码演示的是通过将数据存储在内存中方式实现OAuth授权方式。

IdentityServer4依赖注入

在ConfigureServices方法中添加IdentityServer组件的依赖注入,代码如下

public void ConfigureServices(IServiceCollection services)
{
    services.AddIdentityServer()
        .AddDeveloperSigningCredential() //添加加密证书
        .AddInMemoryPersistedGrants()
        .AddInMemoryApiResources(Config.GetApis())  //添加API资源
        .AddInMemoryIdentityResources(Config.GetIdentityResources())  //添加身份资源
        .AddInMemoryClients(Config.GetClients())  //添加客户端
        .AddTestUsers(Config.GetTestUsers());  //添加测试用户
    services.AddControllersWithViews();
}

在Configure方法中添加IdentityServer中间件,代码如下

public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
    if (env.IsDevelopment())
    {
        app.UseDeveloperExceptionPage();
    }
    else
    {
        app.UseExceptionHandler("/Home/Error");
        app.UseHsts();
    }
    app.UseCors("CorsPolicy");
    app.UseStaticFiles();
    app.UseRouting();
    app.UseIdentityServer();
    app.UseAuthorization();
    app.UseEndpoints(endpoints =>
    {
        endpoints.MapControllerRoute(
            name: "default",
            pattern: "{controller=Home}/{action=Index}/{id?}");
    });
}

基于授权码模式+IdentityServer4实现最简授权服务器

  1. 添加客户端对应的授权模式代码,代码如下

    new Client {
        ClientId = "client1",  //客户端标识
        ClientName = "Client1",  //客户端名称
        AllowedGrantTypes = GrantTypes.Code,  //设置授权方式为授权码
        AccessTokenType = AccessTokenType.Reference,  //访问令牌类型,默认为JWT
        RedirectUris = { "http://localhost:5100/callback" },  //重定向URI
        ClientSecrets = new List<Secret> {  //客户端凭证
            new Secret ("secret".Sha256 ())
        },
        AllowedScopes = new List<string> {  // 允许访问的权限作用域 
            "user_info"
        }
    }
    
  2. 获取授权码,例如

    • Get请求
    GET /connect/authorize
    client_id=client1&
    redirect_uri=http://localhost:5100/callback&
    response_type=code&
    scope=user_info
    
  3. 获取访问令牌,例如

    • Post请求
    POST /connect/token
    
    client_id=client1&
    client_secret=secret&
    grant_type=authorization_code&
    code=FxHmuNWNqWRbShBLs03bsEZOtiMa0vgFNnrHDb-Y67M&
    redirect_uri=http://localhost:5100/callback&
    scope=user_info
    
    • 响应案例
    {
    "access_token": "ea8c351b4357716cbf3289d30e6d10250baf05424414c3afd7af9051f5fe8920",
    "expires_in": 3600,
    "token_type": "Bearer",
    "scope": "user_info"
    }
    

基于简易模式+IdentityServer4实现最简授权服务器

  1. 添加客户端对应的授权模式代码,代码如下

    new Client
    {
        ClientId = "client1",
        ClientName = "Client1",
        AllowedGrantTypes = GrantTypes.Implicit,
        AllowAccessTokensViaBrowser = true,
        RedirectUris = { "http://localhost:5100/callback" },
        AllowedScopes =
        {
            "user_info"
        }
    }
    
  2. 获取访问令牌,例如

    • Get请求
    GET /connect/authorize
    client_id=client1&
    redirect_uri=http://localhost:5100/callback&
    response_type=token&
    scope=user_info
    

基于密码模式+IdentityServer4实现最简授权服务器

  1. 添加客户端对应的授权模式代码,代码如下

    new Client
    {
        ClientId = "client1",
        AllowedGrantTypes = GrantTypes.ResourceOwnerPassword,
        ClientSecrets =
        {
            new Secret("secret".Sha256())
        },
        AllowedScopes =
        {
            "user_info"
        }
    }
    
  2. 获取访问令牌,例如

    • POST请求
    GET /connect/token
    
    "accept: application/json" "content-type: application/x-www-form-urlencoded"
    
    client_id=client1&
    client_secret=secret&
    grant_type=password&
    username=admin&
    password=123&
    scope=user_info
    
    • 响应案例
    {
        "access_token": "eyJhbGciOiJSUzI1NiIsImtpZCI6IjVhYmZiY2M2M2YyNmQxZjE3OTNmOWU1NmY0ZTU0MTE4IiwidHlwIjoiYXQrand0In0.",
        "expires_in": 3600,
        "token_type": "Bearer",
        "scope": "openid"
    }
    

基于客户端模式+IdentityServer4实现最简授权服务器

  1. 添加客户端对应的授权模式代码,代码如下

    new Client
    {
        ClientId = "client1",
        AllowedGrantTypes = GrantTypes.ClientCredentials,
        ClientSecrets =
        {
            new Secret("secret".Sha256())
        },
        AllowedScopes =
        {
            IdentityServerConstants.StandardScopes.OpenId
        }
    }
    
  2. 获取访问令牌,例如

    • POST请求
    POST /connect/token
    
    --user client_id:client_secret
    
    grant_type=client_credentials&
    scopes=user_info
    
    • 响应案例
    {
        "access_token": "eyJhbGciOiJSUzI1NiIsImtpZCI6IjVhYmZiY2M2M2YyNmQxZjE3OTNmOWU1NmY0ZTU0MTE4IiwidHlwIjoiYXQrand0In0.",
        "expires_in": 3600,
        "token_type": "Bearer",
        "scope": "user_info"
    }
    

参考文档

posted @ 2020-06-11 16:40  三人游丶88  阅读(350)  评论(0)    收藏  举报