从Perl中的全球区域导入模块

问题描述 投票:1回答:1

所以,我试图导入模块到Perl包,我尽量做到尽可能的干净的方式。首先,我看了一些以前的线程(如:link)。

该模块位于以下路径:/p/disk/tools/perl/5.26.1/lib64/site_perl。该模块是Data::TreeDumper

我用FindBin模块,以便将其导入:

BEGIN {
    use Exporter ();
    use vars qw(@ISA @EXPORT_OK  %EXPORT_TAGS);
    use FindBin;
    use lib "$FindBin::RealBin";
    use lib "$FindBin::Bin";
    use lib "$FindBin::Bin/../lib";
    use lib "/p/disk/tools/perl/5.26.1/lib64/site_perl";
    @ISA       = qw(Exporter);
    @EXPORT_OK = qw(# ALL subs
                   );
    %EXPORT_TAGS = (all => [@EXPORT_OK]);
}
use constants qw(:all);
use Data::TreeDumper;

这对我的作品,但路径是硬编码。我想包括路径进入constants包(我的包)。但它种了一圈,因为为了使用常量(和路径),我需要先导入它,但随后,来自哪里?呵呵。

所以我想删除use lib "/p/disk/tools/perl/5.26.1/lib64/site_perl";线并以某种方式导入第一constants文件,然后像做:

use constants qw(:all);
use lib $PATH_TO_THE_MODULE; # represents path to the module area
use Data::TreeDumper;

但它不工作了。是否有可能实现吗?

之前,试图导入模块(不知道它被安装在一个全球性的地方),我在本地安装了它,它的工作。但我不想让非矿模块在同一个目录中的项目。因此,IT人员在全球范围安装的模块,我只是询问是否有可能将其导入一个干净的方式。

编辑:我试图插入路径/p/disk/tools/perl/5.26.1/lib64/site_perl到常量在全局变量文件(姑且称之为$PATH_TO_THE_MODULE)。然后我想,所以我用constants从其他包导入FindBin包。然后我想导入使用指向该模块的面积$PATH_TO_THE_MODULE变量的模块。因此,它应该是这个样子:

use constants qw(:all);
use lib $PATH_TO_THE_MODULE; # represents a path to the module area
use Data::TreeDumper;

但是,这是行不通的。我试图切换到require因为我明白,require将动态地使用。但它也失败,Can't locate Data/TreeDumper.pm in @INC

因此,如果我们两件连接的代码中,我们得到:

package test;
$|=1;
use strict;
use warnings;
BEGIN {
    use Exporter ();
    use vars qw(@ISA @EXPORT_OK  %EXPORT_TAGS);
    use FindBin;
    use lib "$FindBin::RealBin";
    use lib "$FindBin::Bin";
    use lib "$FindBin::Bin/../lib";
    @ISA       = qw(Exporter);
    @EXPORT_OK = qw(# ALL subs
                   );
    %EXPORT_TAGS = (all => [@EXPORT_OK]);
}
use constants qw(:all);
use lib $PATH_TO_THE_MODULE; # represents a path to the module area
use Data::TreeDumper;
print "Hi\n";

常量包:

package constants;
$|=1;
use strict;
use warnings;
BEGIN {
    use Exporter ();
    use vars qw(@ISA @EXPORT_OK  %EXPORT_TAGS);
    use FindBin;
    use lib "$FindBin::RealBin";
    use lib "$FindBin::Bin";
    use lib "$FindBin::Bin/../lib";
    @ISA       = qw(Exporter);
    @EXPORT_OK = qw($PATH_TO_THE_MODULE);
    %EXPORT_TAGS = (all => [@EXPORT_OK]);
}
our $PATH_TO_THE_MODULE = "/p/disk/tools/perl/5.26.1/lib64/site_perl";

如果我从use lib $PATH_TO_THE_MODULE;包装中取出use Data::TreeDumper;test,我会打印$PATH_TO_THE_MODULE,它会编译并如预期打印路径。

perl
1个回答
0
投票

你要求你的代码不能正常工作,这是因为$PATH_TO_THE_MODULE的初始化发生在工作时间。

那么,你的代码做的工作,这是因为没有一个单一的编译阶段和单一的运行阶段。

比方说,你有下面的脚本:

use constants ':all';
use lib $PATH_TO_THE_MODULE;
use Data::TreeDumper qw();
print "Hi\n";

让我们简化模块以下几点:

package constants;
use Exporter qw( import );
our @EXPORT_OK = qw( $PATH_TO_THE_MODULE );
our %EXPORT_TAGS = ( all => \@EXPORT_OK );
our $PATH_TO_THE_MODULE = "/path/to/site_perl";

记住,use Foo;大致相当于BEGIN { use Foo; import Foo; }BEGIN块,尽快为他们被编译执行一致,以下描述了当你执行这个脚本会发生什么:

  1. 编译script.pl 编译use constants ':all'; 执行require constants; 编译constants.pm 编译package constants; 编译use Exporter qw( import ); 执行require Exporter; 编译Exporter.pm [...] 执行Exporter.pm [...] 执行import Exporter qw( import ); 编译our @EXPORT_OK = qw( $PATH_TO_THE_MODULE ); 编译our %EXPORT_TAGS = ( all => \@EXPORT_OK ); 编译our $PATH_TO_THE_MODULE = "/path/to/site_perl"; 执行constants.pm 执行our @EXPORT_OK = qw( $PATH_TO_THE_MODULE ); 执行our %EXPORT_TAGS = ( all => \@EXPORT_OK ); 执行our $PATH_TO_THE_MODULE = "/path/to/site_perl"; 执行import constants; 编译use lib $PATH_TO_THE_MODULE; 执行require lib; 编译lib.pm [...] 执行lib.pm [...] 执行import lib $PATH_TO_MODULE; 编译use Data::TreeDumper qw(); 执行require Data::TreeDumper; 编译Data/TreeDumper.pm [...] 执行Data/TreeDumper.pm [...] 编译print "Hi\n";
  2. 执行script.pl 执行print "Hi\n";

从上面,我们可以看到以下情况发生:

  1. 创建[1.2.1.5] $constants::PATH_TO_THE_MODULE
  2. [1.2.2.3] $constants::PATH_TO_THE_MODULE被设定为路径
  3. [1.3] $main::PATH_TO_THE_MODULE创建为别名$constants::PATH_TO_THE_MODULE
  4. [1.6] $main::PATH_TO_THE_MODULE加到@INC
  5. [1.8]数据:: TreeDumper是加载

讽刺的是,你声称只有以下摘录的工作之一,而另一个没有时,他们基本上是相同的:

use FindBin qw( $RealBin );
use lib $RealBin;

use constants qw( $PATH_TO_THE_MODULE );
use lib $PATH_TO_THE_MODULE;
© www.soinside.com 2019 - 2024. All rights reserved.