2012-04-04 57 views
0

根據here提供的答案,我試圖驗證是否安裝了perl模塊。 對於這一點,我有:測試腳本內部是否存在perl mod

# &getYN and &prompt are only included here for completeness 
sub getYN { 
    unless ($autoyes =~ /[Yy]/) { 
     my ($prompt, $default) = @_; 
     my $defaultValue = $default ? "[$default]" : ""; 
     print "$prompt $defaultValue: "; 
     chomp(my $input = <STDIN>); 
     return $input ? $input : $default; 
    } else { 
     return "Y"; 
    } 
} 

sub prompt { 
    my ($prompt, $default) = @_; 
    my $defaultValue = $default ? "[$default]" : ""; 
    print "$prompt $defaultValue: "; 
    chomp(my $input = <STDIN>); 
    return $input ? $input : $default; 
} 

&chklib("RRDTool::OO"); 
sub chklib { 
    my $lib = shift; 
    eval { require $lib; }; 
    if ([email protected]) { 
     print "You are missing a required Perl Module: $lib\n"; 
     my $ok = &getYN("Shall I attempt to install it for you?", "y"); 
     if ($ok =~ /[Yy]/) { 
      require CPAN; 
      CPAN::install($lib); 
     } else { 
      print "Installation requires $lib\n"; 
      exit; 
     } 
    } 
} 

這運行正常,但由於某些原因,EVAL回報,我沒有的RRDTool :: OO安裝的時候,其實我做的。

如果我創建一個空文件並運行:

# File foo.pl 
use strict; 

$| = 1; 

use RRDTool::OO; 

然後我沒有得到任何錯誤。

但是,當我與打印$ @運行的第一個文件,則它返回:

Can't locate RRDTool::OO in ... 

我在做什麼錯?

回答

2

您必須檢查EVAL的結果,就像

if (eval("require xxx;")) { 
    print "you have it\n"; 
} else { 
    print "you don't\n"; 
} 
+1

你可以查看關於「require」的文檔,看看爲什麼報價在這種情況下很有幫助:http://perldoc.perl.org/functions/require.html – oalders 2012-04-04 17:22:12

+1

完美,謝謝! – 2012-04-04 17:24:58

+0

@oalders是的,我已經考慮過將xxx寫成「正確的東西」(甚至不問自己會是什麼):我只是指着我要檢查eval是否成功的方式。 – ShinTakezou 2012-04-04 17:29:09

2

正在發生的事情是,

$lib = "RRDTool::OO"; 
eval { require $lib } 

與字符串化表達

require "RRDTool::OO" 

不是裸字執行風格

require RRDTool::OO 

因此它正在@INC路徑中尋找名爲RRDTool::OO的文件,而不是名爲RRDTool/OO.pm的文件。

如果你想在運行時用變量表達式使用require,你想要麼使用eval

eval "require $lib" 

的帶形或ARG自己處理,以require

$lib = "RRDTool::OO"; 
$lib =~ s{::}{/}g; 
eval { require "$lib.pm" }