有什麼方法可以事先報告Perl文件中使用的缺失模塊,而不是將其作爲錯誤報告。檢查並報告缺少Perl模塊
我在我的Perl程序中有類似use Digest::MD5
,use File::DosGlob
模塊。每當用戶運行腳本時,如果他們的系統中沒有安裝特定的模塊,他們就會收到錯誤信息。他們無法理解@INC
給出的默認錯誤消息。所以我想清楚地告訴他們需要安裝這些模塊來運行腳本。
有什麼方法可以事先報告Perl文件中使用的缺失模塊,而不是將其作爲錯誤報告。檢查並報告缺少Perl模塊
我在我的Perl程序中有類似use Digest::MD5
,use File::DosGlob
模塊。每當用戶運行腳本時,如果他們的系統中沒有安裝特定的模塊,他們就會收到錯誤信息。他們無法理解@INC
給出的默認錯誤消息。所以我想清楚地告訴他們需要安裝這些模塊來運行腳本。
您可以使用a BEGIN
block構建自己的驗證。這些是在編譯時運行的,就像use
一樣。請記住,use Foo
基本上沒有別的,因爲這:
BEGIN {
require Foo;
Foo->import;
}
下面的代碼將取代所有use
語句與單個BEGIN
並將它們放置一個eval
內。這基本上就像一個try/catch機制。
我們需要串eval
(這被認爲是邪惡在這裏),因爲require
只用冒號::
爲路徑包名稱轉換,如果參數爲a bareword。但是因爲我們的名稱是$module
,它是一個字符串,所以我們需要根據require
's docs將它放入eval
。
如果該字符串eval
失敗,我們die
。這被外部eval
區塊所捕獲,並設置了[email protected]
。然後我們可以檢查它是否包含我們的模塊名稱,在這種情況下,我們天真地認爲失敗是因爲該模塊未安裝。這項檢查可能會更詳細。
我們跟蹤$fails
中的任何故障,如果有任何故障,我們將停止。
#!/usr/bin/perl
use strict;
use warnings;
# all our use statements go here
BEGIN {
my $fails;
foreach my $module (qw/Digest::MD5 File::DosGlob ASDF/) {
eval {
eval "require $module" or die; # because $module is not a bareword
$module->import;
};
if ([email protected] && [email protected] =~ /$module/) {
warn "You need to install the $module module";
$fails++;
}
}
exit if $fails;
}
# ...
上面我包括ASDF
,而我沒有,所以在運行時,它會說
您需要在/home/code/scratch.pl線1335安裝ASDF模塊。
您可能希望使該消息更加冗長。如果您的用戶無法理解Perl在找不到模塊時提供的默認錯誤消息,那麼可以明智地包含關於如何在此處安裝東西的指南。
請注意,您列出的兩個模塊已包含在Perl中,用於a while(閱讀:自2002年3月起)。那麼,爲什麼你要爲這些模塊做到這一點?
$ corelist Digest::MD5
Data for 2014-09-14
Digest::MD5 was first released with perl v5.7.3
$ corelist File::DosGlob
Data for 2014-09-14
File::DosGlob was first released with perl 5.00405
一個更好的辦法是運輸您的程序作爲可安裝一個分佈,包括一個Makefile或類似cpanfile或東西,列出了相關。 perlnewmod中有關於如何啓動新模塊的指南。你不想顯然上傳到CPAN,但基本是一樣的。
這樣,你的用戶就可以自動安裝所有的依賴關係。
你的問題並不清楚「預先」的含義。要檢查Perl程序的語法是正確的,直接計入模塊解析,使用
perl -c <perl-program.pl>
這將檢查文件的語法,並確保您的代碼D任何模塊use
存在。但是,它不會過渡檢查整個依賴關係樹,只有在perl-program.pl
中提到的依賴關係樹。
如果你的意思是你的代碼使用模塊'use'd,那麼是的,它是的。它不能做的是檢查在運行時使用'require'加載的模塊。 – mbethke
如果'test1.pl'在同一個目錄下使用'test2.pm',並且'test2.pm'有一個糟糕的'use'語句,它將只被一個expicit'perl -c test2.pm'捕獲,而不是' perl -c test1.pl' –
適用於perl 5.24,我非常確定它一直如此。 '$ echo'使用X;「 > x.pl; echo「package X; use Y;」 > X.pm; perl -c x.pl'導致'Can not locate Y.pm in @ INC' – mbethke
您可以使用Devel::Modlist,它會列出您的程序所需的所有模塊。
perl -d:Modlist test.pl
還有一個模塊Module::ScanDeps它帶有一個工具scandeps.pl
,你可以在你的腳本中使用如:
scandeps.pl test.pl
注意sanity checking your Perl code using perl -c
is dangerous,所以小心使用。
感謝提及_perlnewmod_。我一直想知道CPAN如何獲得人口。 – PerlDuck
除了那個doc @PerlDuck還有很多。有各種工具可以啓動新的發行版,還有一些指南。也許這是在CPAN上發佈一些東西的好時機。開始建立一個暫停帳戶。 :) – simbabque
我真的不熟悉生成文件或cpanfile,開始工作的單個文件謝謝你,但如果我想檢查文件夾中的所有perl文件如何可以做 – VSr