Perl::SFTP::Foreign的ls()方法统计文件数量异常问题排查
Perl::SFTP::Foreign 文件统计与重命名问题排查与解决
你遇到的问题确实和wanted参数的正则表达式写法有关,对比你之前用的Net::FTP代码,两者的匹配逻辑差异是关键原因,咱们一步步拆解解决:
问题根源
Net::FTP的ls($file."*")用的是shell风格通配符,意思是匹配「以$file开头」的所有文件;但你当前Perl::SFTP::Foreign里的qr/$file.*/是Perl正则,它的意思是「匹配任何包含$file字符串的内容」,而且如果$file里有正则特殊字符(比如filename.zip里的.),会被当成元字符匹配任意字符,这就导致匹配范围完全不符合你的预期,自然统计不到正确的文件数量。
解决方案
要实现和Net::FTP中$file."*"相同的匹配逻辑,你需要调整正则表达式:
- 用
^锚定字符串开头,确保文件名从$file开始; - 用
\Q和\E包裹$file,转义其中所有正则特殊字符(比如.、*等),避免它们被错误解析。
修正后的正则应该是:qr/^\Q$file\E/
修正后的完整代码
my $file = "filename.zip"; my $reName = ".bak"; # 匹配以$file开头的文件,自动转义特殊字符 my @rls = $sftp->ls('.', wanted => qr/^\Q$file\E/ ); my $rls_size = @rls; my $fileReName = $file . $reName; if ( $rls_size > 1 ) { $fileReName .= $rls_size; } unless ( $sftp->rename($file, $fileReName) ) { print "Error Renaming $file to $fileReName. $@ $!\n"; }
额外调试技巧
如果还是不确定匹配结果,可以打印出所有匹配到的文件名,直观验证:
foreach my $entry (@rls) { print "Matched file: " . $entry->{filename} . "\n"; }
Perl::SFTP::Foreign的ls返回的是哈希数组,每个元素的filename键对应实际文件名,这样就能清楚看到哪些文件被统计进来了。
补充说明
你原来的代码还有个小语法错误:my $file = "filename.zip" $reName = ".bak";这里少了分号,修正后加上了my声明所有变量,提升代码可读性和规范性。
内容的提问来源于stack exchange,提问作者Allin Brown
相关产品推荐
相关产品推荐

