Pipeline pour le téléchargement et le traitement des fichiers Sous Unix / Linux Environnement Avec Perl
Question
J'ai une liste des fichiers URLS où je veux les télécharger:
http://somedomain.com/foo1.gz
http://somedomain.com/foo2.gz
http://somedomain.com/foo3.gz
Ce que je veux faire est la suivante pour chaque fichier:
- Télécharger foo1,2 .. en parallèle avec
wget
etnohup
. - Chaque fois qu'il complète les processus de téléchargement avec
myscript.sh
Ce que j'est le suivant:
#! /usr/bin/perl
@files = glob("foo*.gz");
foreach $file (@files) {
my $downurls = "http://somedomain.com/".$file;
system("nohup wget $file &");
system("./myscript.sh $file >> output.txt");
}
Le problème est que je ne peux pas dire la canalisation au-dessus de quand la finition de téléchargement du fichier. Alors maintenant, il ne myscript.sh pas exécutée correctement.
Quelle est la bonne façon d'y parvenir?
La solution
Essayez de combiner les commandes à l'aide &&
, de sorte que le 2ème ne redémarrera qu'après la 1ère finalise avec succès.
system("(nohup wget $file && ./myscript.sh $file >> output.txt) &");
Autres conseils
Pourquoi faire cela en utilisant Perl. utiliser bash à la place. Ci-dessous est juste un échantillon.
#!/bin/bash
for file in foo1 foo2 foo3
do
wget http://samedomain.com/$file.gz .
if [ -f $file.gz ];
then
./myscript.sh $file.gz >> output.txt
fi
done
Si vous souhaitez que le traitement parallèle, vous pouvez le faire vous-même avec bifurquer, ou utiliser un module intégré pour gérer pour vous. Essayez Parallel :: ForkManager . Vous pouvez voir un peu plus sur son utilisation dans Comment puis-je gérer un pool de fourche en Perl? , mais la page CPAN pour le module aura la vraie information utile. Vous voulez probablement quelque chose comme ceci:
use Parallel::ForkManager;
my $MAX_PROCESSES = 8; # 8 parallel processes max
my $pm = new Parallel::ForkManager($MAX_PROCESSES);
my @files = glob("foo*.gz");
foreach $file (@all_data) {
# Forks and returns the pid for the child:
my $pid = $pm->start and next;
my $downurls = "http://somedomain.com/".$file;
system("wget $file");
system("./myscript.sh $file >> output.txt");
$pm->finish; # Terminates the child process
}
print "All done!\n";