Galosys.Foundation.Core 26.5.19.1

There is a newer version of this package available.
See the version list below for details.
dotnet add package Galosys.Foundation.Core --version 26.5.19.1
                    
NuGet\Install-Package Galosys.Foundation.Core -Version 26.5.19.1
                    
This command is intended to be used within the Package Manager Console in Visual Studio, as it uses the NuGet module's version of Install-Package.
<PackageReference Include="Galosys.Foundation.Core" Version="26.5.19.1" />
                    
For projects that support PackageReference, copy this XML node into the project file to reference the package.
<PackageVersion Include="Galosys.Foundation.Core" Version="26.5.19.1" />
                    
Directory.Packages.props
<PackageReference Include="Galosys.Foundation.Core" />
                    
Project file
For projects that support Central Package Management (CPM), copy this XML node into the solution Directory.Packages.props file to version the package.
paket add Galosys.Foundation.Core --version 26.5.19.1
                    
#r "nuget: Galosys.Foundation.Core, 26.5.19.1"
                    
#r directive can be used in F# Interactive and Polyglot Notebooks. Copy this into the interactive tool or source code of the script to reference the package.
#:package Galosys.Foundation.Core@26.5.19.1
                    
#:package directive can be used in C# file-based apps starting in .NET 10 preview 4. Copy this into a .cs file before any lines of code to reference the package.
#addin nuget:?package=Galosys.Foundation.Core&version=26.5.19.1
                    
Install as a Cake Addin
#tool nuget:?package=Galosys.Foundation.Core&version=26.5.19.1
                    
Install as a Cake Tool

Galosys.Foundation.Core

**成熟�?*: 🟢 稳定 �?生产可用,测试充分,活跃维护

Galosys.Foundation 核心库,提供统一响应模型、DDD 实体基类、扩展方法、安全加密、消息总线、模块化机制等基础能力�?

功能概览

1. 统一响应模型

// 成功响应
var response = UnifiedResponse.Succeed(data, "操作成功");

// 失败响应
var response = UnifiedResponse.Fail("ERROR_CODE", "操作失败");

// 异常响应
var response = UnifiedResponse.Error("ERROR_CODE", exception);

// 处理�?
var response = UnifiedResponse.Processing("PROCESSING_CODE");

2. 实体�?DDD 模式

// 完整实体(含创建者、修改者、软删除�?
public class User : FullEntity<long>
{
    public string Name { get; set; }
}

// 多租户实�?
public class Order : MtMaEntity
{
    public string OrderNo { get; set; }
}

// 基础实体
public class Entity
{
    public IReadOnlyCollection<ApplicationMessage> DomainEvents { get; }
    protected void AddEvent(ApplicationMessage @event) { }
}
实体基类矩阵
Entity (abstract, 领域事件)
 └── Entity<TID> (abstract, [Key, SnowflakeId] Id)
      └── FullEntity<TID> (abstract, IDeletable + ICreator + ILastModifier)
           ├── TenantEntity<TID>      : FullEntity<TID>, IMultiTenancy
           ├── AppEntity<TID>         : FullEntity<TID>, IMultiApplication
           └── TenantAppEntity<TID>   : FullEntity<TID>, IMultiTenancy, IMultiApplication
基类 适用场景 示例
FullEntity<TID> 全局基础数据,不分租户和应用 地区、字典、系统配�?
TenantEntity<TID> 仅分租户 用户、角色、权�?
AppEntity<TID> 仅分应用 菜单、API 接口
TenantAppEntity<TID> 租户 + 应用 租户应用配置
// 仅分租户(用户、角色、权限)
[Table("sys_user")]
public class SysUser : TenantEntity<long> { }

// 仅分应用(菜单、API 接口�?
[Table("sys_menu")]
public class SysMenu : AppEntity<long> { }

// 租户+应用(租户应用配置)
[Table("sys_tenant_app_config")]
public class SysTenantAppConfig : TenantAppEntity<long> { }

// 不分(全局基础数据�?
[Table("sys_region")]
public class SysRegion : FullEntity<long> { }

// 任意实体可按需实现 IConcurrency Mixin
public class SysUser : TenantEntity<long>, IConcurrency
{
    [Timestamp]
    public byte[] RowVersion { get; protected set; } = null!;
}

3. ID 生成�?

// 雪花算法 ID
var id = SnowflakeIdGenerator.Instance.NextId();

// 本地 ID 发生�?
var id = LocalGenerator.NextId();
var couponKey = LocalGenerator.NextCouponKey();
var seqKey = LocalGenerator.NextSeqKey();
var guid = LocalGenerator.NextGuid();

4. 分页

var pageResult = PageOutput.Of(items, total, page, size);

5. 单例模式

// 线程安全的延迟初始化单例
var instance = Singleton<MyService>.GetInstance();

// 使用 Lazy<T> 的单�?
var instance = LazySingleton<MyService>.Instance;

6. 消息订阅/发布

// 发布消息
await publisher.PublishAsync(new UserCreatedEvent(this));

// 订阅消息
public class UserCreatedListener : ApplicationListener<UserCreatedEvent>
{
    public override Task<bool> HandleAsync(UserCreatedEvent e)
    {
        // 处理逻辑
        return Task.FromResult(true);
    }
}

7. 扩展方法

// DateTime 扩展
var lastDay = dt.LastDayInMonth();
var firstDay = dt.FirstDayInMonth();
var isWeekend = dt.IsWeekend();
var workDate = dt.AddWorkDays(3);
var unixMs = dt.ToUnixTimeMilliseconds();
var unixSec = dt.ToUnixTimeSeconds();
var datetime = timestamp.ToDateTime();

// String 扩展
var compressed = "content".ToGZipCompress();
var decompressed = compressed.ToGZipDecompress();

// Object 扩展
var result = obj.GetAsyncResult<Task<string>>();

8. 安全加密

// MD5 加密
var hashed = SecurityTemplate.Md5Encrypt(original);

// DES 加解�?
var encrypted = SecurityTemplate.DesEncrypt(original);
var decrypted = SecurityTemplate.DesDecrypt(encrypted);

// AES 加解�?
var encrypted = SecurityTemplate.AesEncrypt(original, key);
var decrypted = SecurityTemplate.AesDecrypt(encrypted, key);

// AES 对象加解�?
var encrypted = SecurityTemplate.AesEncrypt(sample, key);
var decrypted = SecurityTemplate.AesDecrypt<SampleDto>(encrypted, key);

// RSA 加解�?
var encrypted = SecurityTemplate.RSAEncrypt(original, publicKey);
var decrypted = SecurityTemplate.RSADecrypt(encrypted, privateKey);

// 许可证生成与验证
var license = SecurityTemplate.GenerateLicense(info);
var valid = SecurityTemplate.ValidateLicense(license);

9. 动态代�?

class HttpProxy : ServiceProxy
{
    protected override void Proceed(InvocationContext context)
    {
        var http = context.ServiceProvider.GetRequiredService<IHttpClientFactory>().CreateClient();
        // 自定义调用逻辑
        context.SetReturnValue(http.GetStringAsync("/posts/1"));
    }
}

interface ITypicodeClient
{
    Task<string> ListPostsAsync();
    Task GetPostByIdAsync(int id);
}

var instance = ServiceProxyFactory.CreateProxy(typeof(ITypicodeClient), typeof(HttpProxy), sp) as ITypicodeClient;

10. 进程管理

// 启动进程
var p = new Process().Start("cmd.exe", runAsAdministrator: true);

// 打开浏览�?
p = new Process().Browser("https://example.com");
p = new Process().Browser("https://example.com", "edge.exe");

// 打开资源管理�?
p = new Process().Explore("c://");

// 执行脚本
p = new Process().Script("dotnet.exe", "info");

11. HTTP 客户�?

services.AddHttpClient<IPlaceholderGateway, PlaceholderGateway>(http =>
{
    http.BaseAddress = new Uri("https://jsonplaceholder");
}).AddServiceDiscovery()
  .AddStandardHedgingHandler();

12. 随机数生�?

// 验证�?
var code = Random.Shared.GenerateCaptcha();

// 短信�?
var code = Random.Shared.GenerateSms();

13. 应用程序启动�?

// 实现 IApplicationRunner 接口
public class MyRunner : IApplicationRunner
{
    public int Order => 0;

    public async Task RunAsync(ApplicationArguments args)
    {
        // 启动时执行逻辑
    }
}

14. 插件注册表(PluginRegistry�?

基于策略路由模式的基础设施,根据请求自动匹配对应插件实现。适用于短信网关、支付渠道、物流商等多 provider 场景�?

定义插件

实现 Plugin<TRequest> 接口,该接口要求实现 Supports 方法,SupportsAsync 有默认实现(委托�?Supports):

using Microsoft.Extensions.Plugining;

public class SmsRequest
{
    public string Provider { get; set; }
}

public interface ISmsPlugin : Plugin<SmsRequest>
{
    Task SendAsync(SmsRequest request);
}

internal class AliyunSmsPlugin : ISmsPlugin
{
    public bool Supports(SmsRequest request) => request.Provider == "aliyun";
    public Task SendAsync(SmsRequest request) { /* ... */ }
}

internal class TencentSmsPlugin : ISmsPlugin
{
    public bool Supports(SmsRequest request) => request.Provider == "tencent";
    public Task SendAsync(SmsRequest request) { /* ... */ }
}
最小化配置
// DI 注册(PluginRegistry �?AddCore 中自动注册为 Singleton�?
services.AddTransient<ISmsPlugin, AliyunSmsPlugin>();
services.AddTransient<ISmsPlugin, TencentSmsPlugin>();
基本用法:单匹配

注入 PluginRegistry<TPlugin, TRequest> 并调�?GetPluginFor�?

public class SmsService
{
    private readonly PluginRegistry<ISmsPlugin, SmsRequest> _registry;

    public SmsService(PluginRegistry<ISmsPlugin, SmsRequest> registry) => _registry = registry;

    public async Task SendAsync(SmsRequest request)
    {
        var plugin = _registry.GetPluginFor(request);
        if (plugin == null) throw new InvalidOperationException($"未找�?Provider: {request.Provider}");
        await plugin.SendAsync(request);
    }
}
多匹配:通知广播

GetAllPluginsFor 返回所有匹配的插件,适用于通知、广播场景:

var plugins = _registry.GetAllPluginsFor(request);
await Task.WhenAll(plugins.Select(p => p.SendAsync(request)));
异步匹配

插件可重�?SupportsAsync 实现异步匹配逻辑(如查询数据库判断是否支持)�?

// 异步获取单个匹配插件
var plugin = await _registry.GetPluginForAsync(request);

// 异步获取所有匹配插�?
var plugins = await _registry.GetAllPluginsForAsync(request);
解析模式

通过 PluginResolutionMode 控制插件实例�?DI 生命周期�?

模式 行为 适用场景
PluginResolutionMode.Scoped 创建新的 DI Scope 解析 默认模式,适用�?Scoped 插件
PluginResolutionMode.Singleton 从根容器直接获取 插件�?Singleton 或无需 Scope
// Scoped(默认,无参方法即此模式�?
var plugin = _registry.GetPluginFor(request);
var plugin = _registry.GetPluginFor(request, PluginResolutionMode.Scoped);

// Singleton
var plugin = _registry.GetPluginFor(request, PluginResolutionMode.Singleton);

15. Executor 模板方法

提供命令执行管道,按顺序执行:前置钩�?�?参数校验 �?业务逻辑 �?后置钩子,统一返回 UnifiedResponse�?

最小化配置
// �?IServiceCollection 上调�?AddCola() 注册 Executor + ExtensionPoint 机制
services.AddCola();

指定扫描程序集:

services.AddCola(typeof(OrderCreateCmd).Assembly);
定义命令
using Galosys.Foundation.Core;

public class OrderCreateCmd : CommandBase
{
    public string OrderNo { get; set; }
    public decimal Amount { get; set; }

    public override ValidationResult Validate()
    {
        if (string.IsNullOrEmpty(OrderNo))
            return new ValidationResult("订单号不能为�?);
        return ValidationResult.Success;
    }
}
实现 Executor
using Galosys.Foundation.Core;

public class OrderCreateExecutor : ExecutorBase<OrderCreateCmd>
{
    public OrderCreateExecutor(ILogger<ExecutorBase<OrderCreateCmd>> logger, IServiceProvider serviceProvider)
        : base(logger, serviceProvider) { }

    protected override UnifiedResponse DoExecute(OrderCreateCmd command)
    {
        // 业务逻辑
        return UnifiedResponse.Succeed(new { OrderId = Guid.NewGuid() });
    }

    protected override Task<UnifiedResponse> DoExecuteAsync(OrderCreateCmd command, CancellationToken cancellationToken)
    {
        return Task.FromResult(DoExecute(command));
    }
}
执行管道行为
阶段 方法 说明
前置钩子 OnBeforeExecute 记录日志,可重写
参数校验 command.Validate() 校验失败返回 VALIDATION_ERROR
业务逻辑 DoExecute / DoExecuteAsync 子类必须实现
后置钩子 OnAfterExecute 记录日志,可重写
业务异常 HandleBusinessException 捕获 BizException,返�?BizException.ErrCode
系统异常 HandleSystemException 捕获其他异常,返�?SYSTEM_ERROR

16. 扩展点机制(ExtensionPoint�?

基于阿里巴巴 COLA 架构的扩展点模式,通过 BizScenario(业务身份)路由到不同的扩展点实现,支持多租户、多渠道等业务身份隔离场景�?

定义扩展�?
using Galosys.Foundation.Core;

public interface IPaymentStrategy : IExtensionPoint
{
    Task<PaymentResult> PayAsync(PaymentRequest request);
}
实现扩展�?

使用 [Extension] 特性声明业务身份(命名空间 System.ComponentModel.Annotations):

using Galosys.Foundation.Core;
using System.ComponentModel.Annotations;

[Extension(BizId = "default", UseCase = "default", Scenario = "wechat")]
public class WechatPaymentStrategy : IPaymentStrategy
{
    public Task<PaymentResult> PayAsync(PaymentRequest request)
    {
        return Task.FromResult(new PaymentResult { Message = "微信支付成功" });
    }
}

[Extension(BizId = "default", UseCase = "default", Scenario = "alipay")]
public class AliPaymentStrategy : IPaymentStrategy
{
    public Task<PaymentResult> PayAsync(PaymentRequest request)
    {
        return Task.FromResult(new PaymentResult { Message = "支付宝支付成�? });
    }
}
使用扩展�?
public class PaymentService
{
    private readonly IExtensionExecutor _executor;

    public PaymentService(IExtensionExecutor executor) => _executor = executor;

    public async Task<PaymentResult> Pay(string paymentType, PaymentRequest request)
    {
        var scenario = BizScenario.ValueOf("default", "default", paymentType);
        return await _executor.ExecuteAsync<IPaymentStrategy, PaymentResult>(
            scenario, svc => svc.PayAsync(request));
    }
}
匹配降级策略

查找扩展点时按以下顺序降级:

  1. 精确匹配 �?bizId:useCase:scenario
  2. 场景通配 �?bizId:useCase:*
  3. 用例通配 �?bizId:*:*
  4. *全默�? �?default:default:default

�?[Extension] 特性的实现类自动注册为 BizScenario.Default�?

自定义匹配策�?

通配符匹配逻辑抽象�?IBizScenarioMatcher 接口,可注册自定义实现替换默认的三级降级策略�?

// 默认实现:三级降级(精确 �?场景通配 �?用例通配 �?全局默认�?
services.AddSingleton<IBizScenarioMatcher, DefaultBizScenarioMatcher>();

// 自定义匹配策�?
public class RegexBizScenarioMatcher : IBizScenarioMatcher
{
    public Type? Match(IDictionary<BizScenario, Type> candidates, BizScenario target) { /* ... */ }
    public IEnumerable<Type> MatchAll(IDictionary<BizScenario, Type> candidates, BizScenario target) { /* ... */ }
}
批量扩展点执�?

IExtensionExecutor 支持批量执行所有匹配的扩展点实现:

// ExecuteAll �?依次执行所有匹配扩展点的副作用操作
executor.ExecuteAll<INotifyExtension>(scenario, ext => ext.SendNotification());

// ExecuteAllAsync �?异步依次执行
await executor.ExecuteAllAsync<INotifyExtension>(scenario, ext => ext.SendAsync());

// ReduceAsync �?聚合多个扩展点的返回�?
var totalScore = await executor.ReduceAsync<IScoreStrategy, int>(
    scenario,
    ext => Task.FromResult(ext.Calculate(input)),
    (acc, val) => acc + val,
    seed: 0);

17. 分页查询(PageQuery�?

独立的分页查询基类,不依�?DTO 继承层级,包含分页、排序、分组等属性:

using Galosys.Foundation.Core;

var query = new PageQuery
{
    PageIndex = 2,     // 最小值自动保护为 1
    PageSize = 10,     // 最小值自动保护为 10
};
query.SetOrderDirection("ASC");

int offset = query.Offset; // (PageIndex - 1) * PageSize = 10
属�? 说明 默认�?
PageIndex 页码(最�?1�? 1
PageSize 每页大小(最�?1�? 10
Offset 偏移量(只读�? (PageIndex-1)*PageSize
OrderDirection 排序方向 "DESC"
OrderBy 排序字段 null
GroupBy 分组字段 null
NeedTotalCount 是否需要总数 true

18. 分层日志通道(ILogChannel�?

**已迁�?*:日志通道、日志实体(AuditLog/LoginLog/RequestLog)、消费者和 Repository 接口已迁�?Galosys.Foundation.Actuator 模块。请参�?Actuator 模块文档�?

19. MessageBus + Outbox 引擎

提供 IMessageBus 统一消息入口(Send + Publish),以及 Transactional Outbox 模式保证业务事务与消息发送的原子性。寄生在 Microsoft.Extensions.MessageBus 命名空间�?

无需 RabbitMQ 即可运行,Core 内置 DefaultMessageBus(Channel 缓冲进程内分发)�?

// �?Core 内置默�?IMessageBus(自动由 AddCore 注册)
// PublishAsync → Channel<(Type, IMessage)> → ConsumeLoopAsync → IMessageHandler<T>
await bus.PublishAsync("order.created", order);

**事务保证(Outbox 模式):** `PendingMsgCol`(AsyncLocal)收集待发送消息,`OutboxSaveChangesInterceptor` 在 `SaveChanges` 时同事务写入 `base_outbox_msg` 表,不再直写 `IOutboxStore`。

```csharp
await _bus.PublishAsync("order.created", order);  // → PendingMsgCol
await _db.SaveChangesAsync();                     // → 拦截器同事务写入

// 引入 RabbitMQ 后自动覆盖为 RabbitMessageBus // services.AddRabbitMessageBus → TryAddSingleton 不生效,RemoveAll 后重建


**进程内消息处理�?*

实现 `IMessageHandler<T>`(命名空间 `Microsoft.Extensions.MessageBus`):

```csharp
using Microsoft.Extensions.MessageBus;

public class OrderCreatedHandler : IMessageHandler<OrderCreatedEvent>
{
    public Task<bool> HandleAsync(OrderCreatedEvent msg)
    {
        // 处理订单...
        return Task.FromResult(true);
    }
}

// DI 注册
services.AddScoped<IMessageHandler<OrderCreatedEvent>, OrderCreatedHandler>();

*RabbitMQ + Outbox(写 Store �?后台发)�?

services.AddRabbitMessageBus(options => {
    options.EnableOutbox = true;
    options.Outbox.TableName = "base_outbox_msg";
});
services.AddEfCoreOutboxStore<MyDbContext>();

await bus.PublishAsync("order.created", order,
    h => h.With("tenantId", "abc"));

注册链覆盖规则:

引用 IMessageBus IOutboxTransport IOutboxStore
仅 Core DefaultMessageBus LocalOutboxTransport InMemoryOutboxStore
+ RabbitMQ.Client MessageBusOutboxDecoratorRabbitMessageBus RabbitMQTransport 不变
+ RabbitMQ.Client + EF Core 同上 同上 EfCoreOutboxStore

*配置�?

{
  "MessageBus": {
    "EnableOutbox": true,
    "Outbox": {
      "TableName": "base_outbox_msg",
      "BatchSize": 100,
      "PollIntervalMs": 1000,
      "MaxRetryCount": 3,
      "RetentionDays": 7
    }
  }
}

模块化机�?

框架内置完整的模块化系统,自动发现、加载、管理所�?Galosys.Foundation.* 模块�?

Quick Start

最小化配置,一行启用模块化�?

// ASP.NET Core
builder.Host.UseModularization();

// 控制台应�?
var host = Host.CreateDefaultBuilder(args)
    .UseModularization()
    .Locate();   // 构建 Host 并初始化服务定位�?

UseModularization() 会自动扫描所�?Galosys.Foundation.* 程序集,发现实现�?IModule 接口的类,按依赖顺序加载并注册服务�?

模块发现

框架采用两层发现策略�?

  1. 编译�?Source Generator �?在编译时自动生成 [assembly: ModuleManifest] 特性到程序集,运行时直接读取,无需全量反射扫描
  2. *运行时反射兜�? �?若程序集没有清单特性,自动 fallback 到反射扫�?IModule 实现�?

两种方式发现的模块会自动合并去重,完全向后兼容�?

模块元数�?

使用 [ModuleInfo] 标记模块的名称、版本等信息�?

[ModuleInfo("Core", Version = "1.0.0", IsRequired = true)]
internal class CoreModule : IModule
{
    public void ConfigureServices(IServiceCollection services, HostBuilderContext context)
    {
        // 注册模块服务
    }

    public void ConfigureHost(IHostBuilder host)
    {
        // 配置 Host(可选)
    }
}
属�? 类型 默认�? 说明
Name string (必填) 模块名称,用于过滤和查询
Version string "1.0.0" 模块版本�?
IsRequired bool false 标记为必需模块,不会被配置过滤禁用,且参与 Health Check

模块依赖

使用 [DependsOn] 声明模块间依赖关系,框架会自动进行拓扑排序,确保依赖模块先加载:

[DependsOn(typeof(DataModule))]
[ModuleInfo("EntityFrameworkCore")]
internal class EntityFrameworkCoreModule : IModule
{
    public void ConfigureServices(IServiceCollection services, HostBuilderContext context)
    {
        // DataModule 必定在此模块之前加载完成
    }
}

框架会在启动时检测循环依赖,发现循环时抛�?ModuleInitializationException 并终止启动�?

配置过滤

通过 appsettings.json 控制模块的加载行为,适用于不同环境按需裁剪模块�?

{
  "Foundation": {
    "Modules": {
      "Enabled": [],          // 白名单,为空时不限制(即允许所有模块加载)
      "Disabled": ["Kafka"]   // 黑名单,优先级高�?Enabled(即�?Enabled 包含也会被禁用)
    }
  }
}

*过滤规则�?

  • Enabled 为空数组 �?不限制,加载所有模�?
  • Enabled 非空 �?仅加载列表中的模�?
  • Disabled �?优先级高�?Enabled,名单中的模块不会被加载
  • 标记 IsRequired = true 的模�?不受过滤影响*,始终加�?

*典型场景�?

// 开发环境:禁用消息队列相关模块
{
  "Foundation": {
    "Modules": {
      "Enabled": [],
      "Disabled": ["Kafka", "RabbitMQ"]
    }
  }
}

// 精简部署:仅加载指定模块
{
  "Foundation": {
    "Modules": {
      "Enabled": ["Core", "Data", "EntityFrameworkCore"],
      "Disabled": []
    }
  }
}

运行时查�?

通过注入 IModuleRegistry 查询模块加载状态:

public class MyService
{
    private readonly IModuleRegistry _registry;

    public MyService(IModuleRegistry registry) => _registry = registry;

    public void Check()
    {
        // 获取所有已加载模块
        var loaded = _registry.LoadedModules;

        // 检查指定模块是否已加载(不区分大小写)
        var hasKafka = _registry.IsLoaded("Kafka");
    }
}

ModuleDescriptor 包含以下信息�?

属�? 类型 说明
Name string 模块名称
Version string 模块版本
ModuleType Type 模块实现类型
LoadDuration TimeSpan 加载耗时
Dependencies string[] 依赖的模块名称列�?
IsRequired bool 是否为必需模块

Health Check

框架自动注册模块 Health Check,访�?/health 端点即可查看模块加载状态:

GET /health
�?Healthy: "已加�?12 个模�?

必需模块(IsRequired = true)的加载状态纳入健康检查判定�?

Metrics

框架内置 OpenTelemetry 指标,可通过 Prometheus 等监控系统采集:

Meter:    Galosys.Foundation.Modules
Counter:  modules.loaded.count        // 已加载模块数量,标签: module.name
Histogram: module.load_duration       // 模块加载耗时(ms),标�? module.name

DI 上下文服�?

框架内置 ITenantContextIAppContextIUserContext 三个 Singleton 上下文服务,基于 static AsyncLocal<T> 实现请求级隔离,用于在业务层获取当前请求的租户、应用和用户信息�?

设计说明:这三个服务的实现类(TenantContext/AppContext/UserContext)全部使�?static AsyncLocal<T> 存储状态,实例本身无状态。注册为 Singleton 确保可从任何 DI 生命周期(包�?root provider、EF Core OnModelCreating)中安全解析,AsyncLocal 天然按异步上下文隔离,无需担心跨请求污染�?

// DI 注册(在 AddCore 中自动注册)
services.TryAddSingleton<ITenantContext, TenantContext>();
services.TryAddSingleton<IAppContext, AppContext>();
services.TryAddSingleton<IUserContext, UserContext>();
// 使用方式:构造函数注�?
public class MyService
{
    private readonly ITenantContext _tenantContext;
    private readonly IAppContext _appContext;
    private readonly IUserContext _userContext;

    public MyService(ITenantContext tenantContext, IAppContext appContext, IUserContext userContext)
    {
        _tenantContext = tenantContext;
        _appContext = appContext;
        _userContext = userContext;
    }
}

注册服务

// 基础注册(模块化、消息总线、消息发布等) — AddMessageBus() 在 AddCore 内自动调用
services.AddCore();

// 单独注册消息总线(不通过 AddCore 时)
services.AddMessageBus();

// 注册 Executor + ExtensionPoint 机制(扫描入口程序集�?
services.AddCola();

// 指定程序集扫描扩展点
services.AddCola(typeof(MyExtension).Assembly, typeof(OtherExtension).Assembly);

// 消息发布
services.AddApplicationMessagePublisher();

安装

<PackageReference Include="Galosys.Foundation.Core" Version="x.x.x" />

目录结构

Galosys.Foundation.Core/
├── Galosys\Foundation\Core\                          # 核心类型(实体、响应、消息等�?
�?  ├── ModuleDescriptor.cs                           # 模块描述�?
�?  ├── Executor/                                     # Executor 模板方法
�?  �?  ├── ICommand.cs                               # 命令接口
�?  �?  ├── CommandBase.cs                            # 命令基类
�?  �?  ├── IExecutor.cs                              # Executor 接口
�?  �?  ├── ExecutorBase.cs                           # Executor 基类(模板方法管道)
�?  �?  ├── ExtensionAwareExecutor.cs                 # 支持扩展点的 Executor
�?  �?  └── PageQuery.cs                              # 分页查询基类
�?  └── ExtensionPoint/                               # 扩展点机�?
�?      ├── BizScenario.cs                            # 业务身份(record�?
�?      ├── IExtensionPoint.cs                        # 扩展点标记接�?
�?      ├── IBizScenarioMatcher.cs                    # 匹配策略接口
�?      ├── DefaultBizScenarioMatcher.cs              # 默认三级降级匹配
�?      ├── IExtensionRegistry.cs                     # 扩展点注册器接口
�?      ├── ExtensionRegistry.cs                      # 扩展点注册器实现
�?      ├── IExtensionExecutor.cs                     # 扩展点执行器接口
�?      └── ExtensionExecutor.cs                      # 扩展点执行器实现
├── Microsoft\Extensions\Hosting\                     # HostBuilder 扩展
�?  └── ModuleHostBuilderExtensions.cs                # UseModularization() 入口
├── Microsoft\Extensions\MessageBus\                      # 消息总线 + Outbox 引擎
�?  ├── IMessageBus.cs                                  # 统一消息入口(Send/Publish)
�?  ├── DefaultMessageBus.cs                            # 进程内默认总线(Channel 缓冲�?
�?  ├── LocalOutboxTransport.cs                         # 本地传输占位
�?  ├── IMessageHandler.cs                              # 消息处理器接口 + IMessage + MessageBase
�?  ├── EventBusHeaders.cs                            # 消息�?
�?  ├── IOutboxStore.cs                               # 存储抽象
�?  ├── IOutboxTransport.cs                           # 传输抽象
�?  ├── OutboxMessage.cs                              # 消息实体
�?  ├── OutboxOptions.cs                              # 配置
�?  ├── OutboxDeliveryMode.cs                         # 投递模式枚�?
�?  ├── OutboxMessageStatus.cs                        # 状态枚�?
�?  ├── OutboxPollingStrategy.cs                      # 轮询策略枚举
�?  ├── OutboxBootstrapper.cs                         # 轮询引擎
�?  ├── OutboxCleanupService.cs                       # 清理服务
�?  └── PendingMsgCol.cs                              # AsyncLocal 消息收集器
�?  └── InMemoryOutboxStore.cs                        # 内存存储(默认�?
├── Microsoft\Extensions\DependencyInjection\          # DI 扩展
�?  ├── IModule.cs                                    # 模块接口 + 特性定�?
�?  ├── IModuleRegistry.cs                            # 模块注册表接�?
�?  ├── ModuleRegistry.cs                             # 模块注册表实�?
�?  ├── CoreColaServiceCollectionExtensions.cs        # AddCola() 注册入口
�?  └── OutboxServiceCollectionExtensions.cs          # AddOutbox() 注册入口
├── Microsoft\Extensions\Options\                     # 配置选项
�?  └── ModuleFilterOptions.cs                        # 模块过滤配置
├── Microsoft\Extensions\Diagnostics\                 # 诊断
�?  ├── ModuleMetrics.cs                              # 模块 Metrics
�?  └── HealthChecks\ModuleHealthCheck.cs             # 模块 Health Check
├── Microsoft\Extensions\DependencyModel\             # 依赖上下文扩�?
�?  └── DependencyContextExtensions.cs                # 模块发现 + 拓扑排序
├── System\ComponentModel\                            # 组件模型扩展
�?  ├── Annotations\ExtensionAttribute.cs             # 扩展点声明特�?
�?  └── DataAnnotations\ValidationResultExtensions.cs # ValidationResult.IsValid()
└── System\                                           # 扩展方法(按功能模块组织�?
    ├── DateTimeExtensions.cs
    ├── StringExtensions.cs
    ├── ObjectExtensions.cs
    ├── Security\Cryptography\
    ├── Net\Http\
    └── Threading\Tasks\

依赖

  • Microsoft.Extensions.Caching.Abstractions
  • Microsoft.Extensions.Caching.Memory
  • Microsoft.Extensions.DependencyInjection
  • Microsoft.Extensions.DependencyModel
  • Microsoft.Extensions.Diagnostics.HealthChecks
  • Microsoft.Extensions.Hosting
  • Microsoft.Extensions.Http
  • System.Text.Json
  • System.Threading.RateLimiting

Outbox 引擎零新增依赖,复用已有 Microsoft.Extensions.Hosting / DI�?

Product Compatible and additional computed target framework versions.
.NET net8.0 is compatible.  net8.0-android was computed.  net8.0-browser was computed.  net8.0-ios was computed.  net8.0-maccatalyst was computed.  net8.0-macos was computed.  net8.0-tvos was computed.  net8.0-windows was computed.  net9.0 was computed.  net9.0-android was computed.  net9.0-browser was computed.  net9.0-ios was computed.  net9.0-maccatalyst was computed.  net9.0-macos was computed.  net9.0-tvos was computed.  net9.0-windows was computed.  net10.0 was computed.  net10.0-android was computed.  net10.0-browser was computed.  net10.0-ios was computed.  net10.0-maccatalyst was computed.  net10.0-macos was computed.  net10.0-tvos was computed.  net10.0-windows was computed. 
Compatible target framework(s)
Included target framework(s) (in package)
Learn more about Target Frameworks and .NET Standard.

NuGet packages (125)

Showing the top 5 NuGet packages that depend on Galosys.Foundation.Core:

Package Downloads
Galosys.Foundation.AspNetCore

Galosys.Foundation快速开发库

Galosys.Foundation.AspNetCore.DynamicApi

Galosys.Foundation快速开发库

Galosys.Foundation.Data

Galosys.Foundation快速开发库

Galosys.Foundation.HttpClient

Galosys.Foundation快速开发库

Galosys.Foundation.RabbitMQ

Galosys.Foundation快速开发库

GitHub repositories

This package is not used by any popular GitHub repositories.

Version Downloads Last Updated
26.5.20.1 2,401 5/20/2026
26.5.19.1 2,566 5/19/2026
26.5.18.1 2,560 5/18/2026
26.5.15.1 2,559 5/15/2026
26.5.12.3 2,510 5/12/2026
26.5.12.2 2,506 5/12/2026
26.4.27.1-rc1 2,117 4/26/2026
26.4.25.1-rc1 2,109 4/25/2026
26.4.22.2-rc7 2,122 4/22/2026
26.4.22.2-rc6 2,119 4/22/2026
26.4.22.2-rc4 2,120 4/22/2026
26.4.22.2-rc3 1,947 4/22/2026
26.4.19.1-rc1 1,854 4/19/2026
26.4.12.8-rc1 1,912 4/12/2026
26.4.12.7-rc1 1,906 4/12/2026
26.4.12.5-rc1 1,470 4/12/2026
26.1.30.1-rc1 2,296 1/30/2026
26.1.29.1 2,365 1/29/2026
26.1.28.5 2,406 1/28/2026
26.1.28.4 2,343 1/28/2026
Loading failed