1 package Moose::Manual::MethodModifiers;
3 # ABSTRACT: Moose's method modifiers
9 =head1 WHAT IS A METHOD MODIFIER?
11 Moose provides a feature called "method modifiers". You can also think
12 of these as "hooks" or "advice".
14 It's probably easiest to understand this feature with a few examples:
24 before 'foo' => sub { print "about to call foo\n"; };
25 after 'foo' => sub { print "just called foo\n"; };
31 print " I'm around foo\n";
35 print " I'm still around foo\n";
38 Now if I call C<< Example->new->foo >> I'll get the following output:
46 You probably could have figured that out from the names "before",
47 "after", and "around".
49 Also, as you can see, the before modifiers come before around
50 modifiers, and after modifiers come last.
52 When there are multiple modifiers of the same type, the before and
53 around modifiers run from the last added to the first, and after
54 modifiers run from first added to last:
68 Method modifiers have many uses. They are often used in roles to alter the
69 behavior of methods in the classes that consume the role. See
70 L<Moose::Manual::Roles> for more information about roles.
72 Since modifiers are mostly useful in roles, some of the examples below
73 are a bit artificial. They're intended to give you an idea of how
74 modifiers work, but may not be the most natural usage.
76 =head1 BEFORE, AFTER, AND AROUND
78 Method modifiers can be used to add behavior to a method that Moose
79 generates for you, such as an attribute accessor:
81 has 'size' => ( is => 'rw' );
83 before 'size' => sub {
87 Carp::cluck('Someone is setting size');
91 Another use for the before modifier would be to do some sort of
92 prechecking on a method call. For example:
94 before 'size' => sub {
97 die 'Cannot set size while the person is growing'
98 if @_ && $self->is_growing;
101 This lets us implement logical checks that don't make sense as type
102 constraints. In particular, they're useful for defining logical rules
103 about an object's state changes.
105 Similarly, an after modifier could be used for logging an action that
108 Note that the return values of both before and after modifiers are
111 An around modifier is more powerful than either a before or
112 after modifier. It can modify the arguments being passed to the
113 original method, and you can even decide to simply not call the
114 original method at all. You can also modify the return value with an
117 An around modifier receives the original method as its first argument,
118 I<then> the object, and finally any arguments passed to the method.
120 around 'size' => sub {
124 return $self->$orig()
129 if $self->likes_small_things();
131 return $self->$orig($size);
134 C<before>, C<after>, and C<around> can also modify multiple methods
135 at once. The simplest example of this is passing them as a list:
137 before [qw(foo bar baz)] => sub {
138 warn "something is being called!";
141 This will add a C<before> modifier to each of the C<foo>, C<bar>,
142 and C<baz> methods in the current class, just as though a separate
143 call to C<before> was made for each of them. The list can be passed
144 either as a bare list, or as an arrayref. Note that the name of the
145 function being modified isn't passed in in any way; this syntax is
146 only intended for cases where the function being modified doesn't
147 actually matter. If the function name does matter, use something like this:
149 for my $func (qw(foo bar baz)) {
150 before $func => sub {
151 warn "$func was called!";
155 In addition, you can specify a regular expression to indicate the
156 methods to wrap, like so:
158 after qr/^command_/ => sub {
159 warn "got a command";
162 This will match the regular expression against each method name
163 returned by L<Class::MOP::Class/get_method_list>, and add a modifier
164 to each one that matches. The same caveats apply as above. Using regular
165 expressions to determine methods to wrap is quite a bit more powerful
166 than the previous alternatives, but it's also quite a bit more
167 dangerous. In particular, you should make sure to avoid wrapping
168 methods with a special meaning to Moose or Perl, such as C<meta>, C<new>,
169 C<BUILD>, C<DESTROY>, C<AUTOLOAD>, etc., as this could cause
170 unintended (and hard to debug) problems.
172 =head1 INNER AND AUGMENT
174 Augment and inner are two halves of the same feature. The augment
175 modifier provides a sort of inverted subclassing. You provide part of
176 the implementation in a superclass, and then document that subclasses
177 are expected to provide the rest.
179 The superclass calls C<inner()>, which then calls the C<augment>
180 modifier in the subclass:
189 my $xml = "<document>\n";
191 $xml .= "</document>\n";
196 Using C<inner()> in this method makes it possible for one or more
197 subclasses to then augment this method with their own specific
206 augment 'as_xml' => sub {
209 my $xml = " <report>\n";
211 $xml .= " </report>\n";
216 When we call C<as_xml> on a Report object, we get something like this:
223 But we also called C<inner()> in C<Report>, so we can continue
224 subclassing and adding more content inside the document:
226 package Report::IncomeAndExpenses;
232 augment 'as_xml' => sub {
235 my $xml = ' <income>' . $self->income . '</income>';
237 $xml .= ' <expenses>' . $self->expenses . '</expenses>';
240 $xml .= inner() || q{};
245 Now our report has some content:
250 <expenses>$8</expenses>
254 What makes this combination of C<augment> and C<inner()> special is
255 that it allows us to have methods which are called from parent (least
256 specific) to child (most specific). This inverts the normal
259 Note that in C<Report::IncomeAndExpenses> we call C<inner()> again. If the
260 object is an instance of C<Report::IncomeAndExpenses> then this call is a
261 no-op, and just returns false. It's a good idea to always call C<inner()> to
262 allow for future subclassing.
264 =head1 OVERRIDE AND SUPER
266 Finally, Moose provides some simple sugar for Perl's built-in method
267 overriding scheme. If you want to override a method from a parent
268 class, you can do this with C<override>:
276 has 'job_title' => ( is => 'rw' );
278 override 'display_name' => sub {
281 return super() . q{, } . $self->title();
284 The call to C<super()> is almost the same as calling C<<
285 $self->SUPER::display_name >>. The difference is that the arguments
286 passed to the superclass's method will always be the same as the ones
287 passed to the method modifier, and cannot be changed.
289 All arguments passed to C<super()> are ignored, as are any changes
290 made to C<@_> before C<super()> is called.
294 Because all of these method modifiers are implemented as Perl
295 functions, you must always end the modifier declaration with a
298 after 'foo' => sub { };