Linux timeout 命令完全指南:指定固定时间并发送固定信号

Linux timeout 命令完全指南:指定固定时间并发送固定信号

日常运维中,我们经常需要运行一些可能"卡住"的命令------压测脚本、爬虫、抓包工具、长任务进程。它们平时运行正常,但偶尔会因为网络抖动、死锁、等待输入等原因一直不退出 ,把终端或后台任务死死占住。这时候,timeout 命令就是最省心的"保险丝"。

一、timeout 能做什么

timeout 是 GNU coreutils 自带的一个命令,作用是:运行一个命令,若它在指定时间内没有结束,就向它发送一个信号,强制或优雅地把它终止。

它解决的核心痛点是:

  • 命令卡死时能自动超时退出,不用人工 Ctrl+C
  • 可以灵活指定"超时多久"、"到时发什么信号"
  • 避免长任务无限期占用系统资源

二、基本语法

bash 复制代码
timeout [选项] 持续时间 命令 [参数...]

其中"持续时间"就是超时阈值,后面的 命令 参数 是真正要执行的内容。

三、指定固定时间

时间可以直接写数字,也可以带后缀。默认单位是秒,后缀 s 表示秒、m 表示分钟、h 表示小时、d 表示天。

bash 复制代码
# 10 秒(不带后缀默认秒)
timeout 10   mycmd

# 显式写 10 秒,更清晰
timeout 10s  mycmd

# 5 分钟
timeout 5m   mycmd

# 2 小时
timeout 2h   mycmd

小提示:timeout 10 和 timeout 10s 是等价的。为了可读性,建议显式加上单位后缀。

四、指定固定信号

到点之后,timeout 默认发送 SIGTERM (信号 15)。我们可以用 -s / --signal= 指定到底发送哪种信号:

bash 复制代码
# 到时发送 SIGINT(Ctrl+C 的等效信号,2 号)
timeout --signal=INT  10s  mycmd

# 到时发送 SIGTERM(默认,15 号)
timeout --signal=TERM 10s  mycmd

# 到时直接 SIGKILL(9 号,无法被捕获,立即强杀)
timeout -s KILL       10s  mycmd

信号既可以写名称(INT、TERM、KILL),也可以写数字(2、15、9)。

常见的信号选择逻辑:

信号 数字 行为 适用场景
SIGTERM 15 优雅终止,进程可捕获并清理 默认选择,多数场景
SIGINT 2 相当于手动 Ctrl+C 希望模拟用户中断
SIGKILL 9 立即强杀,无法被捕获 兜底,进程彻底不响应时

五、完整示例深度解读

你可能会在实际脚本里看到这样一条命令:

bash 复制代码
timeout --signal=INT --kill-after=10s 10s \ ngauge /root/ngauge-test-20260929/config.yml

我们来拆解它的每一部分含义:

  • timeout:超时控制命令
  • --signal=INT:到点时发送 SIGINT 信号,让 ngauge 优雅地收尾
  • --kill-after=10s:发送 SIGINT 之后再给 10 秒缓冲时间
  • 10s:总共运行 10 秒,到时触发超时
  • ngauge /root/ngauge-test-20260929/config.yml:实际要运行的命令及其参数

执行的完整时间线:

  1. 启动 ngauge,加载 config.yml 开始压测
  2. 运行 10 秒后,timeout 向 ngauge 发送 SIGINT,通知它"该停了,自己清理"
  3. 此时 ngauge 有机会保存数据、关闭连接、释放资源(不会立即被杀掉)
  4. 如果 ngauge 在 10 秒的缓冲期内正常退出,流程就顺利结束
  5. 如果 ngauge 收到 SIGINT 后 10 秒内仍然不死,--kill-after 触发,发送 SIGKILL 强制杀死

一句话总结 :这是非常经典的"先优雅后强制"的停止策略------给进程一次体面退出的机会,实在不行再动刀。

六、为什么这样设计很有用

很多服务类工具收到 SIGINT 后会做资源清理:比如压测工具要关闭网络连接、抓包工具要落盘保存数据、数据库客户端要提交事务。如果一上来就发 SIGKILL,这些数据可能直接丢失或损坏。

而 --kill-after 正好弥补了"发了优雅信号但进程仍卡死"的漏洞,保证一定能在某个时间点杀掉进程,不会无限期挂住。这对脚本、CI、定时任务里的防挂死处理特别有价值。

七、其他常用选项

timeout 还有几个实用的参数:

bash 复制代码
# 超时后保留命令的退出码,方便脚本判断失败原因
timeout --preserve-status 10s mycmd

# 在前台模式下运行(配合管道使用,避免无法获取子进程输出)
timeout --foreground 10s cmd | tee log.txt

# 把超时时长作为第一个参数传给命令(少见,但存在)
timeout --timeout=10s mycmd
  • --preserve-status:超时杀掉命令后,返回 127 还是命令实际退出码由它决定,用于脚本精确判断"是超时了还是真出错了"。
  • --foreground:当 timeout 和管道、后台作业一起用,无法往子进程发信号时使用。

八、总结

timeout 是一个小而美的命令,核心要素只有两个:

  1. 时间:告诉它"多久算超时"
  2. 信号:告诉它"超时后怎么处理"

再配合 --kill-after,就能实现"给机会、不无限等 "的优雅停止策略。下次再写压测、抓包或长任务脚本,别忘了给它上一道 timeout 保险丝。

相关推荐
香吧香6 小时前
venv 详解
python
笨笨饿6 小时前
#142_VS Code.map文件插件的用法
git·python·stm32·单片机·嵌入式硬件·物联网·vim
zwd20056 小时前
Manim 竖屏 1080×1920 配置详解:pixel_width、frame_width 怎么写(0.21.0 / 0.22.0 实测)
python·manim·数学动画·短视频制作·manim教程·竖屏视频
Nontee6 小时前
Quartz 新手入门:定时任务的两个承诺
开发语言·windows·python
wewowilling6 小时前
LangChain入门
python·ai·langchain·prompt
haluhalu.7 小时前
深入理解AIAgent(1.3)--- 设计模式
人工智能·python·设计模式·langchain
估值探索者7 小时前
【Python量化选股流水线 #03】候选股怎么排序?动量+低波+流动性三因子打分取 Top-N
开发语言·python·接口·api接口·股票数据接口·数据接口·股票数据api接口
骑士雄师7 小时前
supervisor 中关于上下文多轮信息维护常用到的python语法
开发语言·python
青少儿编程课堂7 小时前
蓝桥杯·全国青少年信息素养大赛·电子学会Python/C/C++考级:任意进制互转与大数多进制加法解析
c++·python·算法·bfs·信息学竞赛
Orchestrator_me7 小时前
k8s网络与应用
网络·python·kubernetes