silence the warnings
[gitmo/Moose.git] / lib / Moose.pm
CommitLineData
fcd84ca9 1
2package Moose;
3
4use strict;
5use warnings;
6
bdabd620 7our $VERSION = '0.04';
fcd84ca9 8
cc65ead0 9use Scalar::Util 'blessed', 'reftype';
fcd84ca9 10use Carp 'confess';
bc1e29b5 11use Sub::Name 'subname';
fcd84ca9 12
7f18097c 13use UNIVERSAL::require;
14
ef1d5f4b 15use Class::MOP;
16
c0e30cf5 17use Moose::Meta::Class;
7415b2cb 18use Moose::Meta::TypeConstraint;
7c13858b 19use Moose::Meta::TypeCoercion;
78cd1d3b 20use Moose::Meta::Attribute;
c0e30cf5 21
fcd84ca9 22use Moose::Object;
7415b2cb 23use Moose::Util::TypeConstraints;
a3c7e2fe 24use Sub::Exporter;
a15dff8d 25
a3c7e2fe 26{
27 my ( $CALLER, %METAS );
28
29 sub meta() {
30 my $class = $CALLER;
31
32 return $METAS{$class} if exists $METAS{$class};
33
34 # make a subtype for each Moose class
35 subtype $class
36 => as 'Object'
37 => where { $_->isa($class) }
38 unless find_type_constraint($class);
39
40 my $meta;
41 if ($class->can('meta')) {
42 $meta = $class->meta();
43 (blessed($meta) && $meta->isa('Moose::Meta::Class'))
44 || confess "Whoops, not møøsey enough";
45 }
46 else {
47 $meta = Moose::Meta::Class->initialize($class => (
48 ':attribute_metaclass' => 'Moose::Meta::Attribute'
49 ));
50 $meta->add_method('meta' => sub {
51 # re-initialize so it inherits properly
52 Moose::Meta::Class->initialize($class => (
53 ':attribute_metaclass' => 'Moose::Meta::Attribute'
54 ));
55 })
56 }
57
58 # make sure they inherit from Moose::Object
59 $meta->superclasses('Moose::Object')
60 unless $meta->superclasses();
61
62 return $METAS{$class} = $meta;
63 }
64
65 my %exports = (
66 extends => sub {
67 my $meta = meta();
3d544ed5 68 return subname 'Moose::extends' => sub {
a3c7e2fe 69 _load_all_classes(@_);
70 $meta->superclasses(@_)
71 };
72 },
73 with => sub {
74 my $meta = meta();
3d544ed5 75 return subname 'Moose::with' => sub {
a3c7e2fe 76 my ($role) = @_;
77 _load_all_classes($role);
78 $role->meta->apply($meta);
79 };
80 },
81 has => sub {
82 my $meta = meta();
3d544ed5 83 return subname 'Moose::has' => sub {
a3c7e2fe 84 my ($name, %options) = @_;
85 $meta->add_attribute($name, %options)
86 };
87 },
88 before => sub {
89 my $meta = meta();
3d544ed5 90 return subname 'Moose::before' => sub {
a3c7e2fe 91 my $code = pop @_;
92 $meta->add_before_method_modifier($_, $code) for @_;
93 };
94 },
95 after => sub {
96 my $meta = meta();
3d544ed5 97 return subname 'Moose::after' => sub {
a3c7e2fe 98 my $code = pop @_;
99 $meta->add_after_method_modifier($_, $code) for @_;
100 };
101 },
102 around => sub {
103 my $meta = meta();
3d544ed5 104 return subname 'Moose::around' => sub {
a3c7e2fe 105 my $code = pop @_;
106 $meta->add_around_method_modifier($_, $code) for @_;
107 };
108 },
109 super => sub {
110 my $meta = meta();
3d544ed5 111 return subname 'Moose::super' => sub {};
a3c7e2fe 112 },
113 override => sub {
114 my $meta = meta();
3d544ed5 115 return subname 'Moose::override' => sub {
a3c7e2fe 116 my ($name, $method) = @_;
117 $meta->add_override_method_modifier($name => $method);
118 };
119 },
120 inner => sub {
121 my $meta = meta();
3d544ed5 122 return subname 'Moose::inner' => sub {};
a3c7e2fe 123 },
124 augment => sub {
125 my $meta = meta();
3d544ed5 126 return subname 'Moose::augment' => sub {
a3c7e2fe 127 my ($name, $method) = @_;
128 $meta->add_augment_method_modifier($name => $method);
129 };
130 },
131 confess => sub {
132 return \&Carp::confess;
133 },
134 blessed => sub {
135 return \&Scalar::Util::blessed;
136 }
137 );
3d544ed5 138
a3c7e2fe 139 my $exporter = Sub::Exporter::build_exporter({
140 exports => \%exports,
141 groups => {
142 default => [':all']
143 }
144 });
145
146 sub import {
147 $CALLER = caller();
148
149 # we should never export to main
150 return if $CALLER eq 'main';
151
152 goto $exporter;
153 };
fcd84ca9 154}
155
e9bb8a31 156## Utility functions
157
78cd1d3b 158sub _load_all_classes {
e9bb8a31 159 foreach my $super (@_) {
160 # see if this is already
161 # loaded in the symbol table
162 next if _is_class_already_loaded($super);
163 # otherwise require it ...
164 ($super->require)
165 || confess "Could not load superclass '$super' because : " . $UNIVERSAL::require::ERROR;
166 }
167}
168
d7f17ebb 169sub _is_class_already_loaded {
170 my $name = shift;
171 no strict 'refs';
172 return 1 if defined ${"${name}::VERSION"} || defined @{"${name}::ISA"};
173 foreach (keys %{"${name}::"}) {
174 next if substr($_, -2, 2) eq '::';
175 return 1 if defined &{"${name}::$_"};
176 }
177 return 0;
178}
179
fcd84ca9 1801;
181
182__END__
183
184=pod
185
186=head1 NAME
187
e522431d 188Moose - Moose, it's the new Camel
fcd84ca9 189
190=head1 SYNOPSIS
e522431d 191
192 package Point;
193 use Moose;
194
182134e8 195 has 'x' => (isa => 'Int', is => 'rw');
196 has 'y' => (isa => 'Int', is => 'rw');
e522431d 197
198 sub clear {
199 my $self = shift;
200 $self->x(0);
201 $self->y(0);
202 }
203
204 package Point3D;
205 use Moose;
206
207 extends 'Point';
09fdc1dc 208
182134e8 209 has 'z' => (isa => 'Int');
e522431d 210
211 after 'clear' => sub {
212 my $self = shift;
213 $self->{z} = 0;
214 };
215
216=head1 CAVEAT
217
79592a54 218This is an early release of this module, it still needs
e522431d 219some fine tuning and B<lots> more documentation. I am adopting
220the I<release early and release often> approach with this module,
221so keep an eye on your favorite CPAN mirror!
222
fcd84ca9 223=head1 DESCRIPTION
224
e522431d 225Moose is an extension of the Perl 5 object system.
226
227=head2 Another object system!?!?
fcd84ca9 228
e522431d 229Yes, I know there has been an explosion recently of new ways to
230build object's in Perl 5, most of them based on inside-out objects,
231and other such things. Moose is different because it is not a new
232object system for Perl 5, but instead an extension of the existing
233object system.
3c7278fb 234
e522431d 235Moose is built on top of L<Class::MOP>, which is a metaclass system
236for Perl 5. This means that Moose not only makes building normal
505c6fac 237Perl 5 objects better, but it also provides the power of metaclass
238programming.
e522431d 239
240=head2 What does Moose stand for??
241
242Moose doesn't stand for one thing in particular, however, if you
243want, here are a few of my favorites, feel free to contribute
244more :)
245
246=over 4
247
5569c072 248=item Make Other Object Systems Envious
e522431d 249
250=item Makes Object Orientation So Easy
251
5569c072 252=item Makes Object Orientation Spiffy- Er (sorry ingy)
505c6fac 253
5569c072 254=item Most Other Object Systems Emasculate
505c6fac 255
256=item My Overcraft Overfilled (with) Some Eels
257
258=item Moose Often Ovulate Sorta Early
259
505c6fac 260=item Many Overloaded Object Systems Exists
261
262=item Moose Offers Often Super Extensions
263
446e850f 264=item Meta Object Orientation Syntax Extensions
265
e522431d 266=back
3c7278fb 267
6ba6d68c 268=head1 BUILDING CLASSES WITH MOOSE
269
270Moose makes every attempt to provide as much convience during class
271construction/definition, but still stay out of your way if you want
272it to. Here are some of the features Moose provides:
273
274Unless specified with C<extends>, any class which uses Moose will
275inherit from L<Moose::Object>.
276
277Moose will also manage all attributes (including inherited ones) that
278are defined with C<has>. And assuming that you call C<new> which is
279inherited from L<Moose::Object>, then this includes properly initializing
280all instance slots, setting defaults where approprtiate and performing any
281type constraint checking or coercion.
282
79592a54 283For more details, see the ever expanding L<Moose::Cookbook>.
284
6ba6d68c 285=head1 EXPORTED FUNCTIONS
286
287Moose will export a number of functions into the class's namespace, which
288can then be used to set up the class. These functions all work directly
289on the current class.
290
291=over 4
292
293=item B<meta>
294
295This is a method which provides access to the current class's metaclass.
296
297=item B<extends (@superclasses)>
298
299This function will set the superclass(es) for the current class.
300
301This approach is recommended instead of C<use base>, because C<use base>
302actually C<push>es onto the class's C<@ISA>, whereas C<extends> will
303replace it. This is important to ensure that classes which do not have
304superclasses properly inherit from L<Moose::Object>.
305
e9ec68d6 306=item B<with ($role)>
307
76d37e5a 308This will apply a given C<$role> to the local class. Role support is
309currently very experimental, see L<Moose::Role> for more details.
e9ec68d6 310
6ba6d68c 311=item B<has ($name, %options)>
312
313This will install an attribute of a given C<$name> into the current class.
314The list of C<%options> are the same as those provided by both
315L<Class::MOP::Attribute> and L<Moose::Meta::Attribute>, in addition to a
316few convience ones provided by Moose which are listed below:
317
318=over 4
319
076c81ed 320=item I<is =E<gt> 'rw'|'ro'>
6ba6d68c 321
322The I<is> option accepts either I<rw> (for read/write) or I<ro> (for read
323only). These will create either a read/write accessor or a read-only
324accessor respectively, using the same name as the C<$name> of the attribute.
325
326If you need more control over how your accessors are named, you can use the
327I<reader>, I<writer> and I<accessor> options inherited from L<Moose::Meta::Attribute>.
328
076c81ed 329=item I<isa =E<gt> $type_name>
6ba6d68c 330
331The I<isa> option uses Moose's type constraint facilities to set up runtime
332type checking for this attribute. Moose will perform the checks during class
333construction, and within any accessors. The C<$type_name> argument must be a
334string. The string can be either a class name, or a type defined using
335Moose's type defintion features.
336
337=back
338
076c81ed 339=item B<before $name|@names =E<gt> sub { ... }>
6ba6d68c 340
076c81ed 341=item B<after $name|@names =E<gt> sub { ... }>
6ba6d68c 342
076c81ed 343=item B<around $name|@names =E<gt> sub { ... }>
6ba6d68c 344
345This three items are syntactic sugar for the before, after and around method
346modifier features that L<Class::MOP> provides. More information on these can
347be found in the L<Class::MOP> documentation for now.
348
159da176 349=item B<super>
350
351The keyword C<super> is a noop when called outside of an C<override> method. In
352the context of an C<override> method, it will call the next most appropriate
353superclass method with the same arguments as the original method.
354
355=item B<override ($name, &sub)>
356
357An C<override> method, is a way of explictly saying "I am overriding this
358method from my superclass". You can call C<super> within this method, and
359it will work as expected. The same thing I<can> be accomplished with a normal
360method call and the C<SUPER::> pseudo-package, it is really your choice.
361
362=item B<inner>
363
364The keyword C<inner>, much like C<super>, is a no-op outside of the context of
365an C<augment> method. You can think of C<inner> as being the inverse of
366C<super>, the details of how C<inner> and C<augment> work is best described in
367the L<Moose::Cookbook>.
368
369=item B<augment ($name, &sub)>
370
371An C<augment> method, is a way of explictly saying "I am augmenting this
372method from my superclass". Once again, the details of how C<inner> and
373C<augment> work is best described in the L<Moose::Cookbook>.
374
6ba6d68c 375=item B<confess>
376
377This is the C<Carp::confess> function, and exported here beause I use it
378all the time. This feature may change in the future, so you have been warned.
379
380=item B<blessed>
381
382This is the C<Scalar::Uti::blessed> function, it is exported here beause I
383use it all the time. It is highly recommended that this is used instead of
384C<ref> anywhere you need to test for an object's class name.
385
386=back
387
05d9eaf6 388=head1 CAVEATS
389
390=over 4
391
392=item *
393
394It should be noted that C<super> and C<inner> can B<not> be used in the same
395method. However, they can be combined together with the same class hierarchy,
396see F<t/014_override_augment_inner_super.t> for an example.
397
398The reason that this is so is because C<super> is only valid within a method
399with the C<override> modifier, and C<inner> will never be valid within an
400C<override> method. In fact, C<augment> will skip over any C<override> methods
401when searching for it's appropriate C<inner>.
402
403This might seem like a restriction, but I am of the opinion that keeping these
404two features seperate (but interoperable) actually makes them easy to use since
405their behavior is then easier to predict. Time will tell if I am right or not.
406
407=back
408
5569c072 409=head1 ACKNOWLEDGEMENTS
410
411=over 4
412
54c189df 413=item I blame Sam Vilain for introducing me to the insanity that is meta-models.
5569c072 414
54c189df 415=item I blame Audrey Tang for then encouraging my meta-model habit in #perl6.
5569c072 416
076c81ed 417=item Without Yuval "nothingmuch" Kogman this module would not be possible,
54c189df 418and it certainly wouldn't have this name ;P
5569c072 419
420=item The basis of the TypeContraints module was Rob Kinyon's idea
421originally, I just ran with it.
422
076c81ed 423=item Thanks to mst & chansen and the whole #moose poose for all the
d46a48f3 424ideas/feature-requests/encouragement
425
5569c072 426=back
427
e90c03d0 428=head1 SEE ALSO
429
430=over 4
431
6ba6d68c 432=item L<Class::MOP> documentation
433
434=item The #moose channel on irc.perl.org
435
e90c03d0 436=item L<http://forum2.org/moose/>
437
159da176 438=item L<http://www.cs.utah.edu/plt/publications/oopsla04-gff.pdf>
439
440This paper (suggested by lbr on #moose) was what lead to the implementation
441of the C<super>/C<overrride> and C<inner>/C<augment> features. If you really
442want to understand this feature, I suggest you read this.
443
e90c03d0 444=back
445
fcd84ca9 446=head1 BUGS
447
448All complex software has bugs lurking in it, and this module is no
449exception. If you find a bug please either email me, or add the bug
450to cpan-RT.
451
fcd84ca9 452=head1 AUTHOR
453
454Stevan Little E<lt>stevan@iinteractive.comE<gt>
455
456=head1 COPYRIGHT AND LICENSE
457
458Copyright 2006 by Infinity Interactive, Inc.
459
460L<http://www.iinteractive.com>
461
462This library is free software; you can redistribute it and/or modify
463it under the same terms as Perl itself.
464
465=cut