[Catalyst] plugins; was Re: debug mode

Matt S Trout dbix-class at trout.me.uk
Fri Jun 8 03:12:34 GMT 2007

On Thu, Jun 07, 2007 at 04:36:41PM -0700, Maurice Aubrey wrote:
> >Separating out the interrogation of the context and retrieval of data into
> >the ACCEPT_CONTEXT is how you avoid loose coupling - and it also then means
> >you know you have -one- method that requires a mocked $c to test rather
> >than potentially any in your entire codebase needing that.
> Avoid loose coupling? You mean tight?

Yes. Braino :)
> I was thinking you're basically pushing the mocked $c testing to the
> singleton class. If it works, then any code that uses it should work.
> The retrieval of the data is already handled for you (by the singleton).
> You just have to interrogate it, so one less piece.

But equally if I'm using the context I can always just pass it when I
instantiate the component I'm planning to test; if the context acquisition
code is inherited from some component with an ACCEPT_CONTEXT you only
need to test -that- once too.

> >>>It can be a bit more work up-front but it makes you think about your
> >>>architecture, which I find pays off down the road.
> >>A method call could also need to have access to other modules/packages
> >>it will delegate to. The singleton seems equivalent.
> >
> >I don't do that either. I generally create associated objects via factory
> >methods and have an attribute for the related class with a default.
> >
> >An example of this would be the _action_class member of 
> >Catalyst::Controller,
> >which is what defaults you to Catalyst::Action as your action class - 
> >related
> >classes should -always- be overridable.
> There are lots of cases where you wouldn't do that though.
> Like if you need to make some directories, you're not going to have a
> new_file_path_like_object() methods and a default_file_path_class().
> You're just going to use File::Path.

I use Path::Class, and actually I usually have something like that hidden
behind a driver API that -does- abstract what class it produces.
> But your point being that you want your models to work with any
> Catalyst-type-thingy, rather than assuming it's part of your Catalyst
> application? Hmmm.

Well, for a start any Catalyst app. But I'll also for e.g. have scripts
where there's a concept of the "current user" but it gets passed explicitly
rather than pulled from $c->user by an ACCEPT_CONTEXT.

Also my components are often designed with the idea I may need to re-use them
in more than one app, at which point at the very least you need to parameterise
the application instance you call ->current_context (or whatever the method
might be called) on.

> So what do you think of things like Perl's @INC? How would you implement
> it without the equivalent of a singleton class?
> And if a class wanted to access it, would you write something equivalent
> to an ACCEPT_CONTEXT method that would be passed the Perl environment?

Lisp environments have already solved that one.

But there -is- a point where it makes sense to have something effectively
global and just use dynamic scoping (i.e. local *foo) to handle it.

I'm just expressing a preference to draw the line in a different place to
you, I think.

      Matt S Trout       Need help with your Catalyst or DBIx::Class project?
   Technical Director    Want a managed development or deployment platform?
 Shadowcat Systems Ltd.  Contact mst (at) shadowcatsystems.co.uk for a quote
http://chainsawblues.vox.com/             http://www.shadowcatsystems.co.uk/ 

More information about the Catalyst mailing list