MooseX::ConstructInstance - small wrapper method for instantiating helper objects
This role consists of a single method:
sub construct_instance { my (undef, $class, @args) = @_; $class->new(@args); }
(Actually, since 0.006, it's a little more complex.)
Normally you would build an LWP::UserAgent something like this:
sub _build_ua { my $self = shift; LWP::UserAgent->new(...); }
Following the principles of dependency injection, you may prefer not to hard-code the class name (see also MooseX::RelatedClasses):
has ua_class => (is => 'ro', default => 'LWP::UserAgent'); sub _build_ua { my $self = shift; $self->ua_class->new(...); }
This module allows you to take it to a further level of abstraction:
has ua_class => (is => 'ro', default => 'LWP::UserAgent'); sub _build_ua { my $self = shift; $self->construct_instance($self->ua_class, ...); }
Why? What benefit do we accrue from constructing all our helper objects via a seemingly redundant object method call? How about this:
{ package Authentication; use Moose::Role; around construct_instance => sub { my ($orig, $self, $class, @args) = @_; my $instance = $self->$orig($class, @args); if ($instance->DOES('LWP::UserAgent')) { $instance->credentials('', '', 'username', 'password'); } return $instance; }; } Moose::Util::ensure_all_roles($something, 'Authentication');
Now whenever $something constructs an LWP::UserAgent object, it will automatically have authentication credentials supplied.
$something
MooseX::ConstructInstance can be used to apply policies such as:
If $foo has a dbh attribute, and it constructs an object $bar, then $bar should inherit $foo's database handle.
$foo
dbh
$bar
All node objects must be have "backlinks" to the parent node that created them.
Despite the name, MooseX::ConstructInstance is actually a Moo::Role. You can apply MooseX::ConstructInstance to Moose classes using:
package MyClass; use Moose; with qw( MooseX::ConstructInstance );
You can apply it to Moo classes using:
package MyClass; use Moo; with qw( MooseX::ConstructInstance );
You can apply it to other classes using:
package MyClass; use MooseX::ConstructInstance -with;
As of version 0.006 of MooseX::ConstructInstance, $class may be a coderef or a blessed object overloading &{}. The construct_instance method acts a bit like this:
$class
&{}
construct_instance
sub construct_instance { my (undef, $class, @args) = @_; if ( is_codelike($class) ) { return $class->(@args); } else { $class->new(@args); } }
new
Aye; there's the rub.
For now, this works, though it's not an especially elegant solution...
sub _build_document { my $self = shift; local $MooseX::ConstructInstance::CONSTRUCTOR = 'new_from_file'; $self->construct_instance($self->document_class, ...); }
Please report any bugs to http://rt.cpan.org/Dist/Display.html?Queue=MooseX-ConstructInstance.
Moose, MooseX::RelatedClasses.
Toby Inkster <tobyink@cpan.org>.
This software is copyright (c) 2012-2013 by Toby Inkster.
This is free software; you can redistribute it and/or modify it under the same terms as the Perl 5 programming language system itself.
THIS PACKAGE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
To install MooseX::ConstructInstance, copy and paste the appropriate command in to your terminal.
cpanm
cpanm MooseX::ConstructInstance
CPAN shell
perl -MCPAN -e shell install MooseX::ConstructInstance
For more information on module installation, please visit the detailed CPAN module installation guide.