Contents

使用wget并行下载

1. 概述

在本教程中,我们将使用一个简单的工具wget并行下载多个文件。

本文中使用的命令在bash 中进行了测试,但在其他兼容 POSIX 的 shell 中也应适用。

2.使用wget下载文件

使用wget下载文件非常简单:

wget https://my.website.com/archive.zip

不幸的是,我们一次只能下载一个文件。

我们必须求助于 shell 脚本在一个命令中下载多个文件:

#!/bin/bash
while read file; do
    wget ${file}
done < files.txt

在这里,files.txt包含所有必须下载的文件,每个文件都在自己的行中:

https://my.website.com/archive-1.zip
https://my.website.com/archive-2.zip
https://my.website.com/archive-3.zip

然而,这种方法的问题是文件是按顺序下载的。我们可以通过并行下载文件来加快速度。

3. 使用wget并行下载

我们可以通过不同的方式使wget并行下载文件。

3.1. Bash 方法

一种简单但有点幼稚的方法是使用 & 运算符将wget进程发送到后台:

#!/bin/bash
while read file; do
    wget ${file} &
done < files.txt

wget的每次调用都分叉到后台并在其自己单独的子 shell 中异步运行。

虽然我们现在并行下载文件,但这种方法并非没有缺点。例如,没有关于下载完成或失败的反馈。另外,我们无法控制一次执行多少进程。

3.2. 让wget Fork 自己

我们可以做得更好一点,通过传递*-b作为参数让wget*将自己分叉到后台:

#!/bin/bash
while read file; do
    wget ${file} -b
done < files.txt

与*&运算符一样,每个调用都分叉到后台并异步运行。但不同的是,-b*参数还为我们制作了每次下载的日志文件。我们可以grep 这些日志文件来检查没有错误发生。

3.3. 使用xargs

解决我们问题的最复杂和干净的解决方案是使用xargsxargs命令接受一个参数列表并将它们传递给一个选择的实用程序,可以并行运行多个进程。

最重要的是,它使我们能够控制在任何给定时间同时运行的最大进程数。

例如,我们可以为files.txt中的每一行调用wget,最多并行两个进程:

#!/bin/bash
cat files.txt | xargs -n 1 -P 2 wget -q

我们还将wget设置为安静 ( -q )。否则,xargs会将所有进程的输出重定向到 stdout,这会立即使我们的终端变得混乱。相反,我们可以依赖xargs的返回码。如果没有发生错误,它将以 0 值退出,否则以 1 值退出。