Moose:类型库 (MooseX::Types)

Moose: type libraries (MooseX::Types)

我正在尝试找出将 Moose 合并到我的项目中的正确方法。 Here 我发现一篇文章建议将 Moose 类型组织在类型​​库中,这似乎是个好主意。所以我根据提供的示例编写了以下代码:

文件 1:MyTypeLib.pm

package MyTypeLib;
use MooseX::Types -declare => [ qw( MyStatus ) ];
use MooseX::Types::Moose qw/Int/;

subtype MyStatus,
      as Int,
      where { $_ >= 0 && $_ < 10 },
      message { "Wrong status: $_" };

1;

文件 2:MyTest.pm

package MyTest;
use MyTypeLib qw( MyStatus );
use Moose;

has status => ( is => 'rw', isa => 'MyStatus' );

no Moose; 1;

文件 3:MyMain.pl

use strict;
use warnings;
use MyTest;

my $t1 = MyTest->new('status' => 5);

当我 运行 它时,我收到此消息:

Attribute (status) does not pass the type constraint because: Validation failed for 'MyStatus' with value 5 (not isa MyStatus) at C:\Strawberry\perl\vendor\lib\Moose\Object.pm line 24

当我在 MyTest.pm 中保留子类型定义并且不使用 MooseX::Types 时,一切都按预期工作。但重点是将子类型移动到一个单独的包中,并在其他包中使用它们。 有人可以建议如何让它工作,或指出(或 post)一些工作示例,或建议实现目标的替代方法。

谢谢!

这似乎有效

MyTypeLib.pm

package MyTypeLib;
use Moose::Util::TypeConstraints;

subtype MyStatus =>
      as 'Num' =>
      where { $_ >= 0 && $_ < 10 },
      message { "Wrong status: $_" };

#coerce MyStatus => from Int => via { $_ };
1;

MyTest.pm

package MyTest;
use MyTypeLib;
use Moose;

has status => ( is  => 'rw', 
                isa => 'MyStatus', 
                #coerce => 1 i
);

no Moose; 1;

MyMain.pl

use strict;
use warnings;
use MyTest;
use Data::Dumper;

my $t1 = MyTest->new( status => 5);
print Dumper $t1;
my $t2 = MyTest->new( status => 10);

这给出了

$ perl MyMain.pl
$VAR1 = bless( {
                 'status' => 5
               }, 'MyTest' );
Attribute (status) does not pass the type constraint because: Wrong
status: 10 at /System/Library/Perl/Extras/5.18/darwin-thread-multi-
2level/Moose/Exception.pm line 37

关于 Moose 这方面的信息不多,但看起来 Moose::Util::TypeConstraints 是折叠到 Moose 中的 MooseX 模块。


编辑 移除强制!

你还需要一个明确的强制转换。-

删除引号:isa => MyStatus,而不是 isa => 'MyStatus'MyStatus 是一个从您的类型库中 exported 的类常量函数。为 isa ("stringy types") 提供字符串而不是适当的类型约束会导致在 Moose 的类型注册表中查找它,或者,如果在那里找不到,它会被解释为 class,类型推断为"any object of that class or its subclasses"。与使用实际类型相比,字符串类型更不明确且更不灵活,并且更容易发生冲突,因为它们都共享一个全局名称空间。最好不要同时使用它们和键入 lbraries。