Otto Hirr wrote:
> Greetings,
>
> What are the implications of trying to define
> subs in a component.

Massive headaches.

> Example: the <%once> and <%init>
> sections may want to do part of the same thing, so
> you define a sub in <%once> call it, and also call it
> in <%init>.
>
> Should this work correctly? Or is it that the closure
> of <%once> and <%init> are not containing the name of
> sub, but in the package, hence there would be name collision?
>
>   

You're on the right track in thinking about name collisions.  When you 
define a sub in a component it actually goes into the 
HTML::Mason::Commands package.  The implications of this depend on the 
way you have Mason configured.  If you're running it within mod_perl on 
a standard Apache setup you have a persistent Perl machine that 
maintains state from one web request to the next.  On top of that you 
have multiple apache processes that can serve requests.  Using 
subroutines in such a situation can lead to name space collisions and 
intermittent race conditions.

An example of a race condition is when you build component A that 
defines sub foo.  Noticing that this function is available to all 
components and you use foo in component B.  In testing this may work 
fine as long as component A is always called at least once IN EVERY 
APACHE process before component B is ever called.  However, if you call 
component B in an apache process that has yet to run component A you'll 
end up with an error saying that foo is not defined.  The same thing can 
happen when you restart the server.

If "foo" is something that should be called by more than one component 
it should be moved to its own component, defined as a <%method> of 
component A, or as a function/method in an external Perl module.  If it 
shouldn't be shared outside of comp A you can define it as a 
subcomponent of A using <%def> or if you don't want to deal with the 
long mason calling syntax you can define it as a localized scalar 
holding a subroutine reference in the <%once> or <%shared> block of 
component A.  So instead of this:

<%once>
sub foo { stuff() }
...
</%once>
<% foo() %>

You can do this:

<%once>
my $foo = sub { stuff() };
...
</%once>
<% &$foo() %>

Good luck,

-- Ben

-------------------------------------------------------------------------
This SF.net email is sponsored by: Microsoft
Defy all challenges. Microsoft(R) Visual Studio 2008.
http://clk.atdmt.com/MRT/go/vse0120000070mrt/direct/01/
_______________________________________________
Mason-users mailing list
Mason-users@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mason-users

Reply via email to