实现自己的.NET Core配置Provider之EF

《10分钟就能学会.NET Core配置》里详细介绍了.NET Core配置的用法,另外我还开源了自定义的配置Provider:EF配置Provider和Yaml配置Provider。本文先来聊聊EF配置Provider的实现,其中会涉及到EntityFramework Core的知识,不熟悉也没关系,且听我慢慢讲来。

配置执行流程#

在使用配置的时候都是先new ConfigurationBuilder(),最后调用Build()方法赋值给Configuration属性。那我们就从这个Build方法说起。

Build方法做了什么呢,它遍历了所有的配置源,等等,配置源哪来的?还记不记得AddJsonFile,AddCommandLine这些扩展方法,它们做的事情就是将配置源添加到ConfigurationBuild中。每个配置源都有一个Build方法,它返回一个Provider。遍历所有配置源时调用配置源的Build方法,就获得了所有配置源的Provider,最后通过构造函数传给ConfigurationRoot

每个Provider里都有一个Load方法,ConfigurationRoot的构造函数会遍历所有的Provider,调用它的Load方法。Load方法里需要做的就是把配置源里的配置转换为IDictionary<string,string>

了解了配置执行的流程,就可以动手实现自己的Provider了。

EF存储#

Json配置Provider的配置存储在Json文件中,基于EF的Provider的配置则是存储在数据库中,因为使用了EF,我们不需要关心使用的是什么数据库。

在数据库中存储配置不支持嵌套和数组,只是简单的键值对形式,对应数据库表中的两列。使用EF,需要先定义一个实体存储配置,它包含两个属性,对应数据库表中的两列。

Copy
internal class Configuration { public string Key { get; set; } public string Value { get; set; } }

接着需要定义一个ConfigurationDbContext用于存储和访问配置。

Copy
internal class ConfigurationDbContext : DbContext { private EFConfigurationOptionsBuilder Builder { get; } public ConfigurationDbContext(EFConfigurationOptionsBuilder options) : base(options.DbContextOptions.Options) { Builder = options; } public DbSet<Configuration> Configurations { get; set; } }

EFConfigurationOptionsBuilder是自定义的类,它包含2个属性,一个用于指定存储配置表的名称,另一个用于配置数据库连接及其他配置。

EFConfigurationProvider#

自定义Provider可继承ConfigurationProvider实现。在ConfigurationProvider中Load是一个虚方法,自定义Provider需要实现Load方法。

Copy
internal class EFConfigurationProvider : ConfigurationProvider { Action<EFConfigurationOptionsBuilder> OptionsAction { get; } public EFConfigurationProvider(Action<EFConfigurationOptionsBuilder> optionsAction) { OptionsAction = optionsAction; } public override void Load() { var builder = new EFConfigurationOptionsBuilder(); OptionsAction(builder); using (var ctx = new ConfigurationDbContext(builder)) { ctx.Database.EnsureCreated(); Data = ctx.Configurations.ToDictionary(t => t.Key, t => t.Value); } } }

EFConfigurationSource#

EFConfigurationSource继承IConfigurationSource,实现了Build方法,在Build中返回EFConfigurationProvider。

Copy
internal class EFConfigurationSource : IConfigurationSource { private readonly Action<EFConfigurationOptionsBuilder> _optionsAction; public EFConfigurationSource(Action<EFConfigurationOptionsBuilder> optionsAction) { _optionsAction = optionsAction; } public IConfigurationProvider Build(IConfigurationBuilder builder) { return new EFConfigurationProvider(_optionsAction); } }

AddEntityFramework扩展方法#

为添加EF配置源增加一个扩展方法。

Copy
public static class EFConfigurationExtensions { public static IConfigurationBuilder AddEntityFramework(this IConfigurationBuilder builder, Action<EFConfigurationOptionsBuilder> setup) { return builder.Add(new EFConfigurationSource(setup)); } }

使用EF配置Provider#

Copy
var builder = new ConfigurationBuilder() .AddEntityFramework(options => { options.TableName = "configs"; // 这里使用SQLite作为演示 options.DbContextOptions.UseSqlite("Filename=config.db"); }); Configuration = builder.Build();

上面我使用SQLite演示,也可以使用SQL Server、MySql、PostgreSQL等。默认配置表的名称为Configuration。

最后#

本项目已在github上开源,地址:https://github.com/chengxulvtu/Cxlt.Extensions.Configuration

在项目中使用可以执行下面的命令

Copy
Install-Package Cxlt.Extensions.Configuration.EF

Copy
dotnet add package Cxlt.Extensions.Configuration.EF

下篇文章《实现自己的.NET Core配置Provider之Yaml》将讲解Yaml配置Provider的细节。

如果这篇文章对你有帮助,请点赞支持一下,也欢迎关注“chengxulvtu"公众号。

posted @   BobTian  阅读(2737)  评论(0编辑  收藏  举报
编辑推荐:
· Linux系列:如何用 C#调用 C方法造成内存泄露
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 理解Rust引用及其生命周期标识(上)
阅读排行:
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· AI与.NET技术实操系列(二):开始使用ML.NET
· 单线程的Redis速度为什么快?
· Pantheons:用 TypeScript 打造主流大模型对话的一站式集成库
点击右上角即可分享
微信分享提示
CONTENTS