lib/Moose/Policy.pm - add documentation
[gitmo/Moose-Policy.git] / lib / Moose / Policy.pm
CommitLineData
82cfc049 1package Moose::Policy;
2
8e7059d6 3# vim:ts=4:sw=4:et:sta
4
82cfc049 5use strict;
6use warnings;
7
b9238462 8our $VERSION = '0.01';
9
10use Moose ();
11use Carp 'confess';
12use Scalar::Util 'blessed';
13
8e7059d6 14=head1 NAME
15
16Moose::Policy - moose-mounted police
17
18=head1 SYNOPSIS
19
20This class allows you to specify your project-wide or company-wide Moose
21meta policy in one location.
22
23 package Foo;
24
25 use Moose::Policy 'My::MooseBestPractice';
26 use Moose;
27
28 has 'bar' => (is => 'rw', default => 'Foo::bar');
29 has 'baz' => (is => 'ro', default => 'Foo::baz');
30
31=head1 USAGE
32
33 use Moose::Policy 'My::Policy';
34 use Moose;
35 ...
36 no Moose;
37
38=over
39
40=item YOU MUST
41
42 use Moose::Policy 'My::Policy';
43
44=item BEFORE
45
46 use Moose;
47
48=back
49
50=head2 The Policy
51
52The argument to C<import()> is a package name. This package is
53require()'d and queried for the following constants:
54
55=over
56
57=item metaclass
58
59Defaults to C<'Moose::Meta::Class'>.
60
61=item attribute_metaclass
62
63=item instance_metaclass
64
65=item method_metaclass
66
67=back
68
69These values are then used to setup your $package->meta object.
70
71Your policy package could be simply a list of constants.
72
73 package My::Policy;
74 use constant attribute_metaclass => 'My::Moose::Meta::Attribute';
75
76But the methods are told what package is using the policy, so they could
77concievably give different answers.
78
79 package My::FancyPolicy;
80
81 sub attribute_metaclass {
82 my $self = shift;
83 my ($user_package) = @_;
84 return('Our::Attributes::Stricter')
85 if $user_package =~ m/^Private::Banking::Money/;
86 return('Our::Attributes');
87 }
88
89=head1 AUTHOR
90
91Stevan Little E<lt>stevan@iinteractive.comE<gt>
92
93In response to a feature request by Eric Wilhelm and suggestions by Matt
94Trout.
95
96Documentation and some code are Eric's fault.
97
98=head1 COPYRIGHT AND LICENSE
99
100...
101
102=head1 SEE ALSO
103
104L<Moose>, L<Moose::Meta::Class>
105
106=cut
107
b9238462 108sub import {
109 shift;
8e7059d6 110
b9238462 111 my $policy = shift || return;
8e7059d6 112
b9238462 113 unless (Moose::_is_class_already_loaded($policy)) {
8e7059d6 114 ($policy->require) or confess "Could not load policy module " .
115 "'$policy' because : $UNIVERSAL::require::ERROR";
b9238462 116 }
8e7059d6 117
118 my $package = caller();
119 $package->can('meta') and
120 croak("'$package' already has a meta() method");
121
b9238462 122 my $metaclass = 'Moose::Meta::Class';
8e7059d6 123 $metaclass = $policy->metaclass($package)
124 if $policy->can('metaclass');
125
b9238462 126 my %options;
8e7059d6 127
bfacd619 128 # build options out of policy's constants
8e7059d6 129 $policy->can($_) and $options{":$_"} = $policy->$_($package)
bfacd619 130 for (qw(
131 attribute_metaclass
132 instance_metaclass
133 method_metaclass
134 ));
8e7059d6 135
b9238462 136 # create a meta object so we can install &meta
137 my $meta = $metaclass->initialize($package => %options);
138 $meta->add_method('meta' => sub {
8e7059d6 139 # we must re-initialize so that it works as expected in
140 # subclasses, since metaclass instances are singletons, this is
141 # not really a big deal anyway.
b9238462 142 $metaclass->initialize((blessed($_[0]) || $_[0]) => %options)
8e7059d6 143 });
b9238462 144}
145
82cfc049 1461;
147
148__END__
149
bfacd619 150