Apache DolphinScheduler RemoteShell 任务深度解析:远程服务器命令执行从配置到原理
【免费下载链接】dolphinschedulerApache DolphinScheduler is the modern data orchestration platform. Agile to create high performance workflow with low-code项目地址: https://gitcode.com/GitHub_Trending/dol/dolphinscheduler
本文以 Apache DolphinScheduler 官方文档 RemoteShell 任务指南 为主线,结合
dolphinscheduler-task-plugin/dolphinscheduler-task-remoteshell模块的源码实现与测试用例,系统讲解 RemoteShell 任务的定义、SSH 数据源前置配置、任务创建步骤、脚本编写规范与运行原理。读完本文,你将掌握如何在 DolphinScheduler 中安全、可靠地把 Shell 命令分发到任意远程服务器执行,并理解其"本地成脚本 → SFTP 上传 → 远程执行 → 日志回传 → 状态回收"的完整链路。
RemoteShell 是 Apache DolphinScheduler 中的一类任务插件,用于在远程服务器上执行命令。它适合对无法直接部署 DolphinScheduler Worker 的存量机器、堡垒机后主机或独立计算节点进行命令下发与结果回收,是 Shell 任务(本机执行)的重要补充。
RemoteShell 任务概述
RemoteShell 任务类型的核心定位非常明确:在远程服务器上执行命令。与 Shell 任务(在 Worker 所在机器执行)不同,RemoteShell 会通过 SSH 协议连接到你在任务中指定的远程服务器,将脚本上传并执行,再把执行日志与退出状态回传到 DolphinScheduler 控制台。
在源码层面,该能力由独立插件模块承载,插件注册名为REMOTESHELL,参见 RemoteShellTaskChannelFactory.java:
@AutoService(TaskChannelFactory.class) public class RemoteShellTaskChannelFactory implements TaskChannelFactory { @Override public TaskChannel create() { return new RemoteShellTaskChannel(); } @Override public String getName() { return "REMOTESHELL"; } }任务参数模型RemoteShellParameters仅需三个核心字段即可驱动整个任务,见 RemoteShellParameters.java:
rawScript:要执行的脚本内容(必填,校验逻辑为rawScript != null && !rawScript.isEmpty());type:数据源类型,固定为 SSH;datasource:所选 SSH 数据源的 ID。
前置准备:创建 SSH 数据源
RemoteShell 任务依赖 SSH 数据源完成远程连接,因此在创建任务之前,需要先在数据源中心添加 SSH 类型的数据源。
从 SSHConnectionParam.java 可以看到 SSH 数据源支持的连接参数:
| 参数 | 说明 | 默认值 |
|---|---|---|
host | 远程服务器地址(IP 或域名) | 无 |
port | SSH 端口 | 22 |
user | 登录用户名 | 无 |
password | 密码认证方式下的登录密码 | 无 |
privateKey | 私钥认证方式下的 SSH 私钥内容 | 无 |
密码与私钥二选一即可完成认证。测试用例中的连接参数 JSON 也印证了这一结构,见 RemoteExecutorTest.java:
{"user":"root","password":"123456","host":"dolphinscheduler.com","port":22, "privateKey":"ssh-rsa AAAAB"}创建数据源的一般路径为:安全中心或数据源中心 → 新增数据源 → 选择 SSH 类型 → 填写上述连接信息 → 测试连接并保存。任务运行时,RemoteShellTask会通过DataSourceUtils.buildConnectionParams将数据源参数转换为SSHConnectionParam,再交由RemoteExecutor建立会话(见 RemoteShellTask.java)。
创建 RemoteShell 任务
在 DAG 编辑页面中创建 RemoteShell 任务的步骤如下:
- 进入项目管理 → 项目名称 → 工作流定义,点击"创建工作流"按钮,进入 DAG 编辑页面。
- 在工具栏中拖动
RemoteShell图标到画板中,即可完成节点创建。
创建后,DAG 画布上会出现 RemoteShell 节点,可以像其他任务节点一样接入前置任务、设置依赖关系并加入工作流调度。
从 UI 源码看,RemoteShell 节点的表单由 use-remote-shell.ts 生成,包含一个必填的脚本编辑器(对应rawScript)和一组自定义参数(对应localParams,用于声明参数与输出参数),这与下方任务参数一一对应。
任务参数详解
RemoteShell 任务的参数分为两部分:
1. 默认任务参数
包括任务名称、运行标志、缓存执行、描述、任务优先级、Worker 分组、任务组名称、组内优先级、环境名称、失败重试次数、失败重试间隔、CPU 配额、最大内存、超时告警、资源、前置任务、延时执行时间等。这些是所有任务类型共享的公共参数,完整说明请参考 DolphinScheduler 任务参数附录 中的"默认任务参数"一栏。
2. RemoteShell 专属参数
| 参数 | 说明 |
|---|---|
| 脚本 | 必填。在远程服务器上执行的 Shell 脚本内容,支持自定义参数占位符与输出参数声明 |
| 自定义参数 | 可选。声明脚本中使用的局部参数,也可通过setValue语法定义输出参数回传上游/下游 |
| SSH Data Source | 必选。选择前面创建好的 SSH 数据源,任务将连接该数据源指向的远程服务器执行脚本 |
其中"SSH Data Source"是 RemoteShell 区别于其他任务类型的核心参数——脚本真正执行的主机由它决定。
任务样例:查看远程服务器的路径
下面演示一个最基础、可复现的样例:通过 RemoteShell 任务查看远程服务器remote-server上的当前路径。
假设你已经创建好指向remote-server的 SSH 数据源,在工作流 DAG 中拖入 RemoteShell 节点后,在脚本编辑器中输入:
pwd保存并在"SSH Data Source"中选择对应数据源,运行工作流后即可在任务日志中看到远程服务器返回的路径,效果如下图所示:
在实际生产脚本中,你可以将pwd替换为任意命令组合,例如df -h、hostname、ls、systemctl status xxx,或一段多行 Shell 逻辑。
运行原理:一次 RemoteShell 任务的完整生命周期
要真正用好 RemoteShell,理解其底层执行链路至关重要。从 RemoteShellTask.java 与 RemoteExecutor.java 的源码可以看出,一次任务执行大致经历以下阶段:
1. 本地生成脚本(buildCommand)
Worker 在本地执行路径下生成{taskAppId}_node.sh脚本文件,buildCommand()会完成三类内容拼接(见 RemoteShellTask.java):
- 将
\r\n统一转换为\n,规避 Windows 换行符导致的执行异常; - 通过
parseScript()把任务参数(prepareParamsMap)中的占位符替换为真实值; - 若任务配置了环境名称(环境变量配置),会将
environmentConfig追加到脚本头部; - 最后统一添加
#!/bin/bash头,并在脚本末尾追加状态标记行:echo DOLPHINSCHEDULER-REMOTE-SHELL-TASK-STATUS-$?。
测试 RemoteShellTaskTest.java 精确验证了上述拼装结果:
#!/bin/bash export PATH=/opt/anaconda3/bin:$PATH # 来自任务的环境名称配置 echo 1 # 来自脚本内容 echo DOLPHINSCHEDULER-REMOTE-SHELL-TASK-STATUS-$? # 自动追加的状态标记2. SFTP 上传脚本(saveCommand)
RemoteExecutor通过 Apache MINA SSHD 客户端建立 SSH 会话(SshClient.setUpDefaultClient()+SSHUtils.getSession),先用mkdir -p确保远程目录存在(目录为/tmp/dolphinscheduler-remote-shell-{user}/),再通过 SFTP 把本地脚本上传为远程的{taskId}.sh,见 RemoteExecutor.java。
3. 远程后台执行(run)
上传成功后,以 nohup 方式在远程启动脚本并把输出重定向到日志文件(见 RemoteExecutor.java):
nohup /bin/bash /tmp/dolphinscheduler-remote-shell-{user}/{taskId}.sh > .../{taskId}.log 2>&1 &同时在执行前会通过ps -ef | grep "{taskId}.sh" | grep -v grep检查是否已有同名任务在跑,避免重复执行(见 RemoteExecutor.java)。
4. 日志跟踪与状态回收(track + getTaskExitCode)
任务采用"轮询式"日志回传:循环执行tail -n +N .../taskId.log增量拉取日志,并在远程进程 PID 消失后结束;同时通过TaskOutputParameterParser解析日志中的setValue(...)输出参数(见 RemoteExecutor.java)。测试 RemoteExecutorTest.java 验证了脚本输出echo "${setValue(my_prop=my_value)}"后,my_prop会被正确解析为任务输出参数。
执行结束后,通过tail -n 1 .../taskId.log读取末尾的状态标记行DOLPHINSCHEDULER-REMOTE-SHELL-TASK-STATUS-{code},解析出真实退出码:0记为成功,非0记为失败(见 RemoteExecutor.java),并最终通过remoteShellParameters.dealOutParam(...)将输出参数写回任务上下文。
5. 取消与清理
- 取消(kill):任务取消时,先用
pstree -p {pid}递归查出全部子进程 PID,再统一kill -9,确保不留孤儿进程,见 RemoteExecutor.java。测试用例中对 PID 解析、异常回退等分支均有覆盖。 - 清理(cleanData):任务结束后删除远程的
{taskId}.sh与{taskId}.log;清理失败不影响任务本身结果(见 RemoteExecutor.java)。
整个执行器实现了AutoCloseable,handle()方法中通过 try-with-resources 在任务结束时自动关闭 SSH 会话与客户端,避免连接泄漏(见 RemoteShellTask.java)。
注意事项
环境变量不会自动加载
RemoteShell 任务连接服务器后,不会自动 sourcebashrc、profile等登录环境文件,这一点与登录远程机器执行命令的行为不同。因此,脚本依赖的 PATH、JAVA_HOME、PYTHON_HOME 等环境变量默认是缺失的,需要显式导入,官方文档给出两种方式:
- 通过环境管理导入:在安全中心 → 环境管理中创建包含所需环境变量(如
export PATH=...)的环境配置,然后在 RemoteShell 任务定义的环境名称选项中引用该环境。源码中环境配置会被追加到脚本头部执行(见上文buildCommand逻辑),等效于先export再执行你的脚本。 - 直接在脚本中输入:在 RemoteShell 脚本正文开头直接书写
export语句,例如:
export PATH=/usr/local/jdk1.8.0_202/bin:$PATH export JAVA_HOME=/usr/local/jdk1.8.0_202 export PYTHON_HOME=/opt/anaconda3 # 你的业务命令两种方式选其一即可,若脚本本身只依赖bash内置命令或系统默认 PATH 中的命令,则无需额外配置。
其他实践建议
- 脚本输出尽量精简:任务日志通过轮询远程
.log文件增量回传,大量冗余输出会占用 Worker 与网络带宽; - 合理使用超时与重试:在任务的默认参数中配置"失败重试次数/间隔"和"超时告警",可提升远程执行场景下的任务健壮性;
- 输出参数使用
setValue语法:在脚本中通过echo "${setValue(key=value)}"声明输出参数,可被下游任务消费(有测试用例验证)。
总结
RemoteShell 为 DolphinScheduler 补齐了"跨主机命令编排"的能力:通过 SSH 数据源解耦目标机器,通过脚本上传、后台执行、日志轮询回传、状态标记回收、进程树 kill 等机制,将远程命令执行纳入工作流调度与监控体系。结合本文源码分析可知,其运行链路成熟、失败路径有明确清理逻辑,适合作为跨集群运维命令、存量机器批量操作的调度底座。
如需了解 RemoteShell 之外更多任务类型,可继续阅读 任务插件使用指南 与 任务参数附录;若关注任务执行环境的完整参数,可参考 系统架构配置说明。
【免费下载链接】dolphinschedulerApache DolphinScheduler is the modern data orchestration platform. Agile to create high performance workflow with low-code项目地址: https://gitcode.com/GitHub_Trending/dol/dolphinscheduler
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考