You are viewing a plain text version of this content. The canonical link for it is here.
Posted to user@struts.apache.org by Ted Husted <hu...@apache.org> on 2007/11/07 20:56:50 UTC

How Many Methods Must an Action Walk Down (was Re: Annotation Validation, per method?)

On Nov 6, 2007 8:10 PM, Gary Affonso <gl...@greywether.com> wrote:
> For some reason folks new to s2 seem to get it backwards and want to
> stuff a bunch of Action methods into a single Action class.

It's probably because the standard S2/WW validation workflow implies
that an Action class will have multiple methods that an application
will invoke in the normal course. Meanwhile, in Struts 1 there is a
"DispatchAction" that does much the same thing. From other
discussions, I gather that "multiple actions per controller" is
considered a Good Thing on platforms like Ruby on Rails.

>From a technical perspective, the two true pain points are "input" and
"prepare". We need a natural way to obtain an input form that can also
call a method that loads any rich controls the form may use. The
standard S2 idiom for that is Preparable and "action!input". It's an
elegant idiom, but the mechanism paves the way for other forms like
"action!create", "action!read", "action!update", and "action!delete".

It might be interesting to discuss some elegant, one-method purist
alternatives that address input preparation without using method
invocation.

-T.

On Nov 6, 2007 8:10 PM, Gary Affonso <gl...@greywether.com> wrote:
> Ted Husted wrote:
> > Of course, if you use one-action-method per Action-class, then all the
> > annotations work just fine.
>
> +1 on one-action-method per Action class.
>
> My personal opinion (after nearly 5 years of heavy WebWork/s2 use) is
> that this is the best-practice and that multiple action methods per
> Action class should be a rarity.
>
> For some reason folks new to s2 seem to get it backwards and want to
> stuff a bunch of Action methods into a single Action class.
>
> There's a lot of downsides to that (as this post and another recent post
> both illustrate) and there are few upsides.  And the upsides you might
> think are upsides (like code sharing between Action methods) are often
> not the upsides you think they are.  If you're sharing lots of code
> between Action methods, it's my experience that code belongs in other
> classes or even in other tiers.
>
> My first WebWork app had a small number of Actions and lots of Action
> methods.  I came to regret it.
>
> My latest s2 apps have one-action-method per Action class.  Religiously,
> no matter how silly it might seem to write a do-nearly-nothing Action.
> I'm much, much happier this way and the app is way more self-documenting.
>
> Just my $.02.
>
> - Gary

---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
For additional commands, e-mail: user-help@struts.apache.org


Re: How Many Methods Must an Action Walk Down (was Re: Annotation Validation, per method?)

Posted by Dave Newton <ne...@yahoo.com>.
--- Jeromy Evans <je...@blueskyminds.com.au>
wrote:
> Dave, does that mean you don't favour one approach
> over the other? ie. happy with multiple methods per
action?

I have no clear preference right now. I tend not to
have a lot of methods in my actions anyway, but I'll
group stuff together when it seems logical
(particularly small-ish Ajax actions that operate on a
common model object) and CRUD-like stuff.

d.


---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
For additional commands, e-mail: user-help@struts.apache.org


Re: How Many Methods Must an Action Walk Down (was Re: Annotation Validation, per method?)

Posted by Jeromy Evans <je...@blueskyminds.com.au>.
Dave Newton wrote:
>> Again, not one *method*.  That'd be crazy!
>>     
>
> That's what's being discussed, I'm pretty sure, but
> with an eye towards a different "prepare" cycle: the
> whole Preparable lifecycle makes more sense if there
> are multiple (request-handling) methods in an Action
> class. If there's only "execute" you don't gain very
> much by having the framework call prepare(), and I'd
> probably even argue it's less clear than calling it
> manually from execute().
>
> If, OTOH, you have several methods that all require
> identical preparation then a prepare() in each method
> is a bit noisier than letting the framework call it.
>
>
>   
Dave, does that mean you don't favour one approach over the other? ie. 
happy with multiple methods per action?

I've never settled on only "one action class per action" or only 
"multiple action methods per action".  I've found both conventions have 
their time and place, although I've been longing for a consistent approach.

I use action!method notation a lot despite a hatred of it.  However I 
have been trying to phase out GET's to action!input and replace them 
with a GET to a clean URL and use the wildcard notation only for posts.  
I also only use doMethod notation (ie. method="do{1}") as a precaution 
against arbitrary method calls. 

Your preparable lifecycle points are well received here.

The "one action class per action" approach is clean and tidy on small 
applications but I find it blows configuration out exponentially on 
large apps (although codebehind fixes that)

My latest favourite approach is as per RoR/the rest plugin - that is, a 
set of WELL KNOWN action methods per action class, rather than just 
execute() or arbitrary action methods per action.

I'd appreciate hearing what others have settled into?


---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
For additional commands, e-mail: user-help@struts.apache.org


Re: How Many Methods Must an Action Walk Down (was Re: Annotation Validation, per method?)

Posted by Don Brown <do...@gmail.com>.
On Nov 8, 2007 12:29 PM, Dave Newton <ne...@yahoo.com> wrote:
> --- Gary Affonso <gl...@greywether.com> wrote:
> >  > Look at the "Dynamic Method Invocation" section,
> >  > 1/2-2/3 of the way down.
> > Well, that explains it.  The wildcard feature seems
> > to come from s1 (which I never used) and the
> > "dynamic method invocation" feature wasn't
> > very well documented (not even named) until s2.
>
> AFAIK that feature was available since ~WW 2.1, but
> I'm a little fuzzy on that. I think it was presented
> as action aliasing without configuration or something.

I think it goes back farther than that - it has been around since the
WW 1 days.  JIRA (a WW 1 app) uses the action!method notation quite a
bit.  The change in WW 2.1 could have been the ability to specify the
method on the ActionConfig.

Don

>
> d.
>
>
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
> For additional commands, e-mail: user-help@struts.apache.org
>
>

---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
For additional commands, e-mail: user-help@struts.apache.org


Re: How Many Methods Must an Action Walk Down (was Re: Annotation Validation, per method?)

Posted by Gary Affonso <gl...@greywether.com>.
Dave Newton wrote:
> --- Gary Affonso <gl...@greywether.com> wrote:
>>  > Look at the "Dynamic Method Invocation" section,
>>  > 1/2-2/3 of the way down.
>> Well, that explains it.  The wildcard feature seems
>> to come from s1 (which I never used) and the 
>> "dynamic method invocation" feature wasn't 
>> very well documented (not even named) until s2.
> 
> AFAIK that feature was available since ~WW 2.1, but
> I'm a little fuzzy on that. I think it was presented
> as action aliasing without configuration or something.

Yah, I vaguely remember seeing something about it on the WebWork lists. 
  I ignored it, of course, given the fact that I had already accepted 
one-action-per-action-class as my personal savior.

:-)

- Gary

P.S.  I'm also seeing more places in the framework (that I rarely use) 
that do seem to guide people to the multiple-methods-per-action-class. 
The taglibs seem to encourage it.  Good thing I avoid taglibs! <grin>

---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
For additional commands, e-mail: user-help@struts.apache.org


Re: How Many Methods Must an Action Walk Down (was Re: Annotation Validation, per method?)

Posted by Dave Newton <ne...@yahoo.com>.
--- Gary Affonso <gl...@greywether.com> wrote:
>  > Look at the "Dynamic Method Invocation" section,
>  > 1/2-2/3 of the way down.
> Well, that explains it.  The wildcard feature seems
> to come from s1 (which I never used) and the 
> "dynamic method invocation" feature wasn't 
> very well documented (not even named) until s2.

AFAIK that feature was available since ~WW 2.1, but
I'm a little fuzzy on that. I think it was presented
as action aliasing without configuration or something.

d.


---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
For additional commands, e-mail: user-help@struts.apache.org


Re: How Many Methods Must an Action Walk Down (was Re: Annotation Validation, per method?)

Posted by Gary Affonso <gl...@greywether.com>.
Dave Newton wrote:
>> Curiously, action!input is not a part of the
>> framework I'm familiarwith.  Can you point me
>> to some docs that describe it?
 >
 > http://struts.apache.org/2.x/docs/action-configuration.html
 >
 > Look at the "Dynamic Method Invocation" section,
 > 1/2-2/3 of the way down.

Well, that explains it.  The wildcard feature seems to come from s1 
(which I never used) and the "dynamic method invocation" feature wasn't 
very well documented (not even named) until s2.

Thanks for the pointer, this is good stuff for me to know.  The vast 
majority of my experience is with WebWork.  For the most part s2 has 
been like slipping into a nicely worn pair of shoes.

But then I find out somebody added blinky light in the soles. :-)

I still have a hard time imagining using either of those features.  I 
completely get why they are there.  There was a time where I valued 
brevity over clarity, too.  I guess I'm gettin old.

>> Again, not one *method*.  That'd be crazy!
> 
> That's what's being discussed, I'm pretty sure, but
> with an eye towards a different "prepare" cycle: the
> whole Preparable lifecycle makes more sense if there
> are multiple (request-handling) methods in an Action
> class. If there's only "execute" you don't gain very
> much by having the framework call prepare(), and I'd
> probably even argue it's less clear than calling it
> manually from execute().

I'd say that argument is more valid for the validate() method.  It 
really does offer nothing besides a dedicated method for doing something 
just as easy to do in the first part of "execute()".

But for prepare() that's not the case (at least for me).  The prepare 
interceptor is typically called after the first of two "params" 
interceptors.  Something like...

   params interceptor
     prepare interceptor
   params interceptor
   ...more

This is a pretty elegant way to deal with hydrating objects from IDs 
embedded in the form and then doing direct-model-injectition into that 
recently retrieved object from fields in the *same* form.

Example...

If your view does this:

   <input type="hidden" name="addressId" value="123">
   <input type="hidden" name="address.name" value="new name">
   <input type="hidden" name="address.zip" value="38123">

Then prepare() allows you to use the first "params" interceptor to scoop 
up the ID, the prepare method to go get an "Address" object 
corresponding to that ID, and then the second "params" interceptor to 
scoop the address-specific fields in the form into that recently 
hydrated object.

In other words, your action gets *two* shots at accepting injected form 
data.

That's not do-able with just the execute() method.

I mean it *is* do-able but you start having to do things like provide a 
temporary address object to capture the form data (in addition to an ID 
property) and then in execute() go get the *real* address object 
after-the-fact (using the ID) and then transfer the address data from 
the temp object to the real address object.

Prepare seems way better and way more clear.  Or did I miss something?

> If, OTOH, you have several methods that all require
> identical preparation then a prepare() in each method
> is a bit noisier than letting the framework call it.

I absolutely agree.  If you're doing a ton of the same preparation for 
your action methods then you should consolidate that into a single place.

But, to paraphrase what as I said earlier, if you're doing a ton of 
preparation for your Action methods, there's probably a better place to 
put that code than in your Action.

Everybody, at this point, seems to "get" that you put as little java 
code as possible in the view (JSP, etc.).  That's something that I think 
we need to start preaching for the Action as well...

   Put as little code as possible in the Actions!

Put the code in domain objects, service objects, dao objects, 
business-logic objects, etc. but keep it out of the action!

Uh, are we still talking apples-to-apples here?  I think maybe I got off 
on a tangent.

:-)

- Gary


---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
For additional commands, e-mail: user-help@struts.apache.org


Re: How Many Methods Must an Action Walk Down (was Re: Annotation Validation, per method?)

Posted by Dave Newton <ne...@yahoo.com>.
--- Gary Affonso <gl...@greywether.com> wrote:
> Ted Husted wrote:
>> Meanwhile, in Struts 1 there is a "DispatchAction"
>> that does much the same thing. From other
>> discussions, I gather that "multiple actions per
>> controller" is considered a Good Thing on platforms
>> like Ruby on Rails.

It's really only a Good Thing in RoR because the
framework and markup makes it easier to do it that
way: it's a result of RoR's opinionation... Linking to
a different action requires an additional parameter in
the link tag "custom tag"; a conceptual equivalent
might be an S2 link with a "namespace" attribute in
addition to a configured "action" name.

> But for what I do with it (fairly typical webapps)
> one-action-class-per-action has served me very well.

I don't think anybody's saying that it's a bad idea,
but the framework does sort of "gently nudge" a
developer in the multiple-methods-per-action-class
(see below).

> I have limited experience using webwork/s2 with AJAX
> (I assume this is what you mean by "rich controls").

I think we're just talking about any type of control
that requires some form of preparation on the server
side; an Ajax control could be loaded by any
action/method on page load.

> Curiously, action!input is not a part of the
> framework I'm familiarwith.  Can you point me
> to some docs that describe it?

http://struts.apache.org/2.x/docs/action-configuration.html

Look at the "Dynamic Method Invocation" section,
1/2-2/3 of the way down.

> Again, not one *method*.  That'd be crazy!

That's what's being discussed, I'm pretty sure, but
with an eye towards a different "prepare" cycle: the
whole Preparable lifecycle makes more sense if there
are multiple (request-handling) methods in an Action
class. If there's only "execute" you don't gain very
much by having the framework call prepare(), and I'd
probably even argue it's less clear than calling it
manually from execute().

If, OTOH, you have several methods that all require
identical preparation then a prepare() in each method
is a bit noisier than letting the framework call it.

(This was just discussed on a current project and that
seemed to be the general consensus, anyway, but for
the most part I agree with it.)

d.


---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
For additional commands, e-mail: user-help@struts.apache.org


Re: How Many Methods Must an Action Walk Down (was Re: Annotation Validation, per method?)

Posted by Gary Affonso <gl...@greywether.com>.
Ted Husted wrote:
> On Nov 6, 2007 8:10 PM, Gary Affonso <gl...@greywether.com> wrote:
>> For some reason folks new to s2 seem to get it backwards and want to
>> stuff a bunch of Action methods into a single Action class.
> 
> It's probably because the standard S2/WW validation workflow implies
> that an Action class will have multiple methods that an application
> will invoke in the normal course.

How does it imply that?  Or do you mean "multiple methods" in the sense 
of prepare() and validate() in addition to execute().

I'm not suggesting those go away (I love those).  But those are not 
"custom" action methods, those are framework action methods.  So maybe I 
need to clarify...

When I say "one action class per action", that's what I mean.  I don't 
mean one action class, having only one action method, per action.  In 
other words, every unique url call into struts has a corresponding Action.

So I if I want to do the typical login stuff (which I no longer do 
thanks to Acegi :-), I have three urls and three actions and two views):

Urls
   http://www.myapp.com/login_form.action
   http://www.myapp.com/login_form_process.action
   http://www.myapp.com/login_thankyou.action

Actions
   LoginFormShow.action
   LoginFormProcess.action
   LoginThankyou.action

Views
   login_form.ftl
   login_form_thankyou.ftl

> Meanwhile, in Struts 1 there is a
> "DispatchAction" that does much the same thing. From other
> discussions, I gather that "multiple actions per controller" is
> considered a Good Thing on platforms like Ruby on Rails.

Curious.  I've only got my niche of experience with s2, I haven't used 
it in every conceivable situation.  But for what I do with it (fairly 
typical webapps) one-action-class-per-action has served me very well.

But I would love to hear reasons why I may be missing the boat, somehow. :-)

>>From a technical perspective, the two true pain points are "input" and
> "prepare". We need a natural way to obtain an input form that can also
> call a method that loads any rich controls the form may use.

I have limited experience using webwork/s2 with AJAX (I assume this is 
what you mean by "rich controls").  I've done a bit with integrating YUI 
controls with s2 Actions that deliver XML (instead of an HTML response). 
  The single-action-class-per-action idiom work well there, though.

> The
> standard S2 idiom for that is Preparable and "action!input". It's an
> elegant idiom, but the mechanism paves the way for other forms like
> "action!create", "action!read", "action!update", and "action!delete".

Curiously, action!input is not a part of the framework I'm familiar 
with.  Can you point me to some docs that describe it?

> It might be interesting to discuss some elegant, one-method purist
> alternatives that address input preparation without using method
> invocation.

Again, not one *method*.  That'd be crazy!  But one action *class* per 
action with that action class only implementing "framework" methods: 
execute, prepare, validate (if not using xml-validation), etc.

Sorry if I wasn't clear or am still not getting something.

- Gary

---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
For additional commands, e-mail: user-help@struts.apache.org