如何在tar提取目标文件后自动终止curl的大tar包下载?
如何在tar提取目标文件后立刻中断curl的下载
我明白你的痛点——用curl https://example.com/big.tar | tar -xf - target-file提取单个文件时,明明tar早就把需要的文件取出来了,curl却还在吭哧吭哧下载整个大tar包,太浪费带宽和时间了对吧?
其实核心问题在于管道的默认行为:只要上游进程(curl)还在输出,下游(tar)哪怕已经停止读取,curl也会继续把整个文件下载完。要解决这个问题,我们需要在tar完成提取后主动终止curl的进程,下面是具体的实现思路,还有你提到的bash脚本方案:
实现思路:追踪进程并主动终止
我们可以把curl放到后台运行,记录它的进程ID,等tar成功提取目标文件后,直接用这个ID杀掉curl进程。这里用命名管道来传递进程ID会比直接用变量更可靠,避免后台进程环境变量隔离的问题。
示例bash脚本
#!/bin/bash # 替换成你的远程tar包URL REMOTE_TAR="https://your-server.com/large-archive.tar" # 替换成你要提取的目标文件(tar包内的相对路径) TARGET="internal/path/to/your/file" # 临时命名管道,用来传递curl的PID PID_FIFO="/tmp/curl_pid.fifo" # 创建命名管道 mkfifo "$PID_FIFO" # 启动curl后台进程,记录PID并写入管道 curl "$REMOTE_TAR" & CURL_PID=$! echo "$CURL_PID" > "$PID_FIFO" # 执行tar提取,成功后立刻终止curl if tar -xf - "$TARGET"; then kill "$(cat "$PID_FIFO")" echo "已成功提取目标文件,已中断curl下载" fi # 清理临时管道 rm "$PID_FIFO"
脚本说明
- 命名管道:用
mkfifo创建的管道可以安全地在不同进程间传递数据,这里用来传递curl的进程ID,避免后台进程和主进程的变量不互通的问题。 - 后台运行curl:
curl &让curl在后台下载,$!会捕获它的进程ID。 - tar执行判断:
tar -xf - "$TARGET"从标准输入读取数据并提取指定文件,一旦tar返回成功(提取完成),就通过kill命令终止curl进程。 - 清理工作:最后删除临时的命名管道,避免残留文件。
这个脚本完美解决了你的问题——tar拿到目标文件后立刻叫停curl,不用再等整个大tar包下载完。
内容的提问来源于stack exchange,提问作者shabbir hussain
相关产品推荐
相关产品推荐

