bump version to 0.63
[gitmo/Moose.git] / lib / Moose / Meta / Class.pm
CommitLineData
c0e30cf5 1
2package Moose::Meta::Class;
3
4use strict;
5use warnings;
6
0addec44 7use Class::MOP;
648e79ae 8
11c86f15 9use Carp ();
f8b6827f 10use List::Util qw( first );
8b1d510f 11use List::MoreUtils qw( any all uniq );
21f1e231 12use Scalar::Util 'weaken', 'blessed';
a15dff8d 13
df8260e9 14our $VERSION = '0.63';
e606ae5f 15$VERSION = eval $VERSION;
d44714be 16our $AUTHORITY = 'cpan:STEVAN';
bc1e29b5 17
8ee73eeb 18use Moose::Meta::Method::Overriden;
3f9e4b0a 19use Moose::Meta::Method::Augmented;
bf6fa6b3 20use Moose::Error::Default;
8ee73eeb 21
c0e30cf5 22use base 'Class::MOP::Class';
23
598340d5 24__PACKAGE__->meta->add_attribute('roles' => (
ef333f17 25 reader => 'roles',
26 default => sub { [] }
27));
28
e606ae5f 29__PACKAGE__->meta->add_attribute('constructor_class' => (
30 accessor => 'constructor_class',
e0001338 31 default => 'Moose::Meta::Method::Constructor',
e606ae5f 32));
33
34__PACKAGE__->meta->add_attribute('destructor_class' => (
35 accessor => 'destructor_class',
e0001338 36 default => 'Moose::Meta::Method::Destructor',
e606ae5f 37));
38
11c86f15 39__PACKAGE__->meta->add_attribute('error_class' => (
bf6fa6b3 40 accessor => 'error_class',
41 default => 'Moose::Error::Default',
11c86f15 42));
43
44
590868a3 45sub initialize {
46 my $class = shift;
47 my $pkg = shift;
685f7e44 48 return Class::MOP::get_metaclass_by_name($pkg)
49 || $class->SUPER::initialize($pkg,
50 'attribute_metaclass' => 'Moose::Meta::Attribute',
51 'method_metaclass' => 'Moose::Meta::Method',
52 'instance_metaclass' => 'Moose::Meta::Instance',
53 @_
54 );
ac2dc464 55}
590868a3 56
61bdd94f 57sub create {
58 my ($self, $package_name, %options) = @_;
59
60 (ref $options{roles} eq 'ARRAY')
11c86f15 61 || $self->throw_error("You must pass an ARRAY ref of roles", data => $options{roles})
61bdd94f 62 if exists $options{roles};
310ba883 63 my $roles = delete $options{roles};
dd37a5be 64
61bdd94f 65 my $class = $self->SUPER::create($package_name, %options);
dd37a5be 66
310ba883 67 if ($roles) {
68 Moose::Util::apply_all_roles( $class, @$roles );
61bdd94f 69 }
70
71 return $class;
72}
73
2b72f3b4 74sub check_metaclass_compatibility {
75 my $self = shift;
76
77 if ( my @supers = $self->superclasses ) {
78 $self->_fix_metaclass_incompatibility(@supers);
79 }
80
81 $self->SUPER::check_metaclass_compatibility(@_);
82}
83
17594769 84my %ANON_CLASSES;
85
86sub create_anon_class {
87 my ($self, %options) = @_;
88
89 my $cache_ok = delete $options{cache};
17594769 90
91 # something like Super::Class|Super::Class::2=Role|Role::1
92 my $cache_key = join '=' => (
6d5cbd2b 93 join('|', sort @{$options{superclasses} || []}),
94 join('|', sort @{$options{roles} || []}),
17594769 95 );
96
6d5cbd2b 97 if ($cache_ok && defined $ANON_CLASSES{$cache_key}) {
17594769 98 return $ANON_CLASSES{$cache_key};
99 }
100
101 my $new_class = $self->SUPER::create_anon_class(%options);
102
6d5cbd2b 103 $ANON_CLASSES{$cache_key} = $new_class
104 if $cache_ok;
17594769 105
106 return $new_class;
107}
108
ef333f17 109sub add_role {
110 my ($self, $role) = @_;
111 (blessed($role) && $role->isa('Moose::Meta::Role'))
11c86f15 112 || $self->throw_error("Roles must be instances of Moose::Meta::Role", data => $role);
ef333f17 113 push @{$self->roles} => $role;
114}
115
b8aeb4dc 116sub calculate_all_roles {
117 my $self = shift;
118 my %seen;
119 grep { !$seen{$_->name}++ } map { $_->calculate_all_roles } @{ $self->roles };
120}
121
ef333f17 122sub does_role {
123 my ($self, $role_name) = @_;
124 (defined $role_name)
11c86f15 125 || $self->throw_error("You must supply a role name to look for");
9c429218 126 foreach my $class ($self->class_precedence_list) {
81c3738f 127 next unless $class->can('meta') && $class->meta->can('roles');
9c429218 128 foreach my $role (@{$class->meta->roles}) {
129 return 1 if $role->does_role($role_name);
130 }
ef333f17 131 }
132 return 0;
133}
134
d79e62fd 135sub excludes_role {
136 my ($self, $role_name) = @_;
137 (defined $role_name)
11c86f15 138 || $self->throw_error("You must supply a role name to look for");
ac2dc464 139 foreach my $class ($self->class_precedence_list) {
140 next unless $class->can('meta');
5cb193ed 141 # NOTE:
142 # in the pretty rare instance when a Moose metaclass
ac2dc464 143 # is itself extended with a role, this check needs to
5cb193ed 144 # be done since some items in the class_precedence_list
ac2dc464 145 # might in fact be Class::MOP based still.
146 next unless $class->meta->can('roles');
9c429218 147 foreach my $role (@{$class->meta->roles}) {
148 return 1 if $role->excludes_role($role_name);
149 }
d79e62fd 150 }
151 return 0;
152}
153
8c9d74e7 154sub new_object {
1308deb4 155 my $class = shift;
e606ae5f 156 my $params = @_ == 1 ? $_[0] : {@_};
1308deb4 157 my $self = $class->SUPER::new_object($params);
158
159 foreach my $attr ( $class->compute_all_applicable_attributes() ) {
160
161 next unless $attr->can('has_trigger') && $attr->has_trigger;
162
163 my $init_arg = $attr->init_arg;
164
165 next unless defined $init_arg;
166
167 next unless exists $params->{$init_arg};
168
169 $attr->trigger->(
170 $self,
171 (
172 $attr->should_coerce
173 ? $attr->get_read_method_ref->($self)
174 : $params->{$init_arg}
175 ),
176 $attr
177 );
8c9d74e7 178 }
1308deb4 179
ac2dc464 180 return $self;
8c9d74e7 181}
182
a15dff8d 183sub construct_instance {
e606ae5f 184 my $class = shift;
185 my $params = @_ == 1 ? $_[0] : {@_};
ddd0ec20 186 my $meta_instance = $class->get_meta_instance;
575db57d 187 # FIXME:
188 # the code below is almost certainly incorrect
189 # but this is foreign inheritence, so we might
ac2dc464 190 # have to kludge it in the end.
e606ae5f 191 my $instance = $params->{'__INSTANCE__'} || $meta_instance->create_instance();
ac2dc464 192 foreach my $attr ($class->compute_all_applicable_attributes()) {
e606ae5f 193 $attr->initialize_instance_slot($meta_instance, $instance, $params);
a15dff8d 194 }
195 return $instance;
196}
197
093b12c2 198### ---------------------------------------------
199
a2eec5e7 200sub add_attribute {
201 my $self = shift;
e472c9a5 202 $self->SUPER::add_attribute(
203 (blessed $_[0] && $_[0]->isa('Class::MOP::Attribute')
204 ? $_[0]
205 : $self->_process_attribute(@_))
206 );
a2eec5e7 207}
208
78cd1d3b 209sub add_override_method_modifier {
210 my ($self, $name, $method, $_super_package) = @_;
18c2ec0e 211
d05cd563 212 (!$self->has_method($name))
11c86f15 213 || $self->throw_error("Cannot add an override method if a local method is already present");
18c2ec0e 214
215 $self->add_method($name => Moose::Meta::Method::Overriden->new(
3f9e4b0a 216 method => $method,
217 class => $self,
218 package => $_super_package, # need this for roles
219 name => $name,
18c2ec0e 220 ));
78cd1d3b 221}
222
223sub add_augment_method_modifier {
ac2dc464 224 my ($self, $name, $method) = @_;
d05cd563 225 (!$self->has_method($name))
11c86f15 226 || $self->throw_error("Cannot add an augment method if a local method is already present");
3f9e4b0a 227
228 $self->add_method($name => Moose::Meta::Method::Augmented->new(
229 method => $method,
230 class => $self,
231 name => $name,
232 ));
78cd1d3b 233}
234
1341f10c 235## Private Utility methods ...
236
05d9eaf6 237sub _find_next_method_by_name_which_is_not_overridden {
238 my ($self, $name) = @_;
68efb014 239 foreach my $method ($self->find_all_methods_by_name($name)) {
ac2dc464 240 return $method->{code}
05d9eaf6 241 if blessed($method->{code}) && !$method->{code}->isa('Moose::Meta::Method::Overriden');
242 }
243 return undef;
244}
245
41419b9e 246sub _fix_metaclass_incompatibility {
1341f10c 247 my ($self, @superclasses) = @_;
e606ae5f 248
1341f10c 249 foreach my $super (@superclasses) {
f8b6827f 250 next if $self->_superclass_meta_is_compatible($super);
e606ae5f 251
252 unless ( $self->is_pristine ) {
f8b6827f 253 $self->throw_error(
254 "Cannot attempt to reinitialize metaclass for "
255 . $self->name
256 . ", it isn't pristine" );
1341f10c 257 }
e606ae5f 258
0635500e 259 $self->_reconcile_with_superclass_meta($super);
f8b6827f 260 }
f8b6827f 261}
262
263sub _superclass_meta_is_compatible {
264 my ($self, $super) = @_;
265
266 my $super_meta = Class::MOP::Class->initialize($super)
267 or return 1;
268
269 next unless $super_meta->isa("Class::MOP::Class");
270
271 my $super_meta_name
272 = $super_meta->is_immutable
273 ? $super_meta->get_mutable_metaclass_name
274 : ref($super_meta);
275
276 return 1
277 if $self->isa($super_meta_name)
278 and
279 $self->instance_metaclass->isa( $super_meta->instance_metaclass );
280}
281
282# I don't want to have to type this >1 time
283my @MetaClassTypes =
8b1d510f 284 qw( attribute_metaclass method_metaclass instance_metaclass
285 constructor_class destructor_class error_class );
f8b6827f 286
287sub _reconcile_with_superclass_meta {
288 my ($self, $super) = @_;
289
290 my $super_meta = $super->meta;
291
dd37a5be 292 my $super_meta_name
f8b6827f 293 = $super_meta->is_immutable
294 ? $super_meta->get_mutable_metaclass_name
295 : ref($super_meta);
e606ae5f 296
f8b6827f 297 my $self_metaclass = ref $self;
298
299 # If neither of these is true we have a more serious
300 # incompatibility that we just cannot fix (yet?).
dd37a5be 301 if ( $super_meta_name->isa( ref $self )
f8b6827f 302 && all { $super_meta->$_->isa( $self->$_ ) } @MetaClassTypes ) {
0635500e 303 $self->_reinitialize_with($super_meta);
f8b6827f 304 }
305 elsif ( $self->_all_metaclasses_differ_by_roles_only($super_meta) ) {
0635500e 306 $self->_reconcile_role_differences($super_meta);
1341f10c 307 }
1341f10c 308}
309
f8b6827f 310sub _reinitialize_with {
311 my ( $self, $new_meta ) = @_;
312
0635500e 313 my $new_self = $new_meta->reinitialize(
f8b6827f 314 $self->name,
315 attribute_metaclass => $new_meta->attribute_metaclass,
316 method_metaclass => $new_meta->method_metaclass,
317 instance_metaclass => $new_meta->instance_metaclass,
318 );
319
8b1d510f 320 $new_self->$_( $new_meta->$_ )
321 for qw( constructor_class destructor_class error_class );
f8b6827f 322
0635500e 323 %$self = %$new_self;
324
325 bless $self, ref $new_self;
326
4c5fcc12 327 # We need to replace the cached metaclass instance or else when it
328 # goes out of scope Class::MOP::Class destroy's the namespace for
329 # the metaclass's class, causing much havoc.
0635500e 330 Class::MOP::store_metaclass_by_name( $self->name, $self );
4c5fcc12 331 Class::MOP::weaken_metaclass( $self->name ) if $self->is_anon_class;
f8b6827f 332}
333
334# In the more complex case, we share a common ancestor with our
335# superclass's metaclass, but each metaclass (ours and the parent's)
336# has a different set of roles applied. We reconcile this by first
337# reinitializing into the parent class, and _then_ applying our own
338# roles.
339sub _all_metaclasses_differ_by_roles_only {
340 my ($self, $super_meta) = @_;
341
342 for my $pair (
343 [ ref $self, ref $super_meta ],
344 map { [ $self->$_, $super_meta->$_ ] } @MetaClassTypes
345 ) {
346
347 next if $pair->[0] eq $pair->[1];
348
349 my $self_meta_meta = Class::MOP::Class->initialize( $pair->[0] );
350 my $super_meta_meta = Class::MOP::Class->initialize( $pair->[1] );
351
352 my $common_ancestor
353 = _find_common_ancestor( $self_meta_meta, $super_meta_meta );
354
355 return unless $common_ancestor;
356
357 return
358 unless _is_role_only_subclass_of(
359 $self_meta_meta,
360 $common_ancestor,
361 )
362 && _is_role_only_subclass_of(
363 $super_meta_meta,
364 $common_ancestor,
365 );
366 }
367
368 return 1;
369}
370
371# This, and some other functions, could be called as methods, but
372# they're not for two reasons. One, we just end up ignoring the first
373# argument, because we can't call these directly on one of the real
374# arguments, because one of them could be a Class::MOP::Class object
375# and not a Moose::Meta::Class. Second, only a completely insane
376# person would attempt to subclass this stuff!
377sub _find_common_ancestor {
378 my ($meta1, $meta2) = @_;
379
380 # FIXME? This doesn't account for multiple inheritance (not sure
381 # if it needs to though). For example, is somewhere in $meta1's
382 # history it inherits from both ClassA and ClassB, and $meta
383 # inherits from ClassB & ClassA, does it matter? And what crazy
384 # fool would do that anyway?
385
386 my %meta1_parents = map { $_ => 1 } $meta1->linearized_isa;
387
388 return first { $meta1_parents{$_} } $meta2->linearized_isa;
389}
390
391sub _is_role_only_subclass_of {
392 my ($meta, $ancestor) = @_;
393
394 return 1 if $meta->name eq $ancestor;
395
396 my @roles = _all_roles_until( $meta, $ancestor );
397
398 my %role_packages = map { $_->name => 1 } @roles;
399
400 my $ancestor_meta = Class::MOP::Class->initialize($ancestor);
401
402 my %shared_ancestors = map { $_ => 1 } $ancestor_meta->linearized_isa;
403
404 for my $method ( $meta->get_all_methods() ) {
405 next if $method->name eq 'meta';
406 next if $method->can('associated_attribute');
407
408 next
409 if $role_packages{ $method->original_package_name }
410 || $shared_ancestors{ $method->original_package_name };
411
412 return 0;
413 }
414
415 # FIXME - this really isn't right. Just because an attribute is
416 # defined in a role doesn't mean it isn't _also_ defined in the
417 # subclass.
418 for my $attr ( $meta->get_all_attributes ) {
419 next if $shared_ancestors{ $attr->associated_class->name };
420
421 next if any { $_->has_attribute( $attr->name ) } @roles;
422
423 return 0;
424 }
425
426 return 1;
427}
428
429sub _all_roles {
430 my $meta = shift;
431
432 return _all_roles_until($meta);
433}
434
435sub _all_roles_until {
436 my ($meta, $stop_at_class) = @_;
437
438 return unless $meta->can('calculate_all_roles');
439
440 my @roles = $meta->calculate_all_roles;
441
442 for my $class ( $meta->linearized_isa ) {
443 last if $stop_at_class && $stop_at_class eq $class;
444
445 my $meta = Class::MOP::Class->initialize($class);
446 last unless $meta->can('calculate_all_roles');
447
448 push @roles, $meta->calculate_all_roles;
449 }
450
8b1d510f 451 return uniq @roles;
f8b6827f 452}
453
454sub _reconcile_role_differences {
455 my ($self, $super_meta) = @_;
456
457 my $self_meta = $self->meta;
458
459 my %roles;
460
461 if ( my @roles = map { $_->name } _all_roles($self_meta) ) {
462 $roles{metaclass_roles} = \@roles;
463 }
464
465 for my $thing (@MetaClassTypes) {
466 my $name = $self->$thing();
467
468 my $thing_meta = Class::MOP::Class->initialize($name);
469
470 my @roles = map { $_->name } _all_roles($thing_meta)
471 or next;
472
473 $roles{ $thing . '_roles' } = \@roles;
474 }
475
2b72f3b4 476 $self->_reinitialize_with($super_meta);
f8b6827f 477
478 Moose::Util::MetaRole::apply_metaclass_roles(
479 for_class => $self->name,
480 %roles,
481 );
482
483 return $self;
484}
485
d7d8a8c7 486# NOTE:
d9bb6c63 487# this was crap anyway, see
488# Moose::Util::apply_all_roles
d7d8a8c7 489# instead
4498537c 490sub _apply_all_roles {
547dda77 491 Carp::croak 'DEPRECATED: use Moose::Util::apply_all_roles($meta, @roles) instead'
4498537c 492}
1341f10c 493
494sub _process_attribute {
a3738e5b 495 my ( $self, $name, @args ) = @_;
7e59b803 496
497 @args = %{$args[0]} if scalar @args == 1 && ref($args[0]) eq 'HASH';
d9bb6c63 498
f9b5f5f8 499 if (($name || '') =~ /^\+(.*)/) {
7e59b803 500 return $self->_process_inherited_attribute($1, @args);
1341f10c 501 }
502 else {
7e59b803 503 return $self->_process_new_attribute($name, @args);
504 }
505}
506
507sub _process_new_attribute {
508 my ( $self, $name, @args ) = @_;
7e59b803 509
d5c30e52 510 $self->attribute_metaclass->interpolate_class_and_new($name, @args);
1341f10c 511}
512
513sub _process_inherited_attribute {
514 my ($self, $attr_name, %options) = @_;
515 my $inherited_attr = $self->find_attribute_by_name($attr_name);
516 (defined $inherited_attr)
11c86f15 517 || $self->throw_error("Could not find an attribute by the name of '$attr_name' to inherit from", data => $attr_name);
1341f10c 518 if ($inherited_attr->isa('Moose::Meta::Attribute')) {
d7d8a8c7 519 return $inherited_attr->clone_and_inherit_options(%options);
1341f10c 520 }
521 else {
522 # NOTE:
523 # kind of a kludge to handle Class::MOP::Attributes
d7d8a8c7 524 return $inherited_attr->Moose::Meta::Attribute::clone_and_inherit_options(%options);
ac2dc464 525 }
1341f10c 526}
527
5cf3dbcf 528## -------------------------------------------------
529
530use Moose::Meta::Method::Constructor;
1f779926 531use Moose::Meta::Method::Destructor;
5cf3dbcf 532
ac2dc464 533# This could be done by using SUPER and altering ->options
534# I am keeping it this way to make it more explicit.
535sub create_immutable_transformer {
536 my $self = shift;
537 my $class = Class::MOP::Immutable->new($self, {
e606ae5f 538 read_only => [qw/superclasses/],
539 cannot_call => [qw/
540 add_method
541 alias_method
542 remove_method
543 add_attribute
544 remove_attribute
545 remove_package_symbol
546 add_role
547 /],
548 memoize => {
549 class_precedence_list => 'ARRAY',
550 linearized_isa => 'ARRAY', # FIXME perl 5.10 memoizes this on its own, no need?
551 get_all_methods => 'ARRAY',
552 #get_all_attributes => 'ARRAY', # it's an alias, no need, but maybe in the future
553 compute_all_applicable_attributes => 'ARRAY',
554 get_meta_instance => 'SCALAR',
555 get_method_map => 'SCALAR',
556 calculate_all_roles => 'ARRAY',
557 },
558 # NOTE:
559 # this is ugly, but so are typeglobs,
560 # so whattayahgonnadoboutit
561 # - SL
562 wrapped => {
563 add_package_symbol => sub {
564 my $original = shift;
565 $self->throw_error("Cannot add package symbols to an immutable metaclass")
566 unless (caller(2))[3] eq 'Class::MOP::Package::get_package_symbol';
567 goto $original->body;
568 },
569 },
ac2dc464 570 });
571 return $class;
572}
573
574sub make_immutable {
575 my $self = shift;
576 $self->SUPER::make_immutable
577 (
e606ae5f 578 constructor_class => $self->constructor_class,
579 destructor_class => $self->destructor_class,
ac2dc464 580 inline_destructor => 1,
581 # NOTE:
582 # no need to do this,
583 # Moose always does it
584 inline_accessors => 0,
585 @_,
586 );
5cf3dbcf 587}
588
bf6fa6b3 589our $error_level;
11c86f15 590
591sub throw_error {
592 my ( $self, @args ) = @_;
bf6fa6b3 593 local $error_level = ($error_level || 0) + 1;
11c86f15 594 $self->raise_error($self->create_error(@args));
595}
596
597sub raise_error {
598 my ( $self, @args ) = @_;
599 die @args;
600}
601
602sub create_error {
603 my ( $self, @args ) = @_;
604
18748ad6 605 require Carp::Heavy;
606
bf6fa6b3 607 local $error_level = ($error_level || 0 ) + 1;
18748ad6 608
11c86f15 609 if ( @args % 2 == 1 ) {
610 unshift @args, "message";
611 }
612
fcab1742 613 my %args = ( metaclass => $self, last_error => $@, @args );
11c86f15 614
bf6fa6b3 615 $args{depth} += $error_level;
11c86f15 616
bf6fa6b3 617 my $class = ref $self ? $self->error_class : "Moose::Error::Default";
11c86f15 618
a810a01f 619 Class::MOP::load_class($class);
620
11c86f15 621 $class->new(
bf6fa6b3 622 Carp::caller_info($args{depth}),
623 %args
11c86f15 624 );
625}
626
c0e30cf5 6271;
628
629__END__
630
631=pod
632
633=head1 NAME
634
e522431d 635Moose::Meta::Class - The Moose metaclass
c0e30cf5 636
c0e30cf5 637=head1 DESCRIPTION
638
ac2dc464 639This is a subclass of L<Class::MOP::Class> with Moose specific
e522431d 640extensions.
641
ac2dc464 642For the most part, the only time you will ever encounter an
643instance of this class is if you are doing some serious deep
644introspection. To really understand this class, you need to refer
6ba6d68c 645to the L<Class::MOP::Class> documentation.
646
c0e30cf5 647=head1 METHODS
648
649=over 4
650
590868a3 651=item B<initialize>
652
61bdd94f 653=item B<create>
654
17594769 655Overrides original to accept a list of roles to apply to
61bdd94f 656the created class.
657
17594769 658 my $metaclass = Moose::Meta::Class->create( 'New::Class', roles => [...] );
659
660=item B<create_anon_class>
661
662Overrides original to support roles and caching.
663
664 my $metaclass = Moose::Meta::Class->create_anon_class(
665 superclasses => ['Foo'],
666 roles => [qw/Some Roles Go Here/],
667 cache => 1,
668 );
669
5cf3dbcf 670=item B<make_immutable>
671
ac2dc464 672Override original to add default options for inlining destructor
673and altering the Constructor metaclass.
674
675=item B<create_immutable_transformer>
676
677Override original to lock C<add_role> and memoize C<calculate_all_roles>
678
8c9d74e7 679=item B<new_object>
680
02a0fb52 681We override this method to support the C<trigger> attribute option.
682
a15dff8d 683=item B<construct_instance>
684
ac2dc464 685This provides some Moose specific extensions to this method, you
686almost never call this method directly unless you really know what
687you are doing.
6ba6d68c 688
689This method makes sure to handle the moose weak-ref, type-constraint
ac2dc464 690and type coercion features.
ef1d5f4b 691
093b12c2 692=item B<get_method_map>
e9ec68d6 693
ac2dc464 694This accommodates Moose::Meta::Role::Method instances, which are
695aliased, instead of added, but still need to be counted as valid
e9ec68d6 696methods.
697
78cd1d3b 698=item B<add_override_method_modifier ($name, $method)>
699
ac2dc464 700This will create an C<override> method modifier for you, and install
02a0fb52 701it in the package.
702
78cd1d3b 703=item B<add_augment_method_modifier ($name, $method)>
704
ac2dc464 705This will create an C<augment> method modifier for you, and install
02a0fb52 706it in the package.
707
2b14ac61 708=item B<calculate_all_roles>
709
ef333f17 710=item B<roles>
711
ac2dc464 712This will return an array of C<Moose::Meta::Role> instances which are
02a0fb52 713attached to this class.
714
ef333f17 715=item B<add_role ($role)>
716
ac2dc464 717This takes an instance of C<Moose::Meta::Role> in C<$role>, and adds it
02a0fb52 718to the list of associated roles.
719
ef333f17 720=item B<does_role ($role_name)>
721
ac2dc464 722This will test if this class C<does> a given C<$role_name>. It will
723not only check it's local roles, but ask them as well in order to
02a0fb52 724cascade down the role hierarchy.
725
d79e62fd 726=item B<excludes_role ($role_name)>
727
ac2dc464 728This will test if this class C<excludes> a given C<$role_name>. It will
729not only check it's local roles, but ask them as well in order to
d79e62fd 730cascade down the role hierarchy.
731
9e93dd19 732=item B<add_attribute ($attr_name, %params|$params)>
4e848edb 733
9e93dd19 734This method does the same thing as L<Class::MOP::Class::add_attribute>, but adds
735support for taking the C<$params> as a HASH ref.
ac1ef2f9 736
e606ae5f 737=item B<constructor_class ($class_name)>
738
739=item B<destructor_class ($class_name)>
740
741These are the names of classes used when making a class
742immutable. These default to L<Moose::Meta::Method::Constructor> and
743L<Moose::Meta::Method::Destructor> respectively. These accessors are
744read-write, so you can use them to change the class name.
745
8b1d510f 746=item B<error_class ($class_name)>
747
748The name of the class used to throw errors. This default to
749L<Moose::Error::Default>, which generates an error with a stacktrace
750just like C<Carp::confess>.
751
4fb87686 752=item B<check_metaclass_compatibility>
753
754Moose overrides this method from C<Class::MOP::Class> and attempts to
755fix some incompatibilities before doing the check.
756
11c86f15 757=item B<throw_error $message, %extra>
758
759Throws the error created by C<create_error> using C<raise_error>
760
761=item B<create_error $message, %extra>
762
763Creates an error message or object.
764
765The default behavior is C<create_error_confess>.
766
767If C<error_class> is set uses C<create_error_object>. Otherwise uses
768C<error_builder> (a code reference or variant name), and calls the appropriate
769C<create_error_$builder> method.
770
771=item B<error_builder $builder_name>
772
773Get or set the error builder. Defaults to C<confess>.
774
775=item B<error_class $class_name>
776
50e9d6a5 777Get or set the error class. This defaults to L<Moose::Error::Default>.
11c86f15 778
779=item B<create_error_confess %args>
780
781Creates an error using L<Carp/longmess>
782
783=item B<create_error_croak %args>
784
785Creates an error using L<Carp/shortmess>
786
787=item B<create_error_object %args>
788
789Calls C<new> on the C<class> parameter in C<%args>. Usable with C<error_class>
790to support custom error objects for your meta class.
791
792=item B<raise_error $error>
793
794Dies with an error object or string.
795
c0e30cf5 796=back
797
798=head1 BUGS
799
ac2dc464 800All complex software has bugs lurking in it, and this module is no
c0e30cf5 801exception. If you find a bug please either email me, or add the bug
802to cpan-RT.
803
c0e30cf5 804=head1 AUTHOR
805
806Stevan Little E<lt>stevan@iinteractive.comE<gt>
807
808=head1 COPYRIGHT AND LICENSE
809
778db3ac 810Copyright 2006-2008 by Infinity Interactive, Inc.
c0e30cf5 811
812L<http://www.iinteractive.com>
813
814This library is free software; you can redistribute it and/or modify
ac2dc464 815it under the same terms as Perl itself.
c0e30cf5 816
8a7a9c53 817=cut
1a563243 818