You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何编写Bash脚本连接Unix套接字待欢迎消息后读写数据?

实现方案

你之前直接通过管道发命令失效的核心原因是:管道会在套接字连接建立的同时就把指令写入,此时服务端还处于初始化握手阶段(未完成欢迎消息发送前不处理命令),因此需要先等待欢迎消息返回,确认服务端就绪后再发送隧道指令。

方案1:仅用socat实现(无额外依赖)

socat原生支持期望-发送的交互逻辑,无需安装其他工具即可满足需求:

# 基础交互命令
socat UNIX-CONNECT:data/files/monitor.socket STDOUT \
  expect="Connected to soundwave server v131" \
  send="tunnel r 7 localhost:22\n"

如果需要直接提取端口供后续SSH使用,可以结合grep过滤结果:

# 提取端口存到变量
TUNNEL_PORT=$(socat UNIX-CONNECT:data/files/monitor.socket STDOUT \
  EXPECT="Connected to soundwave server v131" \
  SEND="tunnel r 7 localhost:22\n" | grep -oP 'local port \K\d+')

# 后续直接调用变量发起SSH连接
ssh -p ${TUNNEL_PORT} 你的用户名@localhost

注意:部分旧版本socat需要将expect、send关键字替换为全大写的EXPECT、SEND,运行报错时调整即可。

方案2:用expect工具实现(适配复杂场景)

如果后续还有更多交互逻辑,可以用专门的交互处理工具expect,脚本复用性更强:

  1. 编写expect脚本tunnel.exp:
#!/usr/bin/expect -f
# 建立Unix套接字连接
spawn socat UNIX-CONNECT:data/files/monitor.socket STDOUT
# 等待服务端返回欢迎消息
expect "Connected to soundwave server v131"
# 发送隧道命令,末尾加\n模拟手动回车
send "tunnel r 7 localhost:22\n"
# 匹配端口返回结果,正则提取端口
expect -re {local port (\d+)\.}
# 输出端口供bash侧捕获
puts $expect_out(1,string)
  1. 给脚本加执行权限后,在bash中直接调用获取端口:
chmod +x tunnel.exp
TUNNEL_PORT=$(./tunnel.exp)
ssh -p ${TUNNEL_PORT} 你的用户名@localhost

内容的提问来源于stack exchange,提问作者Mikey A. Leonetti

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.25 18:54:02