1 个不稳定版本

0.1.0 2021 年 8 月 19 日

#669 in 配置

GPL-3.0-or-later

69KB
1K SLoC

什么是 cbradio?

它是一个基于 Redis 的编排系统,由零个或多个代理和一个基站组成。基站可以发布命令给代理,通过 Redis pub-sub 机制并行执行。基站启动于每个命令,并在收集输出后终止。

该系统的主要目的是通过另一个配置管理系统在多个服务器上触发重新配置,但任何命令都可以使用 shell 脚本或任何编程语言实现。

Redis 作为通信中心,代理将订阅基站发布的命令,并将命令的输出回送到 Redis 列表,供基站消费和显示。Redis 必须可由基站和所有代理访问,但基站或代理无需能够直接相互通信。

基站可能请求执行的命令是位于 run-directory 中的任何可执行文件(或脚本)。标准输出和错误流将被收集并通过 Redis 提供给基站。

出于安全原因,脚本将只获取代理的身份作为第一个参数 - 从基站无法传递任何自定义参数。

安全

安全模型设计时考虑了运行时无需握手,所有加密密钥都是通过不同的系统预先交换的。此外,代理被视为命令的单个通信端点,以避免对每个代理进行加密或需要事先了解代理在网络上的存在。这允许代理自由加入和离开网络。

基站与代理之间的通信是端到端加密的,基于 libsodium 加密箱 - Redis 只传输加密数据。

使用了两个静态密钥对

  1. 代理网络密钥 - 公钥部分与基站共享,私钥部分在所有代理之间共享,
  2. 基站密钥 - 公钥部分与代理共享,私钥部分由基站保留。

基站公钥用于验证命令签名,因此验证其执行的身份验证和授权。网络公钥用于加密命令并验证代理。身份验证基于代理解密请求的能力。

基站将为每个会话(命令请求/代理响应)生成一对临时密钥,用于推导出共享密钥,该密钥用于使用网络公钥(libsodium crypto box与一对临时密钥)加密代理的数据。会话密钥的公钥部分用于加密返回给基站的报文。为确保响应来自有权访问网络私钥的代理,命令和回复中交换随机挑战并由基站验证。

此外,为防止重放和重排序攻击,命令和响应消息使用序列编号方案。

完整性由libsodium crypto box认证加密(所有消息)以及基站签名(仅命令)提供。

本方案存在一些限制

  1. 由于基站和代理之间没有执行交换临时密钥的手握过程,因此目前无法实现前向保密。
  2. 目前,没有尝试隐藏命令和响应的长度和时间,这在此类系统中可能会暴露信息。

警告:由于系统具有非典型要求,该系统使用定制的加密设计,该设计未经专业密码学家的设计和审计!上述所述的假设和保证在理论中可能不成立,或可能被错误实现!

使用方法

使用cb-keygen生成两对密钥,并使用另一个系统分发这些密钥。

然后可以使用cb命令,通过agent子命令设置代理,通过station子命令发送命令。

可以使用--connection-string选项指定Redis的连接字符串。

各方应使用--identity选项分配唯一的标识符字符串。此外,所有各方必须使用指定相同字符串的--channel选项,才能进行通信。

除非使用--run-directory设置其他目录,否则代理将从其工作目录运行可执行文件。

此外,可以使用--tags选项为代理分配零个或多个标签。在发送命令时可以指定一个或多个这些标签,以限制哪些代理将执行它。命令上指定的所有标签都必须在代理上存在,才能执行该命令。如果命令未指定任何标签,则所有代理都将执行它。

基站将跟踪之前收到响应的代理(除非指定了--no-discovery开关),并将遭遇记录在默认应用程序缓存目录中的discovery.toml文件中。新发现的代理或丢失的代理将被记录为错误输出流的一部分,并在运行结束时报告。如果设置了--fail-missing标志,则在任何先前看到的代理没有响应的情况下,进程将以错误退出。

有关更多详细信息,请在cbcb-keygen命令及其子命令上使用--help开关。

响应等待持续时间

有三个可配置的等待持续时间设置。它们控制基站在不同处理阶段等待代理响应多长时间(以秒为单位)

  • -H, --hello-wait - 等待第一个响应的持续时间(0 = 无穷大);默认:2秒。
  • -R, --reply-wait - 等待下一个回复的时间(以秒为单位),当有代理活动时(0 = 无穷大);默认:120秒,
  • -M, --minimum-wait - 发送请求后等待回复的最短时间(以秒为单位)(0 = 1);默认:4秒。

如果没有任何代理回复,则hello等待时间将过期。这可能是由于通道中没有代理,没有代理匹配请求的标签或代理忙碌。

回复等待时间用于在部分代理已回复并执行命令后延长等待期。如果在此期间没有代理报告任何命令输出或最终状态消息,则此等待时间将过期。对于长时间没有输出的命令,可能需要延长此等待时间。

最小等待时间用于在所有活动代理完成其命令后,为代理发送第一次回复提供足够的时间。

状态码

如果设置错误,命令将使用状态 1 退出。

基站将根据运行时遇到的问题以不同的状态码退出。

运行时问题将向返回码添加一个值,以便可以使用位操作从中提取问题列表。

  • +2 - 如果使用了 --fail-missing 开关并且检测到代理缺失,
  • +4 - 检测到与命令执行相关的错误(非零退出状态,中止),
  • +8 - 站点回复等待时间已过期(见 --reply-wait),
  • +16 - 检测到与代理相关的错误(例如,错误的命令)。

待办事项

  • 代理直接消息 - 使用其标识符发送到特定的一个代理。
  • 执行节流 - 限制在任何给定时间内并行运行命令的代理数量。

依赖项

~16-26MB
~409K SLoC