我有一个属性特征,我想根据其他类属性设置。我真的想要一个属性特征的默认值,它获取类$self
的副本而不是属性的元素。我想在班上做这样的事情:
after 'BUILD' => sub {
my $self = shift;
$self->meta->get_attribute('id')->column_name( $self->_unique_key_name );
};
但是,我想保留我的属性特征RO?这可能吗。我知道MOP允许设置类属性的值,但我无法弄清楚如何在元属性上设置属性。
答案 0 :(得分:1)
这听起来像是一个非常奇怪的设计(为什么元类需要它描述的类的实例?) - 但是你可以通过使用元类的元类来轻松地做到这一点(请记住,Moose元类是自引导的使用MOP本身):
$self->meta->meta->get_attribute("foo")->default($some_value);
还要记住,如果默认值是引用本身,则需要将其包装在coderef中:$some_value = sub { $instance };
实际上,这不起作用 - 'default'是只读的。我不是在如此低的水平上摆弄MOP,而是敦促你重新考虑你的设计 - 例如将您的'default'存储在另一个属性中,并编写一个委托给它的默认子:
package MyApp::Meta::Attribute::Trait::Foo;
# set at runtime, when we have an instance to store here
has _default_of_foo => (
is => 'rw', isa => 'Object',
);
has foo => (
is => 'ro', isa => 'Object',
lazy => 1,
default => sub { shift->_default_of_foo },
);