2016-09-18 10 views
-1

У меня есть скрипт Perl, и я знаю, что он делает жесткие ссылки файлов, я хочу вместо этого создать символические ссылки, может ли кто-то из Perl-подкованных помочь мне в изменении моего сценария? Я только PHP, поэтому я могу читать логику цикла и т. Д., Но не знаю, как Perl взаимодействует с файловой системой.Symlink вместо hardlink в Perl

Я предполагаю, что он находится в начальной петли @ линии 62: foreach my $file(@to_add) {...

#!/usr/bin/perl 

use strict; 
use warnings; 
use JSON qw(decode_json); 
use Data::Dumper; 

my $hashkey   = 'myKey'; 
my $data_folder  = '/jail/glftpd/site'; 
my $player_folder = '/var/mediaplayers'; 
my $mediaplayersurl = "myRoute"; 

sub filesInFolder { 
    my ($path) = @_; 
    my @files =(); 

    if(opendir SCANDIR, $path) { 
     push @files, grep !/^\./ && -f "$path/$_", readdir SCANDIR; 

     closedir SCANDIR; 
    } 

    return @files; 
} 

my $json = `wget --no-check-certificate --header "keyFile: $hashkey" -q -O - $mediaplayersurl`; 
die "Failed to retrieve $mediaplayersurl!", unless defined $json; 

my $data = decode_json($json); 

# print Dumper $data; 

foreach my $player(@$data) { 
    my $sync_folder = $player_folder."/".$player->{companyName}."/".$player->{mediaPlayer}; 
    my $source_folder = $data_folder."/".$player->{companyName}; 

    print "Preparing ".$player->{companyName}."/".$player->{mediaPlayer}."\n"; 

    unless(-d $source_folder) { 
     print STDOUT "Source folder '$source_folder' does not exist, doing nothing.\n"; 

     next; 
    } 

    unless(-d $sync_folder) { 
     system("mkdir", "-p", $sync_folder); 
    } 

    my @existing = filesInFolder($sync_folder); 
    my %existing = map {$_, => 1} @existing; 

    my @videos =(); 
    foreach(@{$player->{'videos'}}) { 
     push @videos, $_; 
    } 

    my %videos = map {$_, => 1} @videos; 

    my @to_add = grep {not $existing{$_}} @videos; 
    my @to_del = grep {not $videos{$_}} @existing; 

    foreach my $file(@to_add) { 
     my $source_file = $source_folder."/".$file; 
     my $target_file = $sync_folder."/".$file; 

     unless(-e $source_file) { 
      print STDERR "Failed to create link to '$source_file', file does not exist.\n"; 

      next; 
     } 

     if(system('ln', $source_file, $target_file) != 0) { 
      print STDERR "Failed to create link from '$target_file' to '$source_file'.\n"; 
     } 
     else { 
      print "Linked '$target_file' to '$source_file'.\n"; 
     } 
    } 

    foreach my $file(@to_del) { 
     my $target_file = $sync_folder."/".$file; 

     if(system('rm', $target_file) != 0) { 
      print STDERR "Failed to remove file link '$target_file'.\n"; 
     } 
     else { 
      print "Removed link '$target_file'.\n"; 
     } 
    } 
} 
+2

Ну, так как вы используете '' system' и ln' создавать ссылки, она должна быть столь же просто, как добавление аргумент '-s'. – Biffen

+0

Просто примечание: нет необходимости выкладывать файлы для 'mkdir' и' rm'. Для этого существуют функции Perl. Посмотрите на ['unlink'] (http://perldoc.perl.org/functions/unlink.html) и [' File :: Path :: make_path'] (http://perldoc.perl.org/File /Path.html). Они дают лучший контроль над условиями ошибок. – PerlDuck

ответ

2

Вам не нужно раскошеливаться. Perl имеет встроенный модуль для создания symlink. Вы можете заменить все это:

if(system('ln', $source_file, $target_file) != 0) { 
    print STDERR "Failed to create link from '$target_file' to '$source_file'.\n"; 
} 
else { 
    print "Linked '$target_file' to '$source_file'.\n"; 
} 

С:

my $link_created = symlink $src_file, $link_name or die $!; 

print "symlink created ok\n" if $link_created; 
+0

Ницца. Но вы можете опустить часть 'if $ link_created;', потому что ваш фрагмент уже умирает при ошибке. – PerlDuck

+0

@PerlDog да, я знаю об этом, это просто для иллюстративных целей. Спасибо хоть! – stevieb