我在这里所做的事情有点复杂,所以希望我能很好地解释它,以便它有意义。 tldr 版本是我想读取一个文件的 10 行,然后根据该文件的输入运行一个脚本。完成后,继续下 10 个,直到文件完成,然后结束。
这是一个很长的故事。我正在尝试对新闻组进行一些存档。我有一个要存档的 42227 个新闻组的列表。我正在使用 sinntp 应用程序从 usenet 服务器中提取信息。它是用Python编写的,有一个严重的错误。如果新闻组消息丢失,它将失败地结束命令而不重试。
我的解决方法是 downloader.sh。如果sinntp失败,downloader.sh将强制其重试,直到完成。一旦完成,它会重命名并压缩输出文件以进行永久存储(最终在 archive.org 上)。
下载器.sh:
#!/bin/bash
while getopts g: flag
do
case "${flag}" in
g) group=${OPTARG};;
esac
done
downloader() {
nntp-pull $group
}
until downloader; do
echo "restarting download" >&2
sleep 1
done
if [ $? -eq 0 ]; then
mv -v $group $group.mbox && zip -rm $group.mbox.zip $group.mbox
fi
这一次只会下载一个新闻组。我还编写了第二个脚本 archiver.sh,它将读取主新闻组文件并并行运行 downloader.sh。
归档器.sh
#!/bin/bash
cat newsgroup_list_working.txt | parallel -j 10 ./downloader.sh -g {}
然而,它并没有真正起作用。很多时候,它会停止下载任何内容,并且不会开始新的下载。我没有耗尽磁盘或内存,而且我的 CPU 也没有达到 100%。另外,我的磁盘 I/O 没有达到最大,因为我可以毫无问题地运行其他东西。下载速度仅略高于 1MB,因此我认为我的网络没有出现问题。
任何建议将不胜感激!
答案1
您可能想读取每个命令 10 个参数:
cat file | parallel -N10 ./downloader.sh -g {5}
其中 5 是包含新闻组名称的行。
用于--dry-run
让 GNU Parallel 显示它将运行的命令:
cat file | parallel --dry-run -N10 ./downloader.sh -g {5}
当显示正确的命令时,您可以对其进行调整,-j 300%
让每个 CPU 线程并行运行 3 个作业。