我正在尝试建立一个用Perl编写的大型项目.在IBM MakeMaker的教程非常有帮助,到目前为止,但我不明白如何将所有模块链接到主程序.在我的项目的根,我有MANIFEST
,Makefile.PL
,README
,一个bin
目录和lib
目录.在我的bin
目录中,我有我的主脚本(Main.pl
).在lib
目录中,我有我的每一个模块,分成它们各自的目录(即Utils::Util1
和Utils::Utils2
在utils
目录等).在每个模块目录中,还有一个t
包含测试的目录
我的MANIFEST
文件包含以下内容:
bin/Main.pl
lib/Utils/Util1.pm
lib/Utils/Util2.pm
lib/Utils/t/Utils1.t
lib/Utils/t/Utils2.t
Makefile.PL
MANIFEST
README
Run Code Online (Sandbox Code Playgroud)
Makefile.PL
如下:
use ExtUtils::MakeMaker;
WriteMakefile(
'NAME'=>'Foo',
'VERSION_FROM'=>'bin/Main.pl',
'PREREQ_PM'=>{
"XML::Simple"=> 2.18}, #The libraries that we need and their
#minimum version numbers
'EXE_FILES' =>[("bin/Main.pl")]
);
Run Code Online (Sandbox Code Playgroud)
在我制作和运行之后,程序崩溃,抱怨它找不到Utils::Util1
,当我跑'时make test
,它说no tests defined
.有人可以提出任何建议吗?我从未在perl中完成过这样的大型项目,我需要添加更多模块
给定一个使用C库的Perl XS模块,假设有一个正确设置的Makefile.PL,以便所有头和库位置,编译器和链接器标志等都能正常工作.
现在,假设我想要包含一个小型C程序,该程序包含使用相同底层C库的XS模块.什么是正确的,独立于平台的方式来指定目标可执行文件,以便使用相同的设置和标志构建它?
如果我做以下事情
sub MY::postamble {
return <<FRAG;
target$Config{exe_ext}: target$Config{obj_ext}
target$Config{obj_ext}: target.c
FRAG
}
Run Code Online (Sandbox Code Playgroud)
我没有得到我在参数中设置的那些包含位置,库列表等WriteMakefile
.如果我开始手工编写规则,我必须考虑至少make
,dmake
和nmake
.如果使用ExtUtils :: CBuilder,我无法想出指定要链接的库的直接方法.
我肯定错过了什么.如果你能指出的话,我将不胜感激.
我最近开始使用perlxstut学习XS ,教程建议我使用旧的h2xs工具创建我的模块来创建一个基于ExtUtils :: MakeMaker的项目.但是对于纯Perl项目,h2xs/EUMM长期以来一直不赞成使用Module :: Install,Module :: Build或Dist :: Zilla.
是否有更现代的方式来创建XS项目?能模块::启动创建XS项目?Module :: Build或Dist :: Zilla可以构建XS项目吗?他们的pod页面对此事保持沉默.
另一方面,针对h2xs/EUMM的批评是否适用于XS项目?如果你还需要一个C编译器,那么要求make工具是否合理?
编辑:我看到这个问题回答了我关于创建项目的问题.我仍然想知道构建:EUMM是唯一的选择,还是Module :: Build和Dist :: Zilla也能够构建XS?
我有一个64位的CentOS 6系统,它运行一个定制版本的Perl 5.12.5,它是为32位构建的.(唉,这是因为我们对32位和64位系统使用相同的RPM.)
当我在服务器上构建XS模块(例如JSON :: XS)时,它会失败,因为它正在构建64位库.我得到一个错误
Can't load '.cpanm/work/1370279501.28897/JSON-XS-2.33/blib/arch
/auto/JSON/XS/XS.so' for module JSON::XS: .cpanm/work/137027950
1.28897/JSON-XS-2.33/blib/arch/auto/JSON/XS/XS.so: wrong ELF class: ELFCLASS64
at /opt/perl/lib/5.12.5/i686-linux/DynaLoader.pm line 200.
Run Code Online (Sandbox Code Playgroud)
我已经尝试将CFLAGS变量设置为"-m32-bit"但它不起作用.
如何正确编译XS模块需要做什么?理想情况下,我喜欢与cpanminus一起使用的东西,但如果需要可以使用cpan或cpanplus.
构建Perl模块时,ExtUtils :: MakeMaker使用Config.pm中定义的标志(参见perldoc Config)获取ccflags和ldflags等值.
如何覆盖这些值(缺少编辑Makefile.PL)?
perl Makefile.PL ldflags=<options>
Run Code Online (Sandbox Code Playgroud)
似乎不起作用.
上下文:我试图在OS X 10.6上编译Term :: Readline :: Gnu.默认的OS X perl是一个通用的二进制文件,因此有像-arch i386 -arch ppc等的ccflags.
另一方面,我的Gnu Readline(6.0)版本仅从-arch i386的源代码编译而来.因此,它不包含试图使用-arch ppc链接到它的模块的预期符号.
我正在开发可以在 Win32 和 *nix 上运行的 CPAN 发行版。然而,为了让它在 Win32 上工作,它需要另一个只能安装在 Win32 上的 CPAN 分发(模块)。
问题在于,通过将该模块声明为依赖项,它无法安装在 *nix 机器上。但它不会在 *nix 机器上真正使用/需要,只有在 Win32 上运行时。
我的发行版ExtUtils::MakeMaker
在自动生成的 hash 中使用和配置依赖项%WriteMakefileArgs
。
我尝试Makefile.PL
根据运行它的操作系统进行编辑以添加或删除依赖项。然而,这并没有真正用于产生工作META.json
和META.yml
,这是基于操作系统,我最终执行上产生的make dist
。如果我在 Windows 上运行它,那么仅 Win32 的依赖项会添加到这些文件中并破坏 *nix 安装。如果我在 *nix 上运行它,则不会添加依赖项,并且当测试分发的时间到来时,它可能会破坏 Win32 上的安装。
有没有办法为特定的操作系统定义不同的依赖关系,使应用程序在安装发行版时喜欢CPAN
或CPANminus
可以在每个操作系统上成功运行?
PREREQ_PM
指定运行时先决条件,但是如何指定运行测试用例所需的模块?
我应该用BUILD_REQUIRES
它吗?
有没有办法让ExtUtils :: MakeMaker生成自定义Makefile目标?说,我想做一些只有开发人员感兴趣的特定事情,比如运行pod和回归测试; 我可以使用env变量,但记住这样的事情有点笨拙.能够运行这样的东西make devtest
会非常方便.
我正在研究名为Mite的Perl模块.它是一种"编译器",各种各样.您使用类似Moose的声明性OO语法编写Perl类.Mite不是在每次执行时都将所有工作放在一起,而是在构建时完成这项工作.它会生成一个额外的文件,其中包含用于访问器和继承的Perl代码以及诸如此类的东西.
这个额外的文件将lib
与您的其余代码一起使用,并随您的项目一起发布.因此,安装用户无需安装Mite,代码加载速度更快.
在开发过程中,当螨运行编译器make
或Build
运行.所以像make test
和./Build test
公正的工作.这是通过为MakeMaker或Module :: Build使用特殊填充程序来实现的.
这适用于Module :: Build,但是ExtUtils :: MakeMaker没有看到mite文件.MakeMaker硬编码运行lib
时的列表Makefile.PL
.该pm_to_lib
步则无法复制生成的文件到blib
哪里make test
都会看到他们.
我怎样才能最好地解决这个问题?我希望该过程对开发人员保持透明(一旦他们加载了适当的垫片),并且不需要安装用户的特殊依赖关系.
更新:这是一个更清晰的例子.假设您有一个这样的项目.
Makefile.PL
lib/
Foo.pm
Bar.pm
Foo/
Thing.pm
t/
foo.t
bar.t
Run Code Online (Sandbox Code Playgroud)
你跑perl Makefile.PL
,然后make
.make
已修改该步骤.mite.pm
以为每个.pm
文件生成额外文件.在这make
一步之后,我想要的就是这个.
Makefile.PL
Makefile
lib/
Foo.pm
Foo.pm.mite.pm
Bar.pm
Bar.pm.mite.pm
Foo/
Thing.pm
Thing.pm.mite.pm
blib/
lib/
Foo.pm
Foo.pm.mite.pm
Bar.pm …
Run Code Online (Sandbox Code Playgroud) 寻找有关如何将多个PM文件添加到MakeMaker脚本的一些见解?
我看到这个文档和所有示例看起来像添加了一个文件,如何添加多个文件?
use ExtUtils::MakeMaker;
WriteMakefile(
NAME => 'Your::Module',
VERSION_FROM => 'lib/Your/Module.pm'
);
Run Code Online (Sandbox Code Playgroud)
我只是添加另一组值吗?
use ExtUtils::MakeMaker;
WriteMakefile(
NAME => 'Your::Module',
VERSION_FROM => 'lib/Your/Module.pm'
NAME => 'Your::Module2',
VERSION_FROM => 'lib/Your/Module2.pm'
);
Run Code Online (Sandbox Code Playgroud) 假设我已经创建了一个目录module-starter
,并编写了几个额外的模块和测试.
make test
然后将在所有模块中运行所有测试,但是只会将提到的文件打包到tar.gz中.t/
lib/
make dist
MANIFEST
所以我最近因跑步make test && make dist
而被烧伤,但仍然得到了破损的包裹.
我的问题是:我错过了什么,或者这可以被报告为MakeMaker中的一个小错误?(Makefile.PL似乎依赖于此).