(十一)React Ant Design Pro + .Net5 WebApi:后端环境搭建-IdentityServer4(三)持久化
2022-04-14 14:55
1976 查看
##一、前言 IdentityServer配合EFCore持久化,框架已经为我们准备了两个上下文:
ConfigurationDbContext
:配置数据(资源、客户端、身份等)PersistedGrantDbContext
:操作数据(授权码、访问令牌、刷新令牌等)
用户持久化可以自定义一套逻辑,But,我们直接用微软的Identity,再新建一个用户上下文:
ApplicationDbContext
:用户数据(用户、角色等)
##二、持久化 ####1、新建认证服务 新建一个MVC工程,目录结构跟上篇内存化大致一样,
IdentityServer4.Persistence安装所需包:
IdentityServer4
IdentityServer4.EntityFramework
Microsoft.EntityFrameworkCore.Tools
Npgsql.EntityFrameworkCore.PostgreSQL
(PostgreSQL)IdentityServer4.AspNetIdentity
(IdentityServer4支持微软Indentity)Microsoft.AspNetCore.Identity.EntityFrameworkCore
(Identity支持EF)
####2、新建用户上下文
//IdentityUser实际肯定是需要拓展的,还有一些自定义等功能,Demo这儿就不费劲了,随后要挪到正式的环境,用到再细说 public class ApplicationDbContext : IdentityDbContext<IdentityUser> { public ApplicationDbContext(DbContextOptions<ApplicationDbContext> options) : base(options) { } protected override void OnModelCreating(ModelBuilder builder) { base.OnModelCreating(builder); } }
####3、Startup.cs 配置持久化
public void ConfigureServices(IServiceCollection services) { services.AddControllersWithViews(); //读取数据库连接 var connectionString = Configuration.GetSection("DB").Value; if (connectionString == "") { throw new Exception("数据库配置异常"); } /**********************************IdentityServer4持久化配置**********************************/ var migrationsAssembly = typeof(Startup).GetTypeInfo().Assembly.GetName().Name; //添加用户数据上下文 ApplicationDbContext services.AddDbContext<ApplicationDbContext>(options => options.UseNpgsql(connectionString)); services.AddIdentity<IdentityUser, IdentityRole>() .AddEntityFrameworkStores<ApplicationDbContext>() .AddDefaultTokenProviders(); //添加配置数据上下文 ConfigurationDbContext、操作数据上下文 PersistedGrantDbContext、用户持久化 var builder = services.AddIdentityServer() .AddConfigurationStore(options => { options.ConfigureDbContext = builder => { builder.UseNpgsql(connectionString, sql => sql.MigrationsAssembly(migrationsAssembly)); }; }) .AddOperationalStore(options => { options.ConfigureDbContext = builder => { builder.UseNpgsql(connectionString, sql => sql.MigrationsAssembly(migrationsAssembly)); }; //token配置 options.EnableTokenCleanup = true; options.TokenCleanupInterval = 30; }) .AddAspNetIdentity<IdentityUser>() .AddDeveloperSigningCredential(); }
####4、迁移到数据库 程序包管理器控制台,依次输入一下命令回车:
add-migration InitialPersisted -c PersistedGrantDbContext -o Migrations/Persisted
update-database -Context PersistedGrantDbContext
add-migration InitialConfiguration -c ConfigurationDbContext -o Migrations/Configuration
update-database -Context ConfigurationDbContext
add-migration InitialApplication -c ApplicationDbContext -o Migrations/Application
update-database -Context ApplicationDbContext
数据库表、ER关系图 ####5、初始化种子数据 新建
SeedData.cs,初始化种子数据,使用之前在
InMemoryConfig.cs配置好的内存数据
public class SeedData { public static void InitData(IApplicationBuilder serviceProvider) { using (var scope = serviceProvider.ApplicationServices.CreateScope()) { //初始化种子数据:配置、资源、客户端等 scope.ServiceProvider.GetRequiredService<PersistedGrantDbContext>().Database.Migrate(); { var context = scope.ServiceProvider.GetRequiredService<ConfigurationDbContext>(); context.Database.Migrate(); InitSeedData(context); } //初始化种子数据:用户 { var context = scope.ServiceProvider.GetRequiredService<ApplicationDbContext>(); context.Database.Migrate(); var userManager = scope.ServiceProvider.GetRequiredService<UserManager<IdentityUser>>(); foreach (var user in InMemoryConfig.GetTestUser()) { var find = userManager.FindByNameAsync(user.Username).Result; if (find == null) { IdentityUser u = new IdentityUser() { UserName = user.Username }; //密码格式严格(至少一个非字母字符、至少一位0-9数字) var ret = userManager.CreateAsync(u, "WinterSir123!").Result; if (ret.Succeeded) { userManager.AddClaimsAsync(u, user.Claims); } } } } } } private static void InitSeedData(ConfigurationDbContext context) { if (!context.Clients.Any()) { foreach (var client in InMemoryConfig.GetClients()) { context.Clients.Add(client.ToEntity()); } context.SaveChanges(); } if (!context.IdentityResources.Any()) { foreach (var resource in InMemoryConfig.IdentityResources) { context.IdentityResources.Add(resource.ToEntity()); } context.SaveChanges(); } if (!context.ApiResources.Any()) { foreach (var resource in InMemoryConfig.GetApiResources()) { context.ApiResources.Add(resource.ToEntity()); } context.SaveChanges(); } if (!context.ApiScopes.Any()) { foreach (var resource in InMemoryConfig.GetApiScopes()) { context.ApiScopes.Add(resource.ToEntity()); } context.SaveChanges(); } } }
调用代码放这里,认证服务启动时初始化,之前内存模式配置持久化到数据库 ####6、修改登录、注销代码**
其实我也没弄白为啥要改登录那块,一般情况都是用框架原生提供的方法才对,百度谷歌不得其解,大佬可以指点一下
##三、效果图 **可以看到我们必须要用新密码WinterSir123!才能登录,匹配是已经持久化数据库的信息 ##四、前任栽树,后人乘凉 https://zhuanlan.zhihu.com/p/352497277 ##五、代码已上传 https://github.com/WinterSir/IdentityServer4.GrantTypesDemo
相关文章推荐
- 3分钟搭建Ant Design Pro前端开发环境( MyClouds的前端选型)
- React+Ant Design开发环境搭建的实现步骤
- 极客react之Ant Design Pro系列快速入门(二)--登录与默认路径篇
- 极客react之Ant Design Pro系列快速入门(六)--绑定model
- ant-design环境搭建
- ant design环境搭建过程中遇到的问题--Windows-dva-cli
- 极客react之Ant Design Pro系列快速入门(七)-- 使用新的布局
- 【react自制全家桶】一、Webstrom+React+Ant Design+echarts搭建react项目
- 从零开始使用webpack(4.x)+bable+react+ant-design配置单页面应用开发环境(附模板)
- ant design pro 的model,service,connect的使用以及如何调取后端服务器的数据并渲染到本地
- 搭建express+reactjs前后端分离开发环境
- 极客react之Ant Design Pro系列快速入门(一)--启动篇
- 极客react之Ant Design Pro系列快速入门(三)--菜单与权限
- react+ant design pro得首次使用
- 使用Fiddler搭建Asp.net webapi与Android/IOS调试环境
- 极客react之Ant Design Pro系列快速入门(四)--界面新增
- react+webpack+wepack-dev-server的环境中ant design图标离线的方法
- ant design pro 2.0 新页面探索 umi 页面404 react
- ant design后台模板-1.前端环境搭建
- react(ant-design-pro)路由-router踩坑