Perl从SFTP服务器

时间:2015-10-28 15:16:48

标签: perl net-sftp

我使用perl已经有一段时间了,我试图在SFTP服务器上打印出一个文件列表。

这是我的Perl脚本 -

#! /usr/bin/env perl
use strict;
use warnings;
use feature qw(say);
use autodie;

use Net::SFTP::Foreign;

# US Server Configuration
use constant {
    HOST            => "Server_Name",
    REMOTE_DIR      => "\\",
    LOCAL_DIR       => "sample/local",
    PORT            => "3235",
    USER_NAME       => "name",
    PASSWORD        => "password",
    BACKEND         => "Net_SSH2",
    DEBUG           => "0",
};

my $stfp = Net::SFTP::Foreign->new (
    HOST,
    backend         => BACKEND,
    timeout         => 240,
    user            => USER_NAME,
    password        => PASSWORD,
    port            => PORT,
    autodie         => 1,
);

#
# List remote directory contents
#
my $remotefiles;
$remotefiles = $stfp->ls(REMOTE_DIR); 

#
# Loop through remote files and print each filename
#
foreach ($remotefiles){
    my $file = $_;
    my $filename = $file->{filename};
    if($filename ne "." && $filename ne ".."){
        print"the filename is $filename";
    }
}

$stfp->disconnect;

我收到以下错误 - 此行不是HASH参考 - >我的$ filename = $ file-> {filename};

不确定问题是什么或如何解决。

2 个答案:

答案 0 :(得分:3)

对于Net :: SFTP :: Foreign,

Here's the documentation。这就是它对ls()方法的说法:

  

返回对条目列表的引用。每个条目都是   引用具有三个键的哈希:filename,其名称   条目; longname," long"中的一个条目列出像ls -l;和   a,包含文件的Net::SFTP::Foreign::Attributes对象   atime,mtime,权限和大小

所以当你调用这个方法时:

$remotefiles = $stfp->ls(REMOTE_DIR);

你得到的是对数组的引用。当您尝试迭代该数组时:

foreach ($remotefiles)

你没有做你认为自己正在做的事情。您使用单个元素迭代列表 - 这是一个数组引用。因此$file获取数组引用,而不是您正在寻找的哈希引用。

那么如何解决呢?嗯,这很简单。您需要取消引用$remotefiles,它会将其转换为数组(而不是数组引用)。

# Just add a '@' to dereference the reference and
# get to the underlying array
foreach (@$remotefiles)

现在,每次循环时,$_(以及$file)将包含上面引用中描述的哈希引用之一,并且一切都将按预期工作。

这里要学习的重要一课是,您需要阅读并理解您正在使用的代码的文档。或者,至少,您需要更好地复制示例中的代码。 ls()示例明确使用了取消引用语法。

my $ls = $sftp->ls('/home/foo')
    or die "unable to retrieve directory: ".$sftp->error;

print "$_->{filename}\n" for (@$ls);

答案 1 :(得分:-1)

$ filenane是一个数组引用。取消引用变量以获取referant。有关详细信息,请参阅perlreftut。当你掌握它时很容易,但第一次这样做可能会有点痛苦。