Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Argument for builder subroutine in a moose object

Tags:

perl

moose

I'm currently delegating the builder method to all of the objects that extend one of my base classes. The problem that I'm facing is I need all of the objects to either read an attribute of itself or be passed in a value.

#  In Role:
has 'const_string' => (
    isa     => 'Str',
    is      => 'ro',
    default => 'test',
);

has 'attr' => (
    isa     => 'Str',
    is      => 'ro',
    builder => '_builder',
);

requires '_builder';


#  In extending object  -  desired 1
sub _builder {
    my ($self) = shift;
    #  $self contains $self->const_string
 }

#  In extending object  -  desired 2
sub _builder {
    my ($arg1, $arg2) = @_;
    #  $args can be passed somehow?
 }

Is this currently possible or am I going to have to do it some other way?

like image 898
lespea Avatar asked Jul 20 '10 14:07

lespea


1 Answers

You can't pass arguments to attribute build methods. They are called automatically by Moose internals, and passed only one argument -- the object reference itself. The builder must be able to return its value based on what it sees in $self, or anything else in the environment that it has access to.

What sort of arguments would you be wanting to pass to the builder? Can you instead pass these values to the object constructor and store them in other attributes?

# in object #2:
has other_attr_a => (
    is => 'ro', isa => 'Str',
);
has other_attr_b => (
    is => 'ro', isa => 'Str',
);

sub _builder
{
    my $self = shift;
    # calculates something based on other_attr_a and other_attr_b
}

# object #2 is constructed as:
my $obj = Class2->new(other_attr_a => 'value', other_attr_b => 'value');

Also note that if you have attributes that are built based off of other attribute values, you should define them as lazy, otherwise the builders/defaults will run immediately on object construction, and in an undefined order. Setting them lazy will delay their definition until they are first needed.

like image 176
Ether Avatar answered Nov 14 '22 21:11

Ether