You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多
文档控制台
免费开始使用

Shell脚本并行处理/多线程:优化curl批量拉取文件速度

并行化Curl拉取文件的几种实用方法

Got it, let's fix that slow file download issue right away. Parallelizing your curl requests doesn't require fancy multi-threading skills—there are a few straightforward tools and shell tricks you can use to batch your downloads (10 at a time, like you wanted) and cut down that 30-minute wait significantly.

方法1:用xargs(最简便,原生支持)

xargs是大多数Unix/Linux系统自带的工具,能轻松实现并行任务。核心思路是把你的文件URL列表传给xargs,让它同时启动指定数量的curl进程。

步骤:

  1. 先把所有要拉取的文件URL整理到一个文本文件里,比如urls.txt,每行一个URL:
    # 示例urls.txt内容
    https://yourapp.com/files/file1.txt
    https://yourapp.com/files/file2.txt
    ...
    https://yourapp.com/files/file100.txt
    
  2. 用xargs启动10个并行curl进程,每个进程处理一个URL:
    xargs -P 10 -n 1 curl -O < urls.txt
    
    • -P 10:同时运行10个并行进程
    • -n 1:每次给curl传1个URL参数
    • -O:让curl用原文件名保存文件(如果需要自定义文件名,可以结合xargs占位符调整,比如-o "output_{}"

如果需要更精细的控制(比如加超时、重试),可以把curl命令写得更完整:

xargs -P 10 -n 1 curl --connect-timeout 10 --max-time 30 --retry 2 -O < urls.txt

方法2:用GNU Parallel(功能更强大)

如果你的系统没有自带GNU Parallel,可以通过包管理器安装(比如apt install parallelbrew install parallel)。它比xargs更灵活,支持批量处理、进度显示、失败重试等。

基本用法:

urls.txt读取URL,每次并行10个,保存为原文件名:

parallel -j 10 curl -O {} :::: urls.txt
  • -j 10:设置并行任务数为10
  • {}:代表从文件中读取的每个URL
  • :::::表示从文件读取输入(如果直接传URL列表用:::

如果要自定义输出文件名,比如给每个文件加前缀:

parallel -j 10 curl {} -o "downloaded_{/}" :::: urls.txt

这里{/}会提取URL中的文件名部分,最终保存为downloaded_file1.txt这样的格式。

方法3:原生Shell后台进程(无需额外工具)

如果不想安装任何工具,纯Shell脚本就能实现批次并行。思路是在循环中把每个curl放到后台运行,每积累10个就等待所有后台进程完成,再继续下一批。

示例脚本:

#!/bin/bash

# 读取URL列表文件
URLS_FILE="urls.txt"
# 每批并行数
BATCH_SIZE=10

count=0
while read -r url; do
    # 启动curl后台进程,自定义保存文件名
    filename=$(basename "$url")
    curl --connect-timeout 10 --max-time 30 "$url" -o "$filename" &
    
    count=$((count + 1))
    # 每到BATCH_SIZE个进程,等待所有完成
    if [ $count -eq $BATCH_SIZE ]; then
        wait
        count=0
        echo "完成一批下载,继续下一批..."
    fi
done < "$URLS_FILE"

# 等待最后一批未完成的进程
wait
echo "所有文件下载完成!"

重要注意事项

  • 控制并行数:不要把并行数设得太高(比如超过20),否则可能被目标服务器判定为攻击,导致连接被拒绝或限速。先从10开始测试,根据服务器响应调整。
  • 添加超时和重试:给curl加--connect-timeout--max-time参数,避免单个请求卡住拖慢整个批次;--retry可以让失败的请求自动重试。
  • 处理文件名冲突:如果多个URL指向同名文件,要自定义输出文件名(比如加序号或前缀),避免覆盖。
  • 日志记录:可以把curl的输出重定向到日志文件,方便排查失败的下载:
    curl "$url" -o "$filename" >> download.log 2>&1 &
    

内容的提问来源于stack exchange,提问作者santosh sm

火山引擎 最新活动