* Chisel Wright <[EMAIL PROTECTED]> [2008-04-16 11:50]: > Just for chuckles - does anyone have an idea of the pain-level > involved in converting a non-Chained application to Chained? > > Or is it just not worth the effort for an established project?
Totally depends. I ported an app to Catalyst that previously was basically one-action-per-controller. It cannot be called anything less than a lot of work, but it paid of royally. The code is as DRY as it was before, but it’s now far better structured. Previously it was blocks of if-elsif chains grouping together execution steps that are shared by some URIs but not others – now it’s Chained. A typical controller looks something like this: sub base : Chained PathPart('doc') CaptureArgs(0) { ... } sub list : Chained('base') PathPart('') Args(0) { ... } sub item : Chained('base') PathPart('') CaptureArgs(1) { ... } sub view : Chained('item') PathPart('') Args(0) { ... } sub edit : Chained('item') Args(0) { ... } This gives `/doc` (goes `base` then `list`), `/doc/*` (goes `base` then `item` then `view`), and `/doc/*/edit` (goes `base` then `item` then `edit`). And then you can put stuff shared by all actions in `base`[^1], and stuff shared by all actions that relate to a single document (eg. stuffing that document into the stash) all in `item`. By liberal use of `PathPart('') CaptureArgs(0)` you can force any URI to step down any number of intermediate steps you require, so you can use that to group together shared code any way you see fit: sub foo : Chained CaptureArgs(0) {} sub bar : Chained('foo') PathPart('') CaptureArgs(0) {} sub baz : Chained('bar') PathPart('') CaptureArgs(0) {} sub qux : Chained('baz') Args(0) {} This will dispatch `/foo/qux` across the entire foo bar baz qux chain. Now consider: sub quux : Chained('bar') Args(0) {} This will produce anoter end point, this one at `/foo/quux`, but it will dispatch only across foo bar quux. Chained lets you build trees of actions where each leaf is a URI, and by using `PathPart('') CaptureArgs(0)` you can insert any number of non-leaf nodes into it. Catalyst will just DTRT. So you can use Chained dispatch just like other Perl-level flow control mechanisms and code scoping. What does all this have to do with your question? Well, if you don’t specifically exploit this benefit of Chained, and merely do most of the work at the endpoints of your chains, then you don’t really gain much from switching. It is only worth the bother (but then is *well* worth the bother) if you are willing to restructure your code to benefit from Chained (not necessarily immediately, mind – maybe as an ongoing refactor). The feasibility and cost of that undertaking, however, depends on your codebase and circumstances. In my case, the code structure already quite naturally fit into Chained, so porting about 1,500 LoC of controllers from the ad-hoc style I describe above to Catalyst with Chained took roughly a week, maybe even a little less, and was by far the easiest part of the port. How painful it will be in your case depends on how clean your codebase is. If your controllers are thin, as they should be, and you don’t have terrible spaghetti, it shouldn’t be too painful. What’s more, since you are already writing for Catalyst, you don’t have to get into a boil-the-ocean effort like mine was[^2] (due to the fact that I was porting a non-Catalyst app). [^1]: Usually nothing, but it’s convenient to have a single pivot point you for moving the entire enchilada to a different part of your URI space. [^2]: Still is, actually. 2.5 months and not yet done, though I am finally close. Regards, -- Aristotle Pagaltzis // <http://plasmasturm.org/> _______________________________________________ List: Catalyst@lists.scsys.co.uk Listinfo: http://lists.scsys.co.uk/cgi-bin/mailman/listinfo/catalyst Searchable archive: http://www.mail-archive.com/catalyst@lists.scsys.co.uk/ Dev site: http://dev.catalyst.perl.org/