On Tue, Jun 14, 2011 at 3:37 PM, Jesse Luehrs <d...@tozt.net> wrote: > On Tue, Jun 14, 2011 at 11:03:33AM +0200, Ævar Arnfjörð Bjarmason wrote: >> On Tue, Jun 14, 2011 at 01:56, Jesse Luehrs <d...@tozt.net> wrote: >> > On Mon, Jun 13, 2011 at 06:45:10PM +0200, Ævar Arnfjörð Bjarmason wrote: >> >> On Mon, Jun 13, 2011 at 18:39, Ævar Arnfjörð Bjarmason <ava...@gmail.com> >> >> wrote: >> >> > For Mouse this monkeypatching would work: >> >> >> >> And this would work for Moose: >> >> >> >> package Foo; >> >> use Moose; >> >> { >> >> package Moose::Meta::Attribute; >> >> >> >> sub verify_against_type_constraint { >> >> my $self = shift; >> >> my $val = shift; >> >> >> >> return 1 if !$self->has_type_constraint; >> >> >> >> my $type_constraint = $self->type_constraint; >> >> >> >> $type_constraint->check($val) >> >> || Carp::cluck("Attribute (" >> >> . $self->name >> >> . ") does not pass the type constraint because: " >> >> . $type_constraint->get_message($val), data => $val, >> >> @_); >> >> } >> >> } >> >> >> >> has x => (is => "ro", isa => "Int"); >> >> my $foo = Foo->new(x => "blah"); >> >> use Data::Dumper; >> >> print Dumper $foo; >> >> >> >> And give you: >> >> >> >> $ perl -Ilib /tmp/error.pl >> >> Subroutine RegexpRef redefined at >> >> lib/Moose/Util/TypeConstraints/OptimizedConstraints.pm line 35. >> >> Subroutine verify_against_type_constraint redefined at /tmp/error.pl >> >> line 6. >> >> Attribute (x) does not pass the type constraint because: >> >> Validation failed for 'Int' with value >> >> blahdatablahinstanceFoo=HASH(0x1edadb0) at /tmp/error.pl line 14 >> >> >> >> Moose::Meta::Attribute::verify_against_type_constraint('Moose::Meta::Attribute=HASH(0x27e0078)', >> >> 'blah', 'instance', 'Foo=HASH(0x1edadb0)') called at >> >> lib/Moose/Meta/Attribute.pm line 1125 >> >> >> >> Moose::Meta::Attribute::_coerce_and_verify('Moose::Meta::Attribute=HASH(0x27e0078)', >> >> 'blah', 'Foo=HASH(0x1edadb0)') called at lib/Moose/Meta/Attribute.pm >> >> line 485 >> >> >> >> Moose::Meta::Attribute::initialize_instance_slot('Moose::Meta::Attribute=HASH(0x27e0078)', >> >> 'Moose::Meta::Instance=HASH(0x27ad5c0)', 'Foo=HASH(0x1edadb0)', >> >> 'HASH(0x1ec8f90)') called at lib/Class/MOP/Class.pm line 575 >> >> >> >> Class::MOP::Class::_construct_instance('Moose::Meta::Class=HASH(0x266bab0)', >> >> 'HASH(0x1ec8f90)') called at lib/Class/MOP/Class.pm line 548 >> >> >> >> Class::MOP::Class::new_object('Moose::Meta::Class=HASH(0x266bab0)', >> >> 'HASH(0x1ec8f90)') called at lib/Moose/Meta/Class.pm line 252 >> >> >> >> Moose::Meta::Class::new_object('Moose::Meta::Class=HASH(0x266bab0)', >> >> 'HASH(0x1ec8f90)') called at lib/Moose/Object.pm line 22 >> >> Moose::Object::new('Foo', 'x', 'blah') called at >> >> /tmp/error.pl line 23 >> >> $VAR1 = bless( { >> >> 'x' => 'blah' >> >> }, 'Foo' ); >> >> >> > >> > For the record, please please PLEASE don't do this. Attribute traits >> > exist for a reason. >> >> How would you accomplish the same thing with attribute traits? > > package My::Attr::Trait; > use Moose::Role; > > around verify_against_type_constraint => sub { > my $orig = shift; > my $self = shift; > my ($val) = @_; > > return 1 if !$self->has_type_constraint; > > my $type_constraint = $self->type_constraint; > > $type_constraint->check($val) > || Carp::cluck("Attribute (" > . $self->name > . ") does not pass the type constraint because: " > . $type_constraint->get_message($val), data => $val, @_); > }; > > package Foo; > use Moose; > > has x => ( > traits => ['My::Attr::Trait'], > is => 'ro', > isa => 'Int', > ); > > my $foo = Foo->new(x => "blah"); > use Data::Dumper; > print Dumper $foo;
Jesse gave me permission to expand on this code and make it a CPAN module. I finally got around to releasing it today: https://metacpan.org/module/MooseX::Attribute::TypeConstraint::CustomizeFatal I also pushed a rfc/mention-mx-attr-tc-customizefatal branch to the Moose Git repository with a small change to the FAQ to mention that yes, this is in fact possible, along with a blatant advert for my new module. I hereby request review of that patch: $ git show -U2 --word-diff commit 81325e8 (HEAD, origin/rfc/mention-mx-attr-tc-customizefatal, master) Author: Ævar Arnfjörð Bjarmason <ava...@gmail.com> Date: Wed May 2 21:42:49 2012 +0000 Moose FAQ: Expand "Can I turn off type constraint checking?" Expand the "Can I turn off type constraint checking?" beyond just "no" to "you can do it with a MooseX extension". The shiny new extension happens to be mine, but also point out that if it doesn't do what you want it's easy to override the default behavior. diff --git a/lib/Moose/Manual/FAQ.pod b/lib/Moose/Manual/FAQ.pod index e4294d8..5a8cda0 100644 --- a/lib/Moose/Manual/FAQ.pod +++ b/lib/Moose/Manual/FAQ.pod @@ -267,5 +267,11 @@ C<NaturalLessThanTen> constraint check. =head3 Can I turn off type constraint checking? [-Not-]{+There's no support for it in the core of Moose+} yet. This option may come in a future release. {+Meanwhile there's a L<MooseX+} {+extension|MooseX::Attribute::TypeConstraint::CustomizeFatal> that+} {+allows you to do this on a per-attribute basis, and if it doesn't do+} {+what you it's easy to write one that fits your use case.+} =head3 My coercions stopped working with recent Moose, why did you break it?