14 | 自定义配置数据源:低成本实现定制化配置方案

这一节讲解如何定义自己的数据源,来扩展配置框架

扩展步骤

1、实现 IConfigurationSource

2、实现 IConfigurationProvider

3、实现 AddXXX 扩展方法,用来作为注入的快捷方式

引用以下两个包:

  • Microsoft.Extensions.Configuration
  • Microsoft.Extensions.Configuration.Abstractions

首先定义一个 MyConfigurationSource

namespace ConfigurationCustom
{
class MyConfigurationSource : IConfigurationSource
{
public IConfigurationProvider Build(IConfigurationBuilder builder)
{
return new MyConfigurationProvider();
}
}
}

接着是 MyConfigurationProvider

namespace ConfigurationCustom
{
// ConfigurationProvider 集成自 IConfigurationProvider
class MyConfigurationProvider : ConfigurationProvider
{ Timer timer; public MyConfigurationProvider() : base()
{
// 用一个线程模拟配置发生变化,每三秒钟执行一次,告诉我们要重新加载配置
timer = new Timer();
timer.Elapsed += Timer_Elapsed;
timer.Interval = 3000;
timer.Start();
} private void Timer_Elapsed(object sender, ElapsedEventArgs e) => Load(true); public override void Load() => Load(false); /// <summary>
/// 加载数据
/// </summary>
/// <param name="reload">是否重新加载数据</param>
void Load(bool reload)
{
// Data 表示 Key-value 数据,这是由 ConfigurationProvider 提供的一个数据承载的集合
// 我们把最新的时间填充进去
Data["lastTime"] = DateTime.Now.ToString();
if (reload)
{
base.OnReload();
}
}
}
}

实际上到此扩展就已经完成了,可以通过 builder.AddXXX 这个方法来把 source 注入进来

namespace ConfigurationCustom
{
class Program
{
static void Main(string[] args)
{
var builder = new ConfigurationBuilder();
builder.Add(new MyConfigurationSource()); var configRoot = builder.Build();
Console.WriteLine($"lastTime:{configRoot["lastTime"]}"); Console.ReadKey();
}
}
}

启动程序,输出如下:

lastTime:2020/3/1 22:39:36

这里可以看到,输出最新的时间

但是如果这样去分发配置源的包的话,需要把 MyConfigurationSource

定义为 public,否则使用方式没办法引用到这个类

那么就可以通过扩展方法的方式来保障不需要暴露 ConfigSource

定义一个扩展方法 AddMyConfiguration

namespace Microsoft.Extensions.Configuration
{
public static class MyConfigurationBuilderExtensions
{
public static IConfigurationBuilder AddMyConfiguration(this IConfigurationBuilder builder)
{
builder.Add(new MyConfigurationSource());
return builder;
}
}
}

首先把扩展方法的命名空间放在 config 的命名空间,而不是自己的命名空间,这样方便在引用的时候直接使用而无需加载具体的命名空间

另外一个可以把 Provider 定义为 internal 的,默认是 internal,如果说分发到第三方的话,internal 的类是不能被引用的,这样就意味着只需要暴露一个扩展方法,而不需要暴露具体的配置源的实现

class MyConfigurationProvider : ConfigurationProvider

如何使用呢,其实很简单

只需要在 builder.Add 的时候使用 builder.AddMyConfiguration 就可以了,这样达到的效果是一样的

namespace ConfigurationCustom
{
class Program
{
static void Main(string[] args)
{
var builder = new ConfigurationBuilder();
//builder.Add(new MyConfigurationSource());
builder.AddMyConfiguration(); var configRoot = builder.Build();
Console.WriteLine($"lastTime:{configRoot["lastTime"]}"); Console.ReadKey();
}
}
}

启动程序,输出如下:

lastTime:2020/3/1 22:55:11

在定义扩展的时候,都推荐这样去做,把具体实现都定义为私有的,然后通过扩展方法的方式暴露出去

刚才实际上还定义了一个 timer 来模拟配置的变更,这里可以监听一下它的变更,看是否生效

上一节讲到 ChangeToken 的方式,这里还是用 ChangeToken 的 OnChange 方法

namespace ConfigurationCustom
{
class Program
{
static void Main(string[] args)
{
var builder = new ConfigurationBuilder();
builder.AddMyConfiguration(); var configRoot = builder.Build(); ChangeToken.OnChange(() => configRoot.GetReloadToken(), () =>
{
Console.WriteLine($"lastTime:{configRoot["lastTime"]}");
}); Console.WriteLine("开始了");
Console.ReadKey();
}
}
}

启动程序,输出如下:

开始了
lastTime:2020/3/1 22:59:25
lastTime:2020/3/1 22:59:28
lastTime:2020/3/1 22:59:31

每个三秒钟输出一次,这说明我们定义的配置变更的通知已经生效了

MyConfigurationProvider 中我们只是通过赋值一个 DateTime 来模拟配置源

实际上可以从远程来说,比如阿波罗的配置中心,Kazoo,这些地方远程的读取配置,结合着命令行和环境变量配置,就可以完成配置中心的远程方案,意味着可以版本化的管理配置

这样子在 Docker 容器环境下面,Kubernetes 环境下面,就可以有完善的配置管理解决方案

GitHub源码链接:

https://github.com/MingsonZheng/DotNetCoreDevelopmentActualCombat/tree/main/ConfigurationCustom

本作品采用知识共享署名-非商业性使用-相同方式共享 4.0 国际许可协议进行许可。

欢迎转载、使用、重新发布,但务必保留文章署名 郑子铭 (包含链接: http://www.cnblogs.com/MingsonZheng/ ),不得用于商业目的,基于本文修改后的作品务必以相同的许可发布。

如有任何疑问,请与我联系 (MingsonZheng@outlook.com) 。

.NET Core开发实战(第14课:自定义配置数据源:低成本实现定制化配置方案)--学习笔记的更多相关文章

  1. 2月送书福利:ASP.NET Core开发实战

    大家都知道我有一个公众号“恰童鞋骚年”,在公众号2020年第一天发布的推文<2020年,请让我重新介绍我自己>中,我曾说到我会在2020年中每个月为所有关注“恰童鞋骚年”公众号的童鞋们送一 ...

  2. [ASP.NET Core开发实战]基础篇01 Startup

    Startup,顾名思义,就是启动类,用于配置ASP.NET Core应用的服务和请求管道. Startup有两个主要作用: 通过ConfigureServices方法配置应用的服务.服务是一个提供应 ...

  3. [ASP.NET Core开发实战]开篇词

    前言 本系列课程文章主要是学习官方文档,再输出自己学习心得,希望对你有所帮助. 课程大纲 本系列课程主要分为三个部分:基础篇.实战篇和部署篇. 希望通过本系列课程,能让大家初步掌握使用ASP.NET ...

  4. [ASP.NET Core开发实战]基础篇06 配置

    配置,是应用程序很重要的组成部分,常常用于提供信息,像第三方应用登录钥匙.上传格式与大小限制等等. ASP.NET Core提供一系列配置提供程序读取配置文件或配置项信息. ASP.NET Core项 ...

  5. 【.NET Core项目实战-统一认证平台】第二章网关篇-定制Ocelot来满足需求

    [.NET Core项目实战-统一认证平台]开篇及目录索引 这篇文章,我们将从Ocelot的中间件源码分析,目前Ocelot已经实现那些功能,还有那些功能在我们实际项目中暂时还未实现,如果我们要使用这 ...

  6. ASP.NET Core应用的错误处理[3]:ExceptionHandlerMiddleware中间件如何呈现“定制化错误页面”

    DeveloperExceptionPageMiddleware中间件利用呈现出来的错误页面实现抛出异常和当前请求的详细信息以辅助开发人员更好地进行纠错诊断工作,而ExceptionHandlerMi ...

  7. .NET Core开发实战(第11课:文件配置提供程序)--学习笔记

    11 | 文件配置提供程序:自由选择配置的格式 文件配置提供程序 Microsoft.Extensions.Configuration.Ini Microsoft.Extensions.Configu ...

  8. 2、SpringBoot接口Http协议开发实战8节课(1-6)

    1.SpringBoot2.xHTTP请求配置讲解 简介:SpringBoot2.xHTTP请求注解讲解和简化注解配置技巧 1.@RestController and @RequestMapping是 ...

  9. [ASP.NET Core开发实战]基础篇03 中间件

    什么是中间件 中间件是一种装配到应用管道,以处理请求和响应的组件.每个中间件: 选择是否将请求传递到管道中的下一个中间件. 可在管道中的下一个中间件前后执行. ASP.NET Core请求管道包含一系 ...

  10. Swing应用开发实战系列之一:自定义JdbcTemplate

    笔者本人真正意义上接触编程开发是在2004年,最早用的就是VB,然后是Delphi等,后来转到.Net,中间断断续续还用过PowerBuilder等,无一例外,所研发设计的项目或系统都是WinForm ...

随机推荐

  1. 5分钟教会你如何在生产环境debug代码

    前言 有时出现的线上bug在测试环境死活都不能复现,靠review代码猜测bug出现的原因,然后盲改代码直接在线上测试明显不靠谱.这时我们就需要在生产环境中debug代码,快速找到bug的原因,然后将 ...

  2. Jensen 不等式证明

    Jensen 不等式定义 若 \(f(x)\) 为区间 \(I\) 上的下凸函数,则对于任意 \(x_{i} \in I\) 和满足 \(\displaystyle\sum_{i=1}^{n} \la ...

  3. 机器学习-线性分类-支持向量机SVM-SMO算法代码实现-15

    1. alpha2 的修剪 if y1 != y2 : α1 - α2 = k # 不用算k的具体大小 if k > 0: # 上图的左 下这条线 α2 的区间 (0, c-k) k < ...

  4. hello world 的并发实现

    本篇文章将介绍 hello world 的并发实现,其中涉及到的知识有: 并发与并行 GPM 调度系统 并发与并行 并发不是并行.并发是同时管理很多事情,这些事情可能只做了一半就被暂停做别的事情了.而 ...

  5. DASCTF X CBCTF 2023|无畏者先行 CRYPTO—WP

    EzRSA 1.题目信息 from Crypto.Util.number import * import random from gmpy2 import * from libnum import * ...

  6. MySQL 8.2.0部署安装验证

    MySQL 8.2.0部署安装验证 背景 昨天捯饬了半天Oracle23c Free版本发现自己白忙活了. 然后想着继续看一下 MySQL8.2. 看看会不会又继续白忙活 下载与安装 https:// ...

  7. [转帖]「开源摘星计划」Prometheus监控Harbor(二进制版)

    推荐 原创 键客李大白2022-08-08 11:35:07博主文章分类:Harbor进阶实战(企业实战)著作权 文章标签云原生运维Harbor文章分类kubernetes云计算私藏项目实操分享阅读数 ...

  8. [转帖]Jmeter学习笔记(十七)——jmeter目录结构

      原文链接:http://www.cnblogs.com/zichuan/p/6938772.html 一.bin目录examples:  目录中有CSV样例 jmeter.bat  windows ...

  9. Python学习之十九_程序运行时间的验证

    Python学习之十九_程序运行时间的验证 背景 最近一段时间比较忙. 而且还遇到了一个lua脚本优化redis访问的场景. 想着自己还在学习python(时断时续) 所以想借着这个场景,学习一下py ...

  10. [转帖]台积电3nm成功量产,稳了吗?

    https://docs.pingcode.com/info/13836.html?p=13836 2023-01-19 资讯 21 原标题:台积电3纳米成功量产:未来与三星仍将决战鳍式场效晶体管(F ...