locked_user sundialsvc4 has asked for the wisdom of the Perl Monks concerning the following question:

Within the documentation for HTML::FormHandler (attribute has_field), I found this admonition:

Don't forget no HTML::FormHandler::Moose; at the end of the package.

Hence, two questions:

  1. “Why?”
  2. If this declaration is necessary, where should it be placed? Sometimes I see a no Moose; (or no-whatever...) placed after the attribute-definitions but before the methods. Sometimes I see it at the end of a package. Sometimes I don't see it at all. What's correct? And, why?

I thought that I understood the meaning of this directive, but maybe it has important side-effects that I don't grok.

Replies are listed 'Best First'.
Re: Why "no Moose?"
by Fletch (Bishop) on Jan 27, 2009 at 14:01 UTC

    Moose and friends inserts subs for its helpers (e.g. has) into the package in question. The no Moose incantation runs its unimport method which removes those subs from the package's symbol table which means that you can't accidentally or intentionally call those routines (an extreme example, but in another compilation unit you couldn't do { package Foo; has 'new_attrib' => ( ... ); } since Foo::has is no longer a valid sub). It's not "necessary", but it's "cleaner".

    The cake is a lie.
    The cake is a lie.
    The cake is a lie.

      Moose is also a source filter, so (as with all filters of non-Lisp languages) it's probably best to turn it off when you don't actually need it.

      UPDATE: That's completely wrong; I'm sorry. See kyle's post below.
      UPDATE 2: No, really, I know now. Further down-voting will not convince me any more. :-)

Re: Why "no Moose?"
by ikegami (Patriarch) on Jan 27, 2009 at 21:03 UTC
    To prevent someone from doing YourModule->has_field() or $your_object->has_field();, though I'm hard pressed to find a situation where that would occur. (Automatic documentation generator and other forms of code introspection, I suppose.)

      You would be surprised how many people I have seen try to do this:

      MyMooseModule->has(thing => ( ... ));
      as a way to dynamically extend a class at runtime, instead of just (correctly) using the MOP
      MyMooseModule->meta->add_attribute(thing => ( ... ));
      I suspect to some degree it is because people are too used to the older perl OO frameworks like Class::Accessor which forced you to inherit from itself and therefore made things like $some_object->mk_accessor('foo') possible, even though that is evil and wrong ;)

      -stvn