ハッシュテーブルはPerlオブジェクトの典型的な初期化子です。これで、指定されたキーが定義された値になるかどうか、またはキーがまったく存在するかどうかがわからないという点で、入力が信頼できません。今度は、そのような信頼できない入力をMooseオブジェクトに供給したいのですが、欠けているキーは完全に大丈夫ですが、未定義の値を取り除きたいので、未定義の属性でいっぱいのオブジェクトにならないようにします。Mooseコンストラクタがundef引数を無視するようにします。
オブジェクトをインスタンス化して未定義の値をフィルタリングする際には、十分注意する必要があります。しかし、それが1つの場所にあるので、コンストラクタにそのフィルタをインストールしたいとしましょう。コンストラクタに未定義の値を無視させ、それらに遭遇すると死ぬことは望ましくありません。
アクセサメソッドの場合は、around
を使用して、属性をundef
に設定しないようにすることができます。しかし、method modifiersはコンストラクタのために呼び出されるのではなく、アクセサのためだけに呼び出されます。 c'torと同じ効果を得るために、つまりundef
属性が受け入れられないようにするために、Mooseにも同様の機能がありますか?
属性がundefの場合、Moose Any
タイプはオブジェクトにハッシュキーを作成することに注意してください。 %$self
にはundef
の値が含まれないようにしたいので、私は望んでいません。
ここで私がやったいくつかのテストです:
package Gurke;
use Moose;
use Data::Dumper;
has color => is => 'rw', isa => 'Str', default => 'green';
has length => is => 'rw', isa => 'Num';
has appeal => is => 'rw', isa => 'Any';
around color => sub {
# print STDERR Dumper \@_;
my $orig = shift;
my $self = shift;
return $self->$orig unless @_;
return unless defined $_[0];
return $self->$orig(@_);
};
package main;
use Test::More;
use Test::Exception;
my $gu = Gurke->new;
isa_ok $gu, 'Gurke';
diag explain $gu;
ok ! exists $gu->{length}, 'attribute not passed, so not set';
diag q(attempt to set color to undef - we don't want it to succeed);
ok ! defined $gu->color(undef), 'returns undef';
is $gu->color, 'green', 'value unchanged';
diag q(passing undef in the constructor will make it die);
dies_ok { Gurke->new(color => undef) }
'around does not work for the constructor!';
lives_ok { $gu = Gurke->new(appeal => undef) } 'anything goes';
diag explain $gu;
diag q(... but creates the undef hash key, which is not what I want);
done_testing;
[Moose :: Cookbook](http://search.cpan.org/perldoc/Moose::Cookbook)をお読みください。特に[Moose :: Cookbook :: Basics :: Recipe10](http://search.cpan.org/perldoc/Moose::Cookbook::Basics::Recipe10)。 –