2013-03-20 4 views
1

Im beginner. Я написал скрипт perl, который делает следующее:Perl sftp загружает с Net :: SFTP :: Foreign

-Создайте каталог под «/ x01/abcd/abc_logs/abcd_Logs» на текущую дату в формате «YYYYMMDD», если он еще не был создан. i.e: если сценарий запускается на «01st jan 2013», каталог под названием «20130101» будет создан по указанному пути. Поэтому всякий раз, когда необходимо проверять журналы, всегда ищите каталог по текущей дате.

-Проверьте, были ли файлы журнала уже загружены ранее в тот же день, и если журналы (журналы) не будут загружены в каталог TODAY.

У меня трудное время, придумывая решение для печати сообщения, когда в доле нет файлов. Это, конечно, когда пользователь указывает 2 или более файлов, которых нет в общей папке. Я знаю, что это происходит, потому что в «sub get_LOGS» есть выражение «die». Я просто не могу понять, как вернуть сообщение, когда все файлы, которые я указываю, не находятся в общей папке.

использование этого сценария заключается в следующем

./abc_logs ....

Ниже приведен сценарий.

my $LOGS_LOCAL_PATH = "/x02/abc/abcba2/"; 
chomp $LOGS_LOCAL_PATH; 
my $LOGS_REM_PATH = "/x01/INT/abc/vabc2/"; 
chomp $LOGS_REM_PATH; 
my $TODAY = `date +%Y%m%d`; 
chomp $TODAY; 
my @GETLOOP = @ARGV; 
    unless ($#ARGV >= 0) { 
     print "\nUsage: gtp_logs.pl <file1> <file2> <file3>.....<file(n)>\n\n"; 
     exit; 
    } 
     system("clear"); 
    unless (-d "$LOGS_LOCAL_PATH"."$TODAY") { 
     print "Directory \"$TODAY\" doesn't exist. So creating the directory..!\n"; 
     print "OK..Done.....!\n\n"; 
     system("mkdir $LOGS_LOCAL_PATH/$TODAY"); 
     } 
    else { 
     print "Directory already exists. Logs will be downloaded to ==>  \"$LOGS_LOCAL_PATH$TODAY\".....!\n\n"; 
    } 

       # if_DOWNLOADED($LOGS_LOCAL_PATH,$TODAY,@GETLOOP); 

    chdir("$LOGS_LOCAL_PATH"."$TODAY") || die "cannot cd to ($!)"; 
    foreach my $GETL (@GETLOOP) { 
    my $is_downloaded = if_DOWNLOADED($LOGS_LOCAL_PATH,$TODAY,$GETL); 
    if(!$is_downloaded) 
    { 
     get_LOGS("172.25.70.221","abc","abc2","/x01/INT/abc",$GETL); 
     print "File \"$GETL\" downloaded to ==>   \"$LOGS_LOCAL_PATH$TODAY\"\n\n"; 
    } 
    else 
    { 
     print "File \"$GETL\" has already been Downloaded to ==>   \"$LOGS_LOCAL_PATH$TODAY\"\n\n"; 
    } 


    } 


sub get_LOGS { 
    my $LOG_HOST = shift; 
    my $REM_USER = shift; 
    my $REM_PASSW = shift; 
    my $REM_PATH = shift; 
    my $REM_FILE = shift; 

     print "Connecting to the sftp share! Please wait....!\n"; 
     my $sftp = Net::SFTP::Foreign->new($LOG_HOST, user => $REM_USER, password => $REM_PASSW); 
     $sftp->setcwd($REM_PATH) or die "unable to change cwd: " . $sftp->error; 
     print "OK. On the share! Downloading the file \"$REM_FILE\"...................!\n\n\n\n"; 
     $sftp->error and die "Problem connecting to the share...!!!! " . $sftp->error; 
     $sftp->get($REM_FILE) or die "File does not seem to be present on the remote share. Please re-request..!!!" . $sftp->error; 
     return $REM_FILE; 
} 

sub if_DOWNLOADED { 
    my $DWD_FILE_PATH = shift; 
    my $DWD_DIR  = shift; 
    my $DWD_FILE  = shift; 
    if (-e "$DWD_FILE_PATH/$DWD_DIR/$DWD_FILE") 
    { 
     return 1; 
    } 
    else 
    { 
     return 0; 
    } 
} 

Возможно, кто-нибудь поможет мне найти решение этого вопроса? Попробуйте использовать тот же скрипт и измените его.

/V

+0

Пожалуйста, не используйте ', если ... else' строительство. – Toto

ответ

3

Некоторых комментарии к вашей коде:

  • Используйте строгие и предупреждение для того, чтобы поймать много ошибок в начале.

  • Прочтите некоторую книгу о стиле (т. Е. Лучшие практики Перми Перри). Но в любом случае старайтесь быть последовательными, когда именовать переменные, подпрограммы и все, а также их случай.

  • Если вам нужно использовать определенное значение в нескольких местах, попробуйте рассчитать его один раз и сохранить в переменной.

  • Не используйте подпрограммы для мелочей.

  • Вам не нужно называть chomp на переменные, которые вы определили и которые не имеют символа "\n" в конце.

  • Открытие нового SFTP-соединения для каждой передачи файлов очень неэффективно. Вы можете открыть только один в начале и использовать его для всех передач.

А теперь, упрощенная версия вашего сценария:

#!/usr/bin/perl 

use strict; 
use warnings; 

my $host = "172.25.70.221"; 
my $user = "abc"; 
my $password = "abc1234321"; 

my $LOGS_LOCAL_PATH = "/x02/ABC/abc2"; 
my $LOGS_REM_PATH = "/x01/INT/abc/vim"; 
my $TODAY = `date +%Y%m%d`; 
chomp $TODAY; 
my $TODAY_LOCAL_PATH = "$LOGS_LOCAL_PATH/$TODAY"; 

my @files = @ARGV; 
@files or die "\nUsage: gtp_logs.pl <file1> <file2> <file3>.....<file(n)>\n\n"; 

system("clear"); 

if (-d $TODAY_LOCAL_PATH) { 
    print "Directory already exists. Logs will be downloaded to ==>  \"$TODAY_LOCAL_PATH\".....!\n\n"; 
} 
else { 
    print "Directory \"$TODAY\" doesn't exist. So creating the directory..!\n"; 
    mkdir "$TODAY_LOCAL_PATH" or die "unable to create directory: $!\n"; 
    print "OK..Done.....!\n\n"; 
} 

chdir $TODAY_LOCAL_PATH or die "cannot cd to ($!)\n"; 

my $sftp = Net::SFTP::Foreign->new($host, user => $user, password => $password); 
$sftp->error 
    and die "Problem connecting to the share...!!!! " . $sftp->error; 

my $ok = 0; 
my $failed = 0; 
foreach my $file (@files) { 
    if (-e "$TODAY_LOCAL_PATH/$file") { 
     print "File \"$file\" has already been Downloaded to ==>   \"$TODAY_LOCAL_PATH\"\n"; 
    } 
    else { 
     if ($sftp->get("$LOGS_REM_PATH/$file")) { 
      print "File \"$file\" downloaded to ==>   \"$TODAY_LOCAL_PATH\"\n"; 
      $ok++; 
     } 
     else { 
      print "Unable to download file \"$file\" : " . $sftp->error . "\n"; 
      $failed++; 
     } 
    } 
} 

print "$ok files have been downloaded, $failed files failed!\n\n";  
Смежные вопросы