Since it's Sunday, I had a couple extra hours to spare in the evening, so I decided to play around some more with Moose
.
More specifically I've seen MooseX::Declare
mentioned on several occasions so why not give it a go myself.
This module provides a fancier declarative syntax you can use to define objects much more in the tradition of other so-called 'real' OOP languages. It also automatically includes MooseX::Method::Signatures
, which means I can also use method declarations with type constraints to my heart's delight.
Also within the method declarations you get the good old $self
as a freebie, meaning you don't always have to remember to use the my $self = shift
statement. This makes the whole method declaration syntax cleaner and more elegant.
So having said all that here follows my simple example in which I'm able to try out some of the interesting deals on offer.
use MooseX::Declare; use feature qw(say); class Person { has 'age' => ( isa => 'Num', is => 'rw', default => 0 ); has 'max_age' => ( isa => 'Num', is => 'rw', default => 75 ); method get_older (Int $years_to_add = 1 where { $_ > 0 }) { $self->age( $self->age + $years_to_add ) if $self->is_alive; } method is_alive { return $self->age < $self->max_age; } method speak { say $self->is_alive ? "I'm alive!" : "I've kicked the bucket!"; } }
So let's see how good I've coded this, create a Moosified Person
object and see if it all works.
my $x = Person->new( max_age => 35 ); while ($x->is_alive) { $x->get_older( 5 ); $x->speak; }
When I ran the program, it results in the following not so amazing output:
I'm alive! I'm alive! I'm alive! I'm alive! I'm alive! I'm alive! I've kicked the bucket!
I guess it works good, pretty darn good, will have to investigate this interesting functionality in more detail another day.
MooseX::Method::Signatures is syntactically very nice, but there are a few problems. One is the error messages... which can be hard to decipher. More importantly, start-up time takes a massive hit. It loads a huge amount of modules (including PPI). That's also going to be a large memory footprint, which can be an issue (e.g. under mod_perl).
Also, the way it works can cause conflicts with other modules. I haven't quite tracked it down, but I've seen very odd compile-time errors produced when using it with Module::Pluggable.
In short, I think it's a cool idea, and show what's possible. But I wouldn't recommend it for production code. There's just too much dark magic going on, which is just not worth the pain in the long run. Just like you wouldn't use source filters in production.
You're right, the whole error handling that Moose uses can be quite cumbersome to wade through and figure out what's happening.
For example, at first I'd accidentally used parentheses instead of brackets from within the where statement of the method declaration, getting showered beneath lines and lines of cryptic error messages and warnings.
As for using this in production code, I was under the impression that this has been used long enough successfully that one could consider it pretty much proven technology, but I could be wrong.
thanks for such cool example for Moose