Ble.Framework.Driver.Core 0.0.0.2

There is a newer version of this package available.
See the version list below for details.
dotnet add package Ble.Framework.Driver.Core --version 0.0.0.2
                    
NuGet\Install-Package Ble.Framework.Driver.Core -Version 0.0.0.2
                    
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="Ble.Framework.Driver.Core" Version="0.0.0.2" />
                    
For projects that support PackageReference, copy this XML node into the project file to reference the package.
<PackageVersion Include="Ble.Framework.Driver.Core" Version="0.0.0.2" />
                    
Directory.Packages.props
<PackageReference Include="Ble.Framework.Driver.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 Ble.Framework.Driver.Core --version 0.0.0.2
                    
#r "nuget: Ble.Framework.Driver.Core, 0.0.0.2"
                    
#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 Ble.Framework.Driver.Core@0.0.0.2
                    
#: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=Ble.Framework.Driver.Core&version=0.0.0.2
                    
Install as a Cake Addin
#tool nuget:?package=Ble.Framework.Driver.Core&version=0.0.0.2
                    
Install as a Cake Tool

Ble.Framework.Driver — 工业级多协议驱动框架

一份纯机制层 + 协议层分离的工业驱动框架。Core 负责"连接生命周期 / 故障自愈 / 编排 / 集群 / 可观测";各协议驱动只负责"协议数据单元(PDU)编解码 + 类型化方法"。

业务侧唯一入口是 IBleSessionManager —— 写入 / 删除 / 替换 / 探测连接 / 等待 / 流式枚举 / 标签增删 / 生命周期事件。

凭据走 BleSecret 抽象(引用 / 内联);描述符写入前 fast-fail 校验器链;BleSessionsHealthCheck 暴露 Kubernetes 存活探针;OpenTelemetry 全埋点;优雅停止;断路器;金丝雀探针;反压自动反映到连接池。

架构红线 11 条:见 CONTRIBUTING.md,任一拉取请求违反即拒绝合并。


1. 目录

  1. 适用场景
  2. 架构总览
  3. 11 不变量
  4. 7 个协议驱动
  5. 业务前门:IBleSessionManager
  6. 配置热更 / 端点增删自动重启
  7. 凭据隔离 BleSecret
  8. 描述符校验链 IBleDescriptorValidator
  9. 传输安全 / 端点级传输配置
  10. 断路器 / 优雅排空 / 探针 / 反压
  11. 可观测性:OpenTelemetry + 健康检查
  12. 集群部署
  13. 测试基线
  14. 添加新驱动:5 文件夹模板
  15. 现场坑 → 不变量 反查表

1. 适用场景

该用 不该用
工业混协议采集(Modbus / S7 / OPC UA / SNMP / MQTT / IEC 61850),设备 ≥ 10K 单设备临时调通 → 直接用各 SDK
集群部署 + 分片调度 + 热扩容 + 不停机改配置 协议有强烈定制(私有 PDU)→ 按模板做新驱动
强可观测(OpenTelemetry 链路 + 指标 + 健康检查) 嵌入式资源极限场景(< 50MB)
要求拔网线 100 次不脏流(Modbus 字节错位现场常见) 单线程同步阻塞场景
凭据必须从密钥管理服务解析,不能进存储 / 日志

2. 架构总览

7 层,逐层只依赖下层:

┌─────────────────────────────────────────────────────────────────┐
│ L7  应用层门面                                                    │
│   IBleSessionManager (业务唯一前门)                              │
│     · UpsertSessionAsync / RemoveSessionAsync(写入 / 删除)       │
│     · TestConnectionAsync(写入前探测一下)                       │
│     · ReplaceSessionAsync(强制优雅替换)                          │
│     · GetSession / GetSessionStatus / Count                      │
│     · EnumerateAsync(filter) — 异步流式枚举                      │
│     · WaitForSessionAsync(等连上再用)                            │
│     · UpdateTagsAsync / ApplyTagDeltaAsync(标签全量/增量)         │
│     · SessionLifecycleChanged 事件总线                           │
├─────────────────────────────────────────────────────────────────┤
│ L6  生命周期 / 集群                                              │
│   BleSessionValidator + IBleDescriptorValidator 链(快速失败)     │
│   BleSessionLifecycleBus(跨组件事件)                            │
│   BleClusterSessionManager(分片调度 + 优雅替换)                  │
│   IBleSessionRegistry(进程级注册表)                             │
│   IBleSessionStore(权威源:内存 / Redis)                        │
├─────────────────────────────────────────────────────────────────┤
│ L5  会话                                                         │
│   BleDriverSessionBase<TTag, TFrame>                             │
│     · StartAsync / StopAsync / DisposeAsync                      │
│     · ExecuteFrameAsync(执行单帧)/ WriteBatchAsync(批量写)      │
│     · 能力接口:控制 / 文件传输 / 浏览 / 订阅                     │
├─────────────────────────────────────────────────────────────────┤
│ L4  连接池 / 路由                                                │
│   BlePoolHost<TConn>(各驱动模板基类,30 行)                       │
│   BleConnectionPool<TConn>                                       │
│     · 每端点监督器(退避 + 抖动 + 探针)                          │
│     · 每槽位互斥                                                  │
│     · 每端点断路器(可选)                                        │
│     · 优雅停止(等待在飞请求排空)                                │
│     · 反压自动检查(饱和时快速拒绝)                              │
│     · 唯一业务入口 ExecuteAsync(lambda 风格)                     │
├─────────────────────────────────────────────────────────────────┤
│ L3  连接契约                                                     │
│   IBleXxxConnection(每协议 1 份)                                │
│     · 类型化方法(读 / 写 / 发布)                                │
│     · IsHealthy + Faulted 事件(一次性锁存)                      │
│     · 业务异常 → IBleNonFatalProtocolError                       │
│     · 传输 / 帧错误 → BleTransportException...                   │
├─────────────────────────────────────────────────────────────────┤
│ L2  成帧 / 编解码                                                │
│   IBleXxxFramingCodec(自实现协议用,如 Modbus MBAP / RTU)        │
├─────────────────────────────────────────────────────────────────┤
│ L1  传输                                                         │
│   ITransport: BleTcpTransport / BleTlsTcpTransport               │
│     · 端点级配置(同会话内主路 TLS、备路明文皆可)                 │
└─────────────────────────────────────────────────────────────────┘

           横向依赖              IBleSecretProvider
                                 (环境变量 / 配置 / 缓存装饰)

3. 11 不变量

完整版见 CONTRIBUTING.md:

# 不变量 一句话
1 绝对时间死线 跨层只传 BleDeadline,不传 TimeSpan(相对时长跨层会被反复重算)
2 致命标记一次性锁存 MarkFatalInterlocked.Exchange == 0 保证一次性触发
3 不暴露连接租约 唯一业务入口 pool.ExecuteAsync(lambda)
4 业务异常加标记接口 实现 IBleNonFatalProtocolError,连接池不销毁连接
5 默认致命,例外才非致命 不允许"吞异常继续读"
6 槽位 Faulted 是吸收态 不允许"重置故障标志复用"
7 帧校验在最早字节 校验码 / 长度错立刻抛 BleMalformedFrameException → 销毁连接
8 64 位关联标识 不允许在长生命连接上用 ushort 做事务标识(2^16 易碰撞)
9 每次 ExecuteAsync 开一个 Activity 框架统一开,各驱动不要重复
10 TConn 是协议接口 不暴露第三方 SDK 类型给业务
11 探针(Canary)一等公民 协议层无副作用探活;业务异常视为协议层健康

4. 7 个协议驱动

每驱动统一 5 文件夹模板(IEC 61850 因 4 类能力接口例外):

项目 协议 批读 批写 订阅 控制 文件 浏览
Driver.ModbusTcp Modbus TCP(MBAP) / RTU over TCP ✅(FC15/16/22 智能合并 + 读改写降级)
Driver.S7 S7Comm(300/400/1200/1500) ✅(按 PDU 切块 + 二分定位故障项)
Driver.OpcUa OPC UA(匿名 / 用户名口令 / X509 证书) ✅(订阅项) ✅(地址空间浏览)
Driver.Snmp v1 / v2c / v3 + 告警监听 ✅(GET / GETBULK) ✅(SET 事务) ✅(Trap UDP 监听) ✅(子树枚举)
Driver.Mqtt MQTT 3.1.1 / 5 + 遗嘱 + 自动重订阅 ✅(并行发布,QoS 0/1/2) ✅(SUBSCRIBE)
Driver.Iec61850 MMS + GOOSE + SV + 文件 + 控制 ✅(ReadMultipleVariables) ✅(报告 / GOOSE / SV) ✅(选择-操作-取消) ✅(MMS GetFile) ✅(LD / LN / DO / DA)

5. 业务前门:IBleSessionManager

public interface IBleSessionManager
{
    // 写入 / 删除 / 替换 / 探测
    Task UpsertSessionAsync(BleSessionDescriptor descriptor, CancellationToken ct = default);
    Task RemoveSessionAsync(string sessionId, CancellationToken ct = default);
    Task ReplaceSessionAsync(string sessionId, CancellationToken ct = default);
    Task<BleConnectionTestResult> TestConnectionAsync(BleSessionDescriptor descriptor, CancellationToken ct = default);

    // 查询
    IBleDriverSession? GetSession(string sessionId);
    BleSessionStatus?  GetSessionStatus(string sessionId);
    int Count { get; }
    IAsyncEnumerable<BleSessionStatus> EnumerateAsync(BleSessionFilter? filter = null, CancellationToken ct = default);

    // 等待
    Task<IBleDriverSession> WaitForSessionAsync(string sessionId, TimeSpan timeout, CancellationToken ct = default);

    // 标签原地增删
    Task UpdateTagsAsync(string sessionId, IEnumerable<IBleTagDefinition> tags, CancellationToken ct = default);
    Task ApplyTagDeltaAsync(string sessionId, BleTagDelta delta, CancellationToken ct = default);

    // 事件
    event EventHandler<BleSessionLifecycleEvent>? SessionLifecycleChanged;
}

典型业务流程:

// 依赖注入
services.AddBleDriverCore();
services.AddBleStandalone();         // 集群版换 AddBleClusterRedis(...)
services.AddBleModbusDriver();       // 协议按需添加,N 个并存
services.AddBleOpcUaDriver();
services.AddBleMqttDriver();

// 业务
var manager = sp.GetRequiredService<IBleSessionManager>();

var descriptor = new BleSessionDescriptor
{
    SessionId = "PLC-A1",
    Driver = BleDriverKind.ModbusTcp,
    Endpoints = [
        new() { Host = "192.168.1.10", Port = 502, ConnectionCount = 2 },
        new() { Host = "192.168.1.11", Port = 502 },
    ],
    DefaultFrequencyMs = 500,
    Properties = new Dictionary<string, object?>
    {
        [BleModbusSessionDescriptor.SlaveAddressKey] = (byte)1,
        [BleModbusSessionDescriptor.FramingKey] = BleModbusFraming.Tcp,
    },
    Tags = [ /* 点位定义 */ ],
};

// 1) 保存前探测一下
var probe = await manager.TestConnectionAsync(descriptor);
if (!probe.Ok) { throw new InvalidOperationException(probe.Reason); }

// 2) 写入存储 + 自动调度
await manager.UpsertSessionAsync(descriptor);

// 3) 等连上再用
var session = await manager.WaitForSessionAsync(descriptor.SessionId, TimeSpan.FromSeconds(5));

// 4) 读 / 写
var values = await session.ExecuteFrameAsync("frame-key");
var result = await session.WriteBatchAsync(writes);

// 5) 标签增量(不重启会话)
await manager.ApplyTagDeltaAsync(descriptor.SessionId, delta);

// 6) 强制刷一次(PLC 物理 reset 后)
await manager.ReplaceSessionAsync(descriptor.SessionId);

// 7) 移除
await manager.RemoveSessionAsync(descriptor.SessionId);

// 8) 仪表盘流式
await foreach (var status in manager.EnumerateAsync(new BleSessionFilter
{
    Drivers = new HashSet<BleDriverKind> { BleDriverKind.ModbusTcp },
    States = new HashSet<BleSessionState> { BleSessionState.Connected },
}))
{
    Console.WriteLine($"{status.SessionId}: {status.State}");
}

6. 配置热更 / 端点增删自动重启

// 改端口 / 加备路 / 调超时 → UpsertAsync 即可
var newDescriptor = oldDescriptor with
{
    Endpoints = [.. oldDescriptor.Endpoints, new() { Host = "192.168.1.12", Port = 502 }],
};
await manager.UpsertSessionAsync(newDescriptor);

自动机制:

  1. BleSessionValidator + IBleDescriptorValidator 链快速失败(从站地址范围 / 凭据类型 / 端口范围 / 安全模式等)
  2. IBleSessionStore.SaveAsync 持久化为权威源
  3. BleClusterSessionManager 监听到 Upserted 事件
  4. BleSessionDescriptorEquality.SemanticEquals 判定是否变化
  5. 变化 → 优雅替换:起新会话 → WaitConnectedAsync 等连上 → 替换注册表引用 → 优雅停旧
  6. SessionLifecycleChanged 触发 Replaced 事件

业务侧在飞的 ExecuteFrameAsync 不会被打断(连接池槽位锁 + 排空保证)。

标签增删manager.ApplyTagDeltaAsync 的原地无锁路径(64 分片 CAS-spin),<u>不</u>触发会话重启。


7. 凭据隔离 BleSecret

public abstract record BleSecret;
public sealed record BleSecretRef(string Id) : BleSecret;       // 生产推荐:密钥管理服务 / 环境变量 / Vault 引用
public sealed record BleInlineSecret(string Value) : BleSecret; // 仅测试用

ToString 永远输出引用名或 ***** —— 真值不进任何持久化层。

public interface IBleSecretProvider
{
    ValueTask<string?> ResolveAsync(BleSecret? secret, CancellationToken ct);
}

实现:

  • BleEnvSecretProvider(默认):引用 mqtt-prod-pwd → 环境变量 BLE_SECRET_MQTT_PROD_PWD
  • BleConfigurationSecretProvider:键 Ble:Secrets:{id}IConfiguration 链(可接 Azure App Configuration / Vault)
  • BleCachingSecretProvider 装饰器:按 id 设置 TTL(默认 5 分钟)缓存,密钥服务调用从每秒 N 次降到 5 分钟 N 次
  • BleNoopSecretProvider:依赖注入默认兜底

用法(MQTT 凭据示例):

Properties = new Dictionary<string, object?>
{
    [BleMqttSessionDescriptor.UserNameKey] = "factory",
    [BleMqttSessionDescriptor.PasswordKey] = new BleSecretRef("mqtt-prod-pwd"),
}

描述符解析器见到非 BleSecret 类型直接抛 InvalidOperationException —— 杜绝明文字符串误用。

OPC UA / SNMP V3 同款接口。


8. 描述符校验链 IBleDescriptorValidator

每个驱动注册一个,BleSessionValidatorUpsertSessionAsync 写入存储前依次跑:

public sealed class BleModbusDescriptorValidator : IBleDescriptorValidator
{
    public void Validate(BleSessionDescriptor d, List<string> errors)
    {
        if (d.Driver != BleDriverKind.ModbusTcp) { return; }
        // 校验从站地址范围 / 帧格式 / 字节序枚举
    }
}

services.AddBleDescriptorValidator<BleModbusDescriptorValidator>();   // 自动跑在 6 个驱动里

错误聚合:BleDescriptorValidationException.Errors 一次性返回所有问题,不挤牙膏。

内置校验项:

  • Modbus:从站地址 ∈ [0, 247],帧格式 / 字节序是合法枚举
  • S7:CPU 型号 / 机架号 / 槽号范围,端口 ≤ Int16.MaxValue
  • OPC UA:口令是 BleSecret,安全模式合法,非 opc.tcp 主机时端口 > 0
  • SNMP:版本 / 安全级别合法,认证口令 / 加密口令是 BleSecret,Trap 监听端口范围
  • MQTT:口令是 BleSecret,遗嘱 QoS 合法,心跳间隔 ∈ [1, 65535]
  • IEC 61850:端口范围

9. 传输安全 / 端点级传输配置

端点级配置,同一会话主路 TLS、备路明文完全合法:

new BleEndpointDescriptor
{
    Host = "plc.example.com",
    Port = 8502,
    Properties = new Dictionary<string, string?>
    {
        [BleEndpointTransport.KeyTransport] = "tls",
        [BleEndpointTransport.KeyTlsTargetHost] = "plc.example.com",
        [BleEndpointTransport.KeyTlsProtocols] = "Tls12,Tls13",
        [BleEndpointTransport.KeyTlsPinnedSpkiSha256] = "abc...,def...",  // 公钥指纹白名单
    },
}

BleEndpointTransport.Build(endpoint, ipEndPoint) 在所有自实现协议(Modbus)的连接器内统一调用。


10. 断路器 / 优雅排空 / 探针 / 反压

断路器(每端点独立,默认禁用)

new BleConnectionPoolOptions<...>
{
    BreakerFailureThreshold = 5,                          // 连续 5 次致命 → 打开
    BreakerBreakDuration    = TimeSpan.FromSeconds(30),
}

断路器打开期请求直接抛 BleCircuitOpenException(或路由到下一端点);到期半开放一条试探。业务异常不计入。

优雅停止(默认 5 秒)

new BleConnectionPoolOptions<...> { StopDrainTimeout = TimeSpan.FromSeconds(10) }

StopAsync 先标记拒绝新请求,等在飞请求归零后才取消。

探针(每协议必须)

每驱动实现 ICanary<IBleXxxConnection>,周期发起协议层无副作用探测(Modbus FC03 读 1 寄存器 / S7 读 MB0 / OPC UA 读 Server.ServerStatus.State / SNMP 读 sysUpTime / IEC 61850 GetState / MQTT 检查 IsConnected)。连续 3 次失败 → 槽位致命 → 监督器重连。

反压

new BleConnectionPoolOptions<...> { BackpressureSignal = sp.GetRequiredService<IBleBackpressureSignal>() }

下游接收端上报 BlePressureLevel.Saturated(饱和)→ 连接池后续 ExecuteAsync 直接抛 BleBackpressureException 快速失败,不堆积在飞请求。


11. 可观测性:OpenTelemetry + 健康检查

OpenTelemetry

services.AddOpenTelemetry()
    .WithTracing(b => b.AddSource(BleDriverTelemetry.ActivitySourceName))
    .WithMetrics(b => b.AddMeter(BleDriverTelemetry.MeterName));
指标 类型 标签
ble.driver.requests_total 计数器 driver / endpoint / op / outcome
ble.driver.request_latency_ms 直方图 driver / endpoint / op / outcome
ble.driver.slot_faults_total 计数器 driver / endpoint / reason
ble.driver.slots_healthy 双向计数器 driver / endpoint
ble.driver.circuit_opened_total 计数器 driver / endpoint
ble.driver.canary_probe_total 计数器 driver / endpoint / outcome

健康检查

services.AddBleSessionsHealthCheck();   // 全局,聚合所有会话
// 或按驱动过滤
services.AddBleSessionsHealthCheck(new BleSessionFilter
{
    Drivers = new HashSet<BleDriverKind> { BleDriverKind.ModbusTcp }
});

services.AddHealthChecks()
    .AddCheck<BleSessionsHealthCheck>("ble-driver-sessions");

返回 Healthy(全部已连)/ Degraded(部分在线)/ Unhealthy(任一已断 / 已故障),数据字段含已连 / 部分连 / 已断三分类计数 + 失败会话标识示例。


12. 集群部署

// 单机
services.AddBleStandalone();

// Redis 集群
services.AddBleClusterRedis(opts =>
{
    opts.ConnectionString = "redis-master:6379";
    opts.ShardCount = 64;
    opts.GracefulShutdownMs = 30_000;
});

IBleSessionManager 接口完全不变 —— UpsertSessionAsync 写到 Redis,各节点的 BleClusterSessionManager 通过监听接管自己负责的分片。节点崩 30 秒内,该节点持有的会话自动迁到其他节点。


13. 测试基线

cd components/Driver
dotnet test    # 当前 445/445 全绿
项目 通过
Core.Tests 197
ModbusTcp.Tests 83
Mqtt.Tests 66
OpcUa.Tests 22
S7.Tests 49
Snmp.Tests 28

IEC 61850 无单元测试(libiec61850 跨进程互调用在 CI 跑不动);改动该协议必须本地实跑。


14. 添加新驱动:5 文件夹模板

Ble.Framework.Driver.Foo/
├── Connection/
│   ├── IBleFooConnection.cs                    ← 类型化方法,继承 IBleConnection(对应不变量 #10)
│   ├── BleFooProtocolException.cs              ← 非致命业务异常标记(对应不变量 #4)
│   ├── BleFooCanary.cs                         ← 协议层无副作用探针(对应不变量 #11)
│   └── Impl/
│       ├── BleFooConnection.cs                 ← SDK 包装,致命 / 非致命分流
│       └── BleFooConnectionPool.cs             ← 继承 BlePoolHost<IBleFooConnection>, 30 行
├── Sessions/
│   ├── BleFooSessionDescriptor.cs              ← Properties 键常量 + 强类型 Get*()
│   ├── BleFooConnectionOptions.cs              ← 强类型记录,口令用 BleSecret
│   ├── BleFooDescriptorValidator.cs            ← 实现 IBleDescriptorValidator
│   └── Impl/
│       ├── BleFooSession.cs                    ← 继承 BleDriverSessionBase
│       └── BleFooSessionFactory.cs             ← TestConnectionAsync 用 BleConnectionTestHelpers
├── Diagnostics/BleFooQualityMapper.cs          ← 异常 → 结构化诊断
├── Descriptors/Impl/BleFooDriverDescriptor.cs  ← IBleDriverDescriptor 元数据
├── Extensions/BleFooServiceCollectionExtensions.cs
│       AddBleFooDriver()
│         · AddBleDriverSessionFactory<BleFooSessionFactory>
│         · AddBleDriverDescriptor(new BleFooDriverDescriptor())
│         · AddBleDescriptorValidator<BleFooDescriptorValidator>
├── Module/BleFooModule.cs                      ← Furion 自动加载入口
└── _Imports.cs

骨架 ~600 行(含测试)。不变量都在 CONTRIBUTING.md 写死。


15. 现场坑 → 不变量 反查表

现场坑 由哪条机制根除
拔网线再插上,Modbus 流字节错位,所有读永远 Unexpected byte count 不变量 #7 + 监督器重建
上层显示"在线"但实际所有读都失败 不变量 #11 探针 + #6 槽位故障吸收态
改超时配置要重启服务 SemanticEquals + 优雅替换 + IBleSessionManager.UpsertSessionAsync
配置错(端口 = 99999)运行时才发现 IBleDescriptorValidator 链 + 快速失败
写入描述符时密码进 Redis / 日志 BleSecret 抽象 + IBleSecretProvider 握手瞬间才解析
主路死了所有请求挂 30 秒重连 不变量 #2 + 断路器快速失败
下游接收端慢导致 ExecuteAsync 永久阻塞 反压信号 + BleBackpressureException 快速拒绝
K8s 存活探针看不到驱动死活 BleSessionsHealthCheck
升级 SDK 把业务代码全炸 不变量 #10:TConn 是接口
证书过期 / 中间人攻击 BleTlsTcpTransport + 公钥指纹白名单 + 端点级选择
MQTT 代理重启后订阅消息丢 连接池重连后自动绑定回调 + 会话 OnConnectedAsync 重发订阅
S7-1500 PLC 拒接 PUT/GET 用 OPC UA 驱动(1500 内置服务)
GOOSE / SV 多订阅者重开原始套接字 BleNicHandlePool 引用计数共享
停服时在飞请求被强杀 StopAsync 默认 5 秒优雅排空
端点死了指标看不出来 OpenTelemetry slots_healthy + circuit_opened_total + slot_faults_total{reason}
Modbus FC22 不被某些 PLC 支持 业务侧不感知;会话内自动降级到读改写(FC3 + FC6)
千万级设备仪表盘列表卡死 EnumerateAsync(filter) 流式 + 每 256 项协作让出
Vault 调用密钥服务太频繁 BleCachingSecretProvider 装饰 + 5 分钟 TTL
PLC 后端被人物理 reset 但客户端不知道 manager.ReplaceSessionAsync(id) 强制优雅替换
业务侧改一行配置要写 7 个对象的代码 IBleSessionManager 单前门覆盖写入 / 删除 / 替换 / 探测 / 等待 / 枚举

许可

© Ble Corporation. All rights reserved.

Product Compatible and additional computed target framework versions.
.NET net10.0 is compatible.  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 (8)

Showing the top 5 NuGet packages that depend on Ble.Framework.Driver.Core:

Package Downloads
Ble.Framework.Driver.Snmp

Ble Framework

Ble.Framework.Driver.Standalone

Ble Framework

Ble.Framework.Driver.Iec61850

Ble Framework

Ble.Framework.Driver.ModbusTcp

Ble Framework

Ble.Framework.Driver.S7

Ble Framework

GitHub repositories

This package is not used by any popular GitHub repositories.

Version Downloads Last Updated
0.0.0.3 172 5/17/2026
0.0.0.2 164 5/17/2026
0.0.0.1 169 5/16/2026