从 IDeployable 到 TransferExecutor:一个工业部署工具的可靠性演进

7 阅读11分钟

从 SFTP 部署到现场工作台:DeviceForge v2.6—v2.9 的一次完整演进

一款工业设备运维工具,真正的竞争力不只是“支持多少协议”,而是工程师在网络不稳定、设备数量增加、任务需要反复恢复时,能不能继续工作。

项目:turnarond/DeviceForge

技术栈:Qt 6、C++17、CMake、FTP/FTPS、SFTP、Telnet/SSH、Modbus、OPC UA、WebSocket、TCP/UDP 中继

开头:从“能传文件”到“能完成现场任务”

工业设备的部署工作很少只有一个动作。工程师通常需要先连接设备,再浏览远程目录,确认版本文件,向多台设备分发内容,处理覆盖和权限问题,观察每台设备的进度,最后留下可复核的结果。

如果 FTP、SFTP、批量部署、文件浏览和失败重试分别由不同工具负责,现场就会不断发生上下文切换:路径要重新找,设备要重新选,失败要重新判断,已经成功的设备又可能被重复执行。

DeviceForge 从 v2.6 开始,沿着一条清晰的产品路线持续演进:

v2.6:打通 SFTP 批量部署
  ↓
v2.7:让双栏文件工作区真正可用
  ↓
v2.8:把批量部署变成可并行、可追踪的任务
  ↓
v2.9:用统一可靠性内核连接上传、下载和批量部署

这不是简单的功能叠加,而是从“协议能力”逐步走向“现场工作流”。

v2.6:SFTP 从“能浏览”走到“能部署”

v2.6 解决的是一个非常实际的边界问题:很多 Linux、Ubuntu 和云主机环境默认使用 SSH/SFTP,而不是 FTP。此前工具可以浏览 SFTP 文件,但真正部署时仍然需要切换协议或使用其他工具。

同一套部署语义覆盖 FTP 与 SFTP

v2.6 提取了 IDeployable 部署能力接口,把协议差异收敛在适配器内部:

uploadFile()
uploadFolder()
clearRemoteDirectory()
setProgressCallback()
setCancelFlag()

FTP 适配器和 SSH/SFTP 适配器分别实现底层 I/O,业务层沿用同一套部署循环。用户只需要选择协议、设备和目标目录,不需要为不同协议学习两套部署流程。

SFTP 文件夹部署的关键细节

SFTP 文件夹上传不是简单地把文件逐个发送出去。v2.6 的上传计划先递归生成目录和文件条目,确保目录创建发生在文件上传之前;清空远程目录时保留目标目录本身;每个文件和数据块都会检查取消标志。

这些细节决定了部署行为是否可预测:嵌套目录不会因为缺少父目录而失败,清空后仍然可以继续上传,取消操作也不会等到整批任务结束才生效。

v2.6 的产品意义

v2.6 的核心不是“增加了 SFTP 选项”,而是让 FTP 和 SFTP 在用户眼中成为同一种部署能力:同一处配置、同一套进度、同一种取消和失败语义。

v2.7:把文件操作从页面功能变成双栏工作区

当部署能力补齐之后,下一个问题变成了“工程师如何高效准备任务”。v2.7 围绕双栏文件面板做了系统化收尾。

统一本地与远程文件来源

IFileSource 将文件列表、创建目录、重命名、删除、上传、下载、连接和取消等能力抽象为协议无关接口。LocalFileSource 和 RemoteFileSource 负责各自的实现,FileBrowserPanel 只负责呈现和交互。

这样做的结果是:本地目录、FTP/FTPS 目录和 SFTP 目录都可以使用统一表格、路径栏、面包屑、右键菜单和拖拽逻辑。

Total Commander 式连续操作

v2.7 将双栏操作整理为熟悉的文件管理器语义:

  • 双击目录进入,双击 .. 返回上级;
  • F2 重命名,F5 复制到对面面板,F6 移动到对面面板;
  • Tab 切换左右面板;
  • 远程面板支持系统文件拖入上传;
  • 目录优先排序,. 与 .. 保持稳定位置;
  • 远程目录读取异步化,慢网络不再冻结界面。

v2.7 还补上了异步场景中容易被忽略的可靠性问题:每次导航都带代际令牌,旧目录结果不会覆盖新路径;连接失败会自动重连并重试;SFTP 共享会话通过串行化保护,避免多个 worker 同时访问非线程安全的底层连接。

文件浏览的体验底线

文件管理器的价值不只在“能显示列表”,还在于操作不会被打断。路径栏、面包屑、连接状态点、错误提示和拖拽反馈共同构成了这个底线:工程师始终知道自己在哪个目录、当前是否已连接、一次操作是否真的完成。

v2.8:从逐台部署到并行批量部署

当目标设备从一台增加到十台、几十台,串行部署会明显拖慢现场节奏。但单纯增加并发线程并不能解决问题,真正需要的是可控的调度、独立的设备状态和可追溯的报告。

可配置的并发调度

v2.8 引入并行批量部署能力,部署并发度可在 1—8 之间配置并持久化。每台设备抽象为独立部署任务,由调度器根据并发上限分配执行资源。

设备列表
  ↓
DeploymentRunner
  ↓
并发度限制 + 取消传播
  ↓
每台设备独立执行与上报

用户不需要等待前一台设备完全结束后再手动点击下一台。与此同时,单台设备失败不会阻塞其他设备,失败设备也可以在任务结束后单独重试。

每台设备都有自己的进度和终态

批量部署最怕“总进度条显示 80%,但不知道哪台设备出了问题”。v2.8 为每台设备提供独立进度和终态:等待中、连接中、上传中、成功、失败、已取消。

取消也有明确边界:尚未开始的设备不会继续启动,正在传输的任务在安全检查点停止,所有未继续执行的设备统一记录为已取消。

报告让部署结果可以交付

v2.8 增加 CSV 和 HTML 部署报告,记录设备、文件、状态、失败摘要和耗时。报告不仅用于排查问题,也适合售后交付、版本归档和后续复盘。

从这一版开始,批量部署不再只是“同时点了很多次上传”,而成为一个有输入、有过程、有结果的任务系统。

v2.9:统一可靠传输闭环

v2.8 解决了并行批量部署,v2.9 进一步解决不同传输入口之间的语义割裂:双栏上传、双栏下载、本地复制/移动和批量部署,都应该遵循同一套可靠性规则。

一条统一的传输链路

TransferTask
    ↓
TransferScheduler
    ↓
TransferExecutor
    ↓
ITransferChannel
    ↓
FTP/FTPS 或 SFTP 通道

界面负责表达“用户想做什么”,调度器负责排队和并发,执行器负责重试、取消、校验和交付,协议通道负责具体 I/O。协议差异被隔离,可靠性语义被集中管理。

v2.9 的可靠性语义

  • 瞬时网络错误可以有限重试;
  • 认证、权限、路径和目标变化等确定性错误直接报告;
  • 文件传输支持 SHA-256 校验;
  • 临时文件完成后再提交,避免半文件被误认为成功;
  • 非原子交付场景明确告警;
  • 支持项目级取消和失败文件跳过;
  • 批量任务保留 FTP/SFTP 目录映射、清空语义和部署报告。

这套闭环的核心思想是:成功必须有证据,失败必须能定位,取消必须有终态,恢复不能破坏已经完成的结果。

现场导航也属于可靠性

可靠性不只发生在传输线程里。v2.9 同时完善了双栏导航:

  • 上下键选择文件和目录;
  • 右方向键进入目录;
  • 左方向键返回上级;
  • 返回后自动重新选中刚才进入的目录;
  • FTP CRLF 行结束不会再被误识别为目录名的一部分。

这些看似细小的行为,决定了工程师能否连续操作。一次返回不应该让用户重新寻找目录,一次服务器格式差异也不应该变成“URL 格式错误”。

四个版本,解决的是同一个问题

把 v2.6 到 v2.9 放在一起看,可以发现它们始终围绕同一条主线:让设备、文件和任务成为一个连续上下文。

阶段主要问题解决方式
v2.6SFTP 能浏览但不能完整部署IDeployable 统一 FTP/SFTP 部署能力
v2.7文件操作割裂、慢网络易卡顿IFileSource + 双栏面板 + 异步目录加载
v2.8多设备部署慢且结果不清晰并发调度、设备级进度、报告和失败重试
v2.9上传、下载、批量部署语义不一致TransferScheduler + TransferExecutor 统一可靠传输闭环

这条路线没有追求“功能数量最多”,而是持续减少现场操作中的断点。

一个完整的现场使用场景

假设需要把一个软件版本部署到多台 Linux 设备:

  1. 在 DeviceForge 中选择 SFTP,绑定目标设备;
  2. 左栏打开本地版本目录,右栏定位远程目标目录;
  3. 用方向键或双击检查目录结构;
  4. 将文件拖到远程面板,或者提交批量部署任务;
  5. 统一选择覆盖策略,避免任务过程中反复确认;
  6. 由调度器按并发度执行,实时查看每台设备状态;
  7. 网络短暂中断时执行有限重试;
  8. 对失败设备单独重试,成功设备不重复执行;
  9. 导出 CSV/HTML 报告,留存本次版本交付记录。

工程师始终围绕同一个工作区完成任务,不需要在 FTP 客户端、脚本窗口、批量部署工具和表格之间来回切换。

技术架构:让可靠性成为公共能力

DeviceForge 采用 Qt 6 + C++17,应用层使用 ToolBackend/ToolWidget 双层结构,协议访问通过 IProtocolAdapter 和 ProtocolRegistry 统一管理。文件工作区和传输内核进一步将 UI、业务编排和协议 I/O 分开:

FileBrowserPanel
    ↓
TransferTask / DeploymentJob
    ↓
TransferScheduler
    ↓
TransferExecutor
    ↓
ITransferChannel / IDeployable
    ↓
FtpAdapter / SshAdapter

异步 UI 使用代际令牌、QPointer 守卫和 queued callback,防止快速导航、重连和窗口销毁时出现旧回调覆盖新状态。配置通过 ConfigStore 持久化,敏感凭据使用 DPAPI 保护;日志遵循脱敏规则,不记录密码和不必要的原始通信内容。

适合哪些团队?

  • 工业自动化、PLC 和嵌入式设备研发团队;
  • 需要批量升级 Linux 网关、工控机和边缘设备的交付团队;
  • 需要同时使用 FTP/SFTP、Telnet/SSH、Modbus、OPC UA 的调试人员;
  • 需要把部署结果交付给客户或纳入版本归档的售后团队。

如果只是偶尔上传一个文件,普通 FTP 客户端已经足够;但如果你的工作包含多台设备、目录确认、失败恢复和结果交付,那么“工具是否能连续工作”就比“有没有上传按钮”重要得多。

当前边界与后续方向

DeviceForge v2.6—v2.9 已覆盖 FTP/FTPS/SFTP 文件浏览与部署、双栏文件管理、并行批量部署、报告导出和统一可靠传输。SCP 独立上传通道、跨平台 GUI、插件化 ToolHost 等能力仍属于后续路线,不把规划内容包装成当前已交付功能。

这也是项目希望坚持的发布方式:每个版本明确完成了什么、没有完成什么,并用测试和现场验证支撑功能描述。

结语:从工具集合走向现场伙伴

从 v2.6 到 v2.9,DeviceForge 完成了一次连续演进:

  • 从 FTP 扩展到 FTP/SFTP 并行支持;
  • 从文件浏览扩展到完整双栏工作区;
  • 从逐台部署扩展到可配置并发和设备级报告;
  • 从多个传输入口扩展到统一可靠性闭环。

最终目标不是让软件看起来更复杂,而是让工程师在真实现场少做重复确认,多保留有效进度;遇到慢网络、断线和失败时,知道系统正在做什么,也知道下一步从哪里继续。

DeviceForge 仍在持续演进。如果你正在维护一批工业设备,或者正在为团队寻找一个可以统一部署、测试和调试的桌面工具,欢迎访问项目主页、试用软件并提出 Issue。

项目地址:turnarond/DeviceForge