如果我想分发Perl脚本,那么无痛地安装用户系统中缺少的任何所需模块的最佳方法是什么?如果有一种方法甚至可以安装/升级Perl本身(如果它丢失或“太旧”),则可获得额外的功劳。
答案 0 :(得分:6)
自动安装软件是让最终用户和系统管理员对您非常生气的最佳方式。忘记这种方法。
您可以使用您的应用程序发行版简单地发送所有依赖项,inc
目录是惯例。
答案 1 :(得分:3)
通常,这会以类似CPAN的包创建结束。
因此,当您需要安装所有依赖项时,请键入make installdeps
参见perldoc perlmodlib
此外,Module::Install
可能对您和某些Makefile.PL示例
Makefile.PL
允许您定义deps和所需的perl版本。
您也可以添加
use 5.010;
到您的脚本,以便要求运行最低版本的perl。有关详细信息,请参阅perldoc -f use。
答案 2 :(得分:2)
为什么不使用创建可执行文件的pp(PAR Packager)。不需要Perl或目标机器上的任何东西。
答案 3 :(得分:2)
如果查看cpanminus,只需执行一个文件即可安装:
curl -L http://cpanmin.us | perl - --self-upgrade
这可能是你正在寻找的行为;它是用App :: Fatpacker完成的。看看:
答案 4 :(得分:0)
从here获取的半自动脚本,适用于具有中级bash技能和近乎0级perl技能的人:
#!/usr/bin/env perl
use strict ; use warnings ;
use 5.10.0 ;
use ExtUtils::Installed;
# quick and dirty check for prerequisites perl modules:
# courtesy of:http://stackoverflow.com/a/9340304/65706
# if you have a calling bash script call by :
# perl "/path/to/isg_pub_preq_checker.pl"
# export ret=$?
# test $ret -ne 0 && doExit 1 "[FATAL] perl modules not found!!!"
my $PrintOkCheck = 1 ;
# check that all the required modules are installed
my ( $ret , $msg ) = doCheckRequiredModules();
unless ( $ret == 0 ) {
print "$msg" ;
# give some time for the user to react
print "printing all installed modules :" ;
my $c = 9 ;
for ( my $i=0;$i<=$c;$i++){
print ( ( $c-$i) . '.') ;
sleep 1 ;
}
print "\n" ;
doListAllInstalledModules();
print "\n" ;
}
exit(0);
sub doListAllInstalledModules {
my $instmod = ExtUtils::Installed->new();
foreach my $module ($instmod->modules()) {
my $version = $instmod->version($module) || "???";
print "found module:$module -- v$version\n";
}
}
#eof sub
sub doCheckRequiredModules {
my @modules = qw(
YAML::Any
Test::More
Spreadsheet::XLSX
Test::Deep
File::Copy::Recursive
IO::HTML
Test::More
Filter::Util::Call
Algorithm::Diff
Text::Diff
Test::Base
Test::CPAN::Meta::YAML
Test::YAML::Valid
Test::YAML::Meta
Test::YAML
Data::Printer
ExtUtils::Installed
Sub::StrictDecl
Spreadsheet::WriteExcel
Mojolicious::Plugin::RenderFile
JSON
Carp::Always
Mojolicious::Plugin::PDFRenderer
Redis::Client
);
for(@modules) {
eval "use $_";
if ($@) {
#flush the screen
print "\033[2J";
print "\033[0;0H";
my $msg = "\n\n\n [FATAL] did not found the following prerequisite perl module: $_ \n\n" ;
$msg .= "\n # == START copy paste == " ;
$msg .= "\n#you must install it otherwise the application will not work" ;
$msg .= "\n#the module could be installef by running the following commands:" ;
# if the user knows already the difference between the running the cmd
# with sudo or he / she probably knows already how-to install perl modules
$msg .= "\n# as a start configure the cpan to install dependancies first \n" ;
$msg .= "\n" . 'perl -MCPAN -e \'my $c = "CPAN::HandleConfig"; $c->load(doit => 1, autoconfig => 1); $c->edit(prerequisites_policy => "follow"); $c->edit(build_requires_install_policy => "yes"); $c->commit\'' . "\n" ;
$msg .= "\n#than install the $_ module by running: \n" ;
$msg .= "\nsudo perl -MCPAN -e 'install $_'\n\n\n" ;
$msg .= "\n # == STOP copy paste == \n\n\n" ;
$msg .= "\n # == START copy paste == " ;
$msg .= "\n# if you seem to be stuck in circular reference kind of loop try even :\n" ;
$msg .= "\nsudo perl -MCPAN -e 'CPAN::Shell->force(qw( install $_));'\n" ;
$msg .= "\n # == STOP copy paste == " ;
$msg .= "\n# You may end-up now with Ctrl + C \n\n\n" ;
return ( 1, "$msg") if $@;
} else {
say "[INFO ] == ok == check for prerequisite perl module : $_" if $PrintOkCheck == 1 ;
}
}
#eof foreach module
return ( 0 , "all required modules found" ) ;
}
#eof sub
# ??!!
#perl -MCPAN -e 'install Module::Signature'
# the following modules have been or might be part of the installable modules
#PDF::WebKit
#HTML::TreeBuilder
#HTML::TreeBuilder::XPath
#HTML::TableExtract
#HTML::ElementTable