• aspnetcore 应用 接入Keycloak快速上手指南


    登录及身份认证是现代web应用最基本的功能之一,对于企业内部的系统,多个系统往往希望有一套SSO服务对企业用户的登录及身份认证进行统一的管理,提升用户同时使用多个系统的体验,Keycloak正是为此种场景而生。本文将简明的介绍Keycloak的安装、使用,并给出aspnetcore 应用如何快速接入Keycloak的示例。

    Keycloak是什么

    Keycloak是一种面向现代应用和服务的开源IAM(身份识别与访问管理)解决方案

    Keycloak提供了单点登录(SSO)功能,支持OpenID ConnectOAuth 2.0SAML 2.0标准协议,拥有简单易用的管理控制台,并提供对LDAP、Active Directory以及Github、Google等社交账号登录的支持,做到了非常简单的开箱即用。

    官网: https://www.keycloak.org/

    Keycloak常用核心概念介绍

    首先通过官方的一张图来了解下整体的核心概念

    image

    这里先只介绍4个最常用的核心概念:

    1. Users: 用户,使用并需要登录系统的对象

    2. Roles: 角色,用来对用户的权限进行管理

    3. Clients: 客户端,需要接入Keycloak并被Keycloak保护的应用和服务

    4. Realms: 领域,领域管理着一批用户、证书、角色、组等,一个用户只能属于并且能登陆到一个域,域之间是互相独立隔离的, 一个域只能管理它下面所属的用户

    Keycloak服务安装及配置

    安装Keycloak

    Keycloak安装有多种方式,这里使用Docker进行快速安装

    登录后复制

    docker run -d --name keycloak 
        -p 8080:8080 
        -e KEYCLOAK_USER=admin 
        -e KEYCLOAK_PASSWORD=admin 
        jboss/keycloak:13.0.0

    访问http://localhost:8080并点击Administration Console进行登录

     

    image

     

    创建Realm

    首先,我们需要创建一个Realm。Realm是一个隔离的概念,Realm A中的用户与Realm B中的用户完全隔离。创建一个新的realm: demo,后续所有的客户端、用户、角色等都在此realm中创建

    image

    image

    image

    创建客户端
    创建前端应用客户端

    创建一个新的客户端:KeycloakAuthaspnet,Access Type选择confidential

    image

    关于客户端的访问类型(Access Type)

    上面创建的客户端的访问类型分别是confidential,那么为什么分别选择这种类型,实际不同的访问类型有什么区别呢?

    事实上,Keycloak目前的访问类型共有3种:

    • confidential:适用于服务端应用,且需要浏览器登录以及需要通过密钥获取access token的场景。典型的使用场景就是服务端渲染的web系统。
    • public:适用于客户端应用,且需要浏览器登录的场景。典型的使用场景就是前端web系统,包括采用vue、react实现的前端项目等。
    • bearer-only:适用于服务端应用,不需要浏览器登录,只允许使用bearer token请求的场景。典型的使用场景就是restful api。

     

    Access Type 里面选 Confidential,然后才有 Client Secret ,保存之后,会出现Credentials的Tab,记录下这里的secret,后面要用到

    image

    创建用户和角色
    创建角色

    创建2个角色:admin、user

    image

    还可以创建全局的角色

    image

    创建用户

    创建1个用户:geffzhang

    image

    绑定用户和角色
    给geffzhang 用户分配角色admin和user

    image

    aspnetcore 应用集成Keycloak简明指南

    添加 Microsoft.AspNetCore.Authentication.OpenIdConnect  和  Microsoft.AspNetCore.Identity 包

    <Project Sdk="Microsoft.NET.Sdk.Web">

      <PropertyGroup>
         <TargetFramework>net5.0</TargetFramework>
         <UserSecretsId>afab524d-850e-499a-bc13-98f61ca0eb3b</UserSecretsId>
         <DockerDefaultTargetOS>Linux</DockerDefaultTargetOS>
       </PropertyGroup>

      <ItemGroup>
         <PackageReference Include="Microsoft.AspNetCore.Authentication.OpenIdConnect" Version="5.0.5" />
         <PackageReference Include="Microsoft.AspNetCore.Identity" Version="2.2.0" />
         <PackageReference Include="Microsoft.VisualStudio.Azure.Containers.Tools.Targets" Version="1.10.8" />
         <PackageReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Design" Version="5.0.2" />
       </ItemGroup>

    </Project>

    Appsettings.json

    image

    image

    // This method gets called by the runtime. Use this method to add services to the container.
         public void ConfigureServices(IServiceCollection services)
         {
             services.AddControllersWithViews();
            
             services.AddAuthentication(options =>
             {
                 //Sets cookie authentication scheme
                 options.DefaultAuthenticateScheme = CookieAuthenticationDefaults.AuthenticationScheme;
                 options.DefaultSignInScheme = CookieAuthenticationDefaults.AuthenticationScheme;
                 options.DefaultChallengeScheme = OpenIdConnectDefaults.AuthenticationScheme;
             })

            .AddCookie(cookie =>
             {
                 //Sets the cookie name and maxage, so the cookie is invalidated.
                 cookie.Cookie.Name = "keycloak.cookie";
                 cookie.Cookie.MaxAge = TimeSpan.FromMinutes(60);
                 cookie.Cookie.SecurePolicy = CookieSecurePolicy.SameAsRequest;
                 cookie.SlidingExpiration = true;
             })
             .AddOpenIdConnect(options =>
             {
                 /*
                  * ASP.NET core uses the http://*:5000 and https://*:5001 ports for default communication with the OIDC middleware
                  * The app requires load balancing services to work with :80 or :443
                  * These needs to be added to the keycloak client, in order for the redirect to work.
                  * If you however intend to use the app by itself then,
                  * Change the ports in launchsettings.json, but beware to also change the options.CallbackPath and options.SignedOutCallbackPath!
                  * Use LB services whenever possible, to reduce the config hazzle :)
                 */

                //Use default signin scheme
                 options.SignInScheme = CookieAuthenticationDefaults.AuthenticationScheme;
                 //Keycloak server
                 options.Authority = Configuration.GetSection("Keycloak")["ServerRealm"];
                 //Keycloak client ID
                 options.ClientId = Configuration.GetSection("Keycloak")["ClientId"];
                 //Keycloak client secret
                 options.ClientSecret = Configuration.GetSection("Keycloak")["ClientSecret"];
                 //Keycloak .wellknown config origin to fetch config
                 options.MetadataAddress = Configuration.GetSection("Keycloak")["Metadata"];
                 //Require keycloak to use SSL
                 options.RequireHttpsMetadata = false;
                 options.GetClaimsFromUserInfoEndpoint = true;
                 options.Scope.Add("openid");
                 options.Scope.Add("profile");
                 //Save the token
                 options.SaveTokens = true;
                 //Token response type, will sometimes need to be changed to IdToken, depending on config.
                 options.ResponseType = OpenIdConnectResponseType.Code;
                 //SameSite is needed for Chrome/Firefox, as they will give http error 500 back, if not set to unspecified.
                 options.NonceCookie.SameSite = SameSiteMode.Unspecified;
                 options.CorrelationCookie.SameSite = SameSiteMode.Unspecified;
                
                 options.TokenValidationParameters = new TokenValidationParameters
                 {
                     NameClaimType = "name",
                     RoleClaimType = ClaimTypes.Role,
                     ValidateIssuer = true
                 };


             });

            /*
              * For roles, that are defined in the keycloak, you need to use ClaimTypes.Role
              * You also need to configure keycloak, to set the correct name on each token.
              * Keycloak Admin Console -> Client Scopes -> roles -> mappers -> create
              * Name: "role client mapper" or whatever you prefer
              * Mapper Type: "User Client Role"
              * Multivalued: True
              * Token Claim Name: role
              * Add to access token: True
              */

           
             /*
              * Policy based authentication
              */

            services.AddAuthorization(options =>
             {
                 //Create policy with more than one claim
                 options.AddPolicy("users", policy =>
                 policy.RequireAssertion(context =>
                 context.User.HasClaim(c =>
                         (c.Value == "user") || (c.Value == "admin"))));
                 //Create policy with only one claim
                 options.AddPolicy("admins", policy =>
                     policy.RequireClaim(ClaimTypes.Role, "admin"));
                 //Create a policy with a claim that doesn't exist or you are unauthorized to
                 options.AddPolicy("noaccess", policy =>
                     policy.RequireClaim(ClaimTypes.Role, "noaccess"));
             });


             /*
              * Non policy based authentication
              * Uncomment below and comment the policy section
              */
           
             //services.AddAuthorization();

        }

    经过上述的配置,通过oidc 很容易就接入到了Keycloak。具体代码请参见:https://github.com/NanoFabricFX/AspNetCore-keycloak/tree/dotnet5

    运行效果,第一次访问项目会跳转Keycloak登录页

    image

    用户登陆geffzhang

     

    image

    总结

    Keycloak部署及接入简单,轻量的同时功能又不失强大,非常适合企业内部的SSO方案。在Identity Server4 收费的背景之下,微软计划在.NET 6里面继续集成,已经被社区骂的狗血喷头https://devblogs.microsoft.com/aspnet/asp-net-core-6-and-authentication-servers/ 

    相关文章:

    欢迎大家扫描下面二维码成为我的客户,为你服务和上云

  • 相关阅读:
    对象 函数
    流程控制语句 label 从键盘输入 计时器 []中括号的使用
    类型转换 运算符 流程控制语句
    JS的编写的位置 输出语句 注释 字面量和变量 数据类型
    AutoCad 二次开发 .net 之创建Table
    AutoCad 二次开发 .net 之相同块的自动编号
    Java 多线程练习
    C# Winform 自定义控件——竖着的Navbar
    C# Winfrom 自定义控件——带图片的TextBox
    Task CancellationTokenSource和Task.WhenAll的应用
  • 原文地址:https://www.cnblogs.com/shanyou/p/14751793.html
Copyright © 2020-2023  润新知