并行运行多个curl命令

问题描述 投票:0回答:9

我有以下 shell 脚本。问题是我想并行/并发运行事务,而无需等待一个请求完成即可转到下一个请求。例如,如果我发出 20 个请求,我希望它们同时执行。

for ((request=1;request<=20;request++))
do
    for ((x=1;x<=20;x++))
    do
        time curl -X POST --header "http://localhost:5000/example"
    done
done

有什么指南吗?

bash shell curl
9个回答
98
投票

您可以使用

xargs
-P
选项来并行运行任何命令:

seq 1 200 | xargs -n1 -P10  curl "http://localhost:5000/example"

这将运行

curl
命令 200 次,最多并行 10 个作业。


76
投票

使用

xargs -P
选项,您可以并行运行任何命令:

xargs -I % -P 8 curl -X POST --header "http://localhost:5000/example" \
< <(printf '%s\n' {1..400})

这将运行给定的

curl
命令
400
次,一次并行运行最多
8
作业。


32
投票

2020 年更新:

Curl 现在可以并行获取多个网站:

curl --parallel --parallel-immediate --parallel-max 3 --config websites.txt

websites.txt 文件:

url = "website1.com"
url = "website2.com"
url = "website3.com"

13
投票

这是对

@saeed's
答案的补充。

我遇到了一个问题,它向以下主机发出了不必要的请求

0.0.0.1, 0.0.0.2 .... 0.0.0.N

原因是命令

xargs
将参数传递给curl命令。为了防止传递参数,我们可以使用
-I
标志来指定用哪个字符来替换参数。

所以我们将使用它,

 ... xargs -I '$' command ...

现在,只要找到

xargs
文字,
$
就会替换参数。如果没有找到,则参数不会通过。所以使用这个最终命令将是。

seq 1 200 | xargs -I $ -n1 -P10  curl "http://localhost:5000/example"

注意:如果您在命令中使用

$
,请尝试将其替换为其他未使用的字符。


7
投票

除了

@saeed's
答案之外,我创建了一个通用函数,它利用函数参数在并行的
N
作业中总共触发命令
M

function conc(){
    cmd=("${@:3}")
    seq 1 "$1" | xargs -n1 -P"$2" "${cmd[@]}"
}
$ conc N M cmd
$ conc 10 2 curl --location --request GET 'http://google.com/'

这将以两个最大并行度触发

10
curl 命令。

将此功能添加到

bash_profile.rc
中会更容易。 要点


2
投票

最后添加“等待”,并将其背景化。

for ((request=1;request<=20;request++))
do
    for ((x=1;x<=20;x++))
    do
        time curl -X POST --header "http://localhost:5000/example" &
    done
done

wait

它们都会输出到同一个标准输出,但您可以将时间结果(以及标准输出和标准错误)重定向到命名文件:

time curl -X POST --header "http://localhost:5000/example" > output.${x}.${request}.out 2>1 &

2
投票

想分享我如何将并行 xargs 与 curl 结合使用的示例。

使用 xargs 的优点是您可以指定将使用多少个线程来并行卷曲,而不是使用带“&”的卷曲,这将同时安排所有卷曲,比如说 10000 个卷曲。

希望对smdy有帮助:

#!/bin/sh

url=/any-url
currentDate=$(date +%Y-%m-%d)
payload='{"field1":"value1", "field2":{},"timestamp":"'$currentDate'"}'
threadCount=10

cat $1 | \
xargs -P $threadCount -I {} curl -sw 'url= %{url_effective}, http_status_code = %{http_code},time_total = %{time_total} seconds \n' -H "Content-Type: application/json" -H "Accept: application/json" -X POST $url --max-time 60 -d $payload

.csv 文件每行有 1 个值,将插入到 json 负载中


0
投票

根据 @isorylcyanide 提供的解决方案和 @Dario Seidl 的评论,我发现这是最好的响应,因为它同时处理curl和httpie。

# conc N M cmd - fire (N) commands at a max parallelism of (M) each
function conc(){
    cmd=("${@:3}")
    seq 1 "$1" | xargs -I'$XARGI' -P"$2" "${cmd[@]}"
}

例如:

conc 10 3 curl -L -X POST https://httpbin.org/post -H 'Authorization: Basic dXNlcjpwYXNz' -H 'Content-Type: application/json' -d '{"url":"http://google.com/","foo":"bar"}'

conc 10 3 http --ignore-stdin -F -a user:pass httpbin.org/post url=http://google.com/ foo=bar

0
投票

要使用 cURL 发送多个请求,您只需使用此行

for i in $(seq 100); do $(curl 'http://192.168.0.1/' > /dev/null 2>&1 &) ; done ;
即可并行化您指定的连接数。

© www.soinside.com 2019 - 2024. All rights reserved.