Yes.
The sugary API,
the one 95% of users will interact with,
is very stable.
Any changes will be 100% backwards compatible.

The meta API is less set in stone.
We reserve the right to tweak parts of it to improve efficiency or consistency.
This will not be done lightly.
We do perform deprecation cycles.
We really do not like making ourselves look bad by breaking your code.
Submitting test cases is the best way to ensure that your code is not inadvertently broken by refactoring.

Firstly,
nothing in life is free,
and some Moose features do cost more than others.
It is also the policy of Moose to only charge you for the features you use,
and to do our absolute best to not place any extra burdens on the execution of your code for features you are not using.
Of course using Moose itself does involve some overhead,
but it is mostly compile time.
At this point we do have some options available for getting the speed you need.

Currently we provide the option of making your classes immutable as a means of boosting speed.
This will mean a slightly larger compile time cost,
but the runtime speed increase (especially in object construction) is pretty significant.
This can be done with the following code:

Ideally, you should never write your own new method, and should use Moose's other features to handle your specific object construction needs. Here are a few scenarios, and the Moose way to solve them;

If you need to call initialization code post instance construction, then use the BUILD method. This feature is taken directly from Perl 6. Every BUILD method in your inheritance chain is called (in the correct order) immediately after the instance is constructed. This allows you to ensure that all your superclasses are initialized properly as well. This is the best approach to take (when possible) because it makes subclassing your class much easier.

If you need to affect the constructor's parameters prior to the instance actually being constructed, you have a number of options.

To change the parameter processing as a whole, you can use the BUILDARGS method. The default implementation accepts key/value pairs or a hash reference. You can override it to take positional args, or any other format

To change the handling of individual parameters, there are coercions (See the Moose::Cookbook::Basics::HTTP_SubtypesAndCoercion for a complete example and explanation of coercions). With coercions it is possible to morph argument values into the correct expected types. This approach is the most flexible and robust, but does have a slightly higher learning curve.

This creates a custom type for DateTime objects, then attaches a coercion to that type. The timestamp attribute is then told to expect a DateTime type, and to try to coerce it. When a Str type is given to the timestamp accessor, it will attempt to coerce the value into a DateTime object using the code in found in the via block.

It is also possible to do deflation using coercion, but this tends to get quite complex and require many subtypes. An example of this is outside the scope of this document, ask on #moose or send a mail to the list.

Still another option is to write a custom attribute metaclass, which is also outside the scope of this document, but we would be happy to explain it on #moose or the mailing list.

You can't, actually: before only runs before the main method, and it cannot easily affect the method's execution.

You similarly can't use after to affect the return value of a method.

We limit before and after because this lets you write more concise code. You do not have to worry about passing @_ to the original method, or forwarding its return value (being careful to preserve context).

The around method modifier has neither of these limitations, but is a little more verbose.

Alternatively, the MooseX::Mangle extension provides the mangle_args function, which does allow you to affect @_.

Yes, but only if you throw an exception. If this is too drastic a measure then we suggest using around instead. The around method modifier is the only modifier which can gracefully prevent execution of the main method. Here is an example:

This is not what they intended, because the type constraint Address is too loose in this case. It is saying that all strings are Addresses, which is obviously not the case. The solution is to provide a where clause that properly restricts the type constraint:

subtype 'Address', as 'Str', where { looks_like_address($_) };

This will allow the coercion to apply only to strings that fail to look like an Address.

BUILD is never called in composed roles. The primary reason is that roles are not order sensitive. Roles are composed in such a way that the order of composition does not matter (for information on the deeper theory of this read the original traits papers here http://www.iam.unibe.ch/~scg/Research/Traits/).

Because roles are essentially unordered, it would be impossible to determine the order in which to execute the BUILD methods.

Use attribute triggers, which fire after an attribute is set, to facilitate initialization. These are described in the Moose docs, and examples can be found in the test suite.

In general, roles should not require initialization; they should either provide sane defaults or should be documented as needing specific initialization. One such way to "document" this is to have a separate attribute initializer which is required for the role. Here is an example of how to do this:

In this example, the role will not compose successfully unless the class provides a init_height method.

If none of those solutions work, then it is possible that a role is not the best tool for the job, and you really should be using classes. Or, at the very least, you should reduce the amount of functionality in your role so that it does not require initialization.

Currently when subclassing a module is done at runtime with the extends keyword, but attributes are checked at compile time by Perl. To make attributes work, you must place extends in a BEGIN block so that the attribute handlers will be available at compile time, like this: