使用MySql对IdentityServer4进行持久化
哈喽大家好,看见网上很少有使用MySql进行持久化的,毕竟又很多坑,说句实话,就连 MySql.Data.EntityFrameworkCore 都有问题,不知道是.net core更新太快还是其它的问题,但毕竟mssql驱动是没问题的,感觉还是私心太大了。不得以之下选择了一个第三方的驱动 Pomelo.EntityFrameworkCore.MySql 驱动,在这里主要是你安装了它,你就又了它的设计器,但你还需要你安装EFCore的设计器,因为你执行dotnet命令迁移的时候还得靠它,好吧,我们继续,在你的应用程序中最好保持这几个包。能多不能少。
<ItemGroup>
<PackageReference Include="IdentityServer4" Version="2.0.0-rc1" />
<PackageReference Include="IdentityServer4.AspNetIdentity" Version="2.0.0-rc1" />
<PackageReference Include="IdentityServer4.EntityFramework" Version="2.0.0-rc1" />
<PackageReference Include="Microsoft.AspNetCore.All" Version="2.0.0" />
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="2.0.0" />
<PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="2.0.0" />
<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="2.0.0" />
<PackageReference Include="Pomelo.EntityFrameworkCore.MySql" Version="2.0.0-rtm-10062" />
<PackageReference Include="Pomelo.EntityFrameworkCore.MySql.Design" Version="1.1.2" />
</ItemGroup>
就这样,在Model里创建两个类,一个是用户、一个是关系,这个是Identity的类。其实这个和IdentityServer是没有多大关系的。主要是为了扩展一些东西,比如你需要其它的字段?
public class ApplicationRole : IdentityRole{}
public class ApplicationUser : IdentityUser{}
随后我们定义IdentityDbContext,将我们自己定义的两个类放进去,它是个泛型的。
public class ApplicationDbContext : IdentityDbContext<ApplicationUser, ApplicationRole, string>
{
public ApplicationDbContext(DbContextOptions<ApplicationDbContext> options)
: base(options)
{
} protected override void OnModelCreating(ModelBuilder builder)
{
base.OnModelCreating(builder);
// Customize the ASP.NET Identity model and override the defaults if needed.
// For example, you can rename the ASP.NET Identity table names and more.
// Add your customizations after calling base.OnModelCreating(builder);
}
}
再之后我们就可以注入到.Net Core的服务里了,IdentityServer的数据库中有三个大类,有AspNet的票据用户、资源的管理、以及一些操作的记录。这里你可以用一个database,你也可以分开。
public void ConfigureServices(IServiceCollection services)
{
// Add framework services.
services.AddDbContext<ApplicationDbContext>(options =>
options.UseMySql(Configuration.GetConnectionString("DefaultConnection"))); services.AddIdentity<ApplicationUser, ApplicationRole>()
.AddEntityFrameworkStores<ApplicationDbContext>()
.AddDefaultTokenProviders(); services.AddMvc(); string migrationsAssembly = typeof(Startup).GetTypeInfo().Assembly.GetName().Name;
services.AddIdentityServer()
.AddConfigurationStore(options =>
{
options.ConfigureDbContext = builder =>
builder.UseMySql(Configuration.GetConnectionString("DefaultConnection"),
sql => sql.MigrationsAssembly(migrationsAssembly));
})
.AddOperationalStore(options =>
{
options.ConfigureDbContext = builder =>
builder.UseMySql(Configuration.GetConnectionString("DefaultConnection"),
sql => sql.MigrationsAssembly(migrationsAssembly)); // this enables automatic token cleanup. this is optional.
options.EnableTokenCleanup = true;
options.TokenCleanupInterval = ;
});
}
随后注册IdentityServer服务,这个里面调用了 InitializeDatabase 方法为了初始化的迁移数据。
public void Configure(IApplicationBuilder app, IHostingEnvironment env)
{
InitializeDatabase(app); if (env.IsDevelopment())
app.UseDeveloperExceptionPage();
else
app.UseExceptionHandler("/Home/Error");
app.UseIdentityServer();
}
这个方法就很有意思了,获取了.net core的服务实例,然后对我的Context进行了更新迁移,直接将Config中的内存数据添加到了数据库中。
private void InitializeDatabase(IApplicationBuilder app)
{
using (var serviceScope = app.ApplicationServices.GetService<IServiceScopeFactory>().CreateScope())
{
serviceScope.ServiceProvider.GetRequiredService<ApplicationDbContext>().Database.Migrate();
serviceScope.ServiceProvider.GetRequiredService<PersistedGrantDbContext>().Database.Migrate(); var context = serviceScope.ServiceProvider.GetRequiredService<ConfigurationDbContext>();
context.Database.Migrate();
if (!context.Clients.Any())
{
foreach (var client in Config.GetClients())
{
context.Clients.Add(client.ToEntity());
}
context.SaveChanges();
} if (!context.IdentityResources.Any())
{
foreach (var resource in Config.GetIdentityResources())
{
context.IdentityResources.Add(resource.ToEntity());
}
context.SaveChanges();
} if (!context.ApiResources.Any())
{
foreach (var resource in Config.GetApiResources())
{
context.ApiResources.Add(resource.ToEntity());
}
context.SaveChanges();
}
}
最后你需要执行三个命令,执行EFCore的数据迁移。
dotnet ef migrations add InitialIdentityServerPersistedGrantDbMigration -c PersistedGrantDbContext -o Data/Migrations/IdentityServer/PersistedGrantDb
dotnet ef migrations add InitialIdentityServerConfigurationDbMigration -c ConfigurationDbContext -o Data/Migrations/IdentityServer/ConfigurationDb
dotnet ef migrations add InitialIdentityServerApplicationDbMigration -c ApplicationDbContext -o Data/Migrations/IdentityServer/ApplicationDb
就这样,生成完毕我们测试一下程序。

Ok,一些正常。
使用MySql对IdentityServer4进行持久化的更多相关文章
- 认证授权:IdentityServer4 - 数据持久化
前言: 前面的文章中IdentityServer4 配置内容都存储到内存中,本篇文章开始把配置信息存储到数据库中:本篇文章继续基于github的代码来实现配置数据持久化到MySQL中 一.基于EFCo ...
- IdentityServer4之持久化很顺手的事
前言 原计划打算在春节期间多分享几篇技术文章的,但到最后一篇也没出,偷懒了吗?算是吧,过程是这样的:每次拿出电脑,在孩姥姥家的院子总有阳光沐浴,看不清屏幕,回屋又有点冷(在强行找理由),于是又带着娃遛 ...
- IdentityServer4.FreeSql 持久化实现
前言 故事是这样开始的: 然后突然又来了句... 扪心自问自从不知道怎么当了 FreeSql 开发群 () 的管理以来, 几乎没有给 FreeSql 做过什么贡献...惭愧惭愧. 借此机会, 似乎可以 ...
- [转]MySQL 5.6 全局事务 ID(GTID)实现原理(三)
原文连接:http://qing.blog.sina.com.cn/1757661907/68c3cad333002s5l.html 原文作者:淘长源 转载注明以上信息 这是 MySQL 5.6 全局 ...
- .NET Core+MySql+Nginx 容器化部署
.NET Core容器化@Docker .NET Core容器化之多容器应用部署@Docker-Compose .NET Core+MySql+Nginx 容器化部署 GitHub-Demo:Dock ...
- mysql+ssl主从复制
一.作为主服务器Master, 会把自己的每一次改动都记录到 二进制日志 Binarylog 中. (从服务器I/O thread会负责来读取master binary log, 然后写入自身rela ...
- Kafka实战-数据持久化
1.概述 经过前面Kafka实战系列的学习,我们通过学习<Kafka实战-入门>了解Kafka的应用场景和基本原理,<Kafka实战-Kafka Cluster>一文给大家分享 ...
- Redis 持久化操作
hash类型 类比:mysql数据库存储数据 持久化操作 以本身的数据以文件形式保存到硬盘中 手动快照持久化 i 备份机制(频率) vi redis.conf save 900 1 900s如果一个 ...
- NET Core+MySql+Nginx
NET Core+MySql+Nginx 容器化部署 .NET Core容器化@Docker.NET Core容器化之多容器应用部署@Docker-Compose.NET Core+MySql+Ngi ...
随机推荐
- Android开发之《libyuv库的使用》
转自:http://bashell.nodemedia.cn/archives/build-google-libyuv-with-ndk-for-android.html 官方网站:https://c ...
- HttpClient-get请求/Post请求/Post-Json/Header
1.Pom文件添加httpClient 依赖 <dependency> <groupId>org.apache.httpcomponents</groupId> & ...
- js new 与 return
前置: 默认情况下, 函数的返回值是 undefined (即没有定义返回值). new 操作符 js 中的 new 操作符,可以是我们像 java 一样,获得一个新的对象,例如: function ...
- SimpleTrigger的使用
SimpleTrigger的作用 在一个指定时间段内执行一次作业任务或是在指定的时间间隔内多次执行作业任务 使用实例1:距离当前时间4s钟后执行,且执行一次 package com.test.quar ...
- Servlet+JSP 对外访问路径配置
servlet类似 servlet配置为: <servlet> <servlet-name>Demo01_OutWrite</servlet-name> ...
- iOS中如何实现准确的倒计时程序 · 九十里
iOS中倒计时程序,考虑线程暂停场景. iOS App进入后台时,GCD线程也会跟着暂停.当程序进入前台后,GCD线程恢复.因而倒计时程序需要考虑这一点,通过加入时间的比对来实现. + (void)c ...
- JavaScript if为true的情况
变量如果不为0,null,undefined,false,都会被处理为true.只要变量有非0的值或是某个对象,数组,字符串,都会认为true
- makefile(3)函数
前言 学习make和makefile的主要目的是分析大型项目的源代码的关系,上一节我们讲述了makefile 中的变量,本节主要学习一下 makefile 中的函数,首先函数肯定可以分为几部分: 内置 ...
- Android 绘制中国地图
最近的版本有这样一个需求: 有 3 个要素: 中国地图 高亮省区 中心显示数字 面对这样一个需求,该如何实现呢? 高德地图 因为项目是基于高德地图来做的,所以很自然而然的想到了高德.但是当查阅高德地图 ...
- 微软亚洲研究院开源图数据库GraphView
我们很高兴地宣布,由微软亚洲研究院系统算法组开发的图数据库GraphView通过GitHub平台开源.GraphView是一款中间件软件,方便用户使用关系数据库SQL Server 或Azure SQ ...