How to NOT trigger a trigger when building an object
I have this code:
package Foo;
use Moo;
has attr => ( is => "rw", trigger => 1 );
sub _trigger_attr
{ print "trigger! value:". shift->attr ."\n" }
package main;
use Foo;
my $foo = Foo->new( attr => 1 );
$foo->attr( 2 );
It returns:
$ perl test.pl
trigger! value:1
trigger! value:2
This is the standard documented trigger behavior in Moo.
How to disable trigger execution if the attribute is set through the constructor?
Of course, I can do it like this:
package Foo;
use Moo;
has attr => ( is => "rw", trigger => 1 );
has useTriggers => ( is => "rw", default => 0 );
sub _trigger_attr
{
my $self = shift;
print "trigger! value:". $self->attr ."\n" if $self->useTriggers
}
package main;
use Foo;
my $foo = Foo->new( attr => 1 );
$foo->useTriggers( 1 );
$foo->attr( 2 );
And we get:
$ perl testt.pl
trigger! value:2
So it works, but ... it feels wrong;).
I know little about Moo, but in Mooseyou can implement your own code after the constructor. If you can do something similar in Moo, this will give you the desired effect.
sub BUILD {
my $self = shift;
# Sets "useTriggers" AFTER the object is already constructed.
$self->useTriggers(1);
};
This will lead to the fact that it useTriggerswill be installed immediately after construction, so the trigger will be active after the object is created, but not before it is created.
, :
my $foo->new(attr => 1);
$foo->attr(2);
.