Re: Make Struts set form data onto the action in same order as the form's fields

2007-01-26 Thread Célio Cidral Junior

Hi Chris,

2007/1/25, Christopher Schultz <[EMAIL PROTECTED]>:

I agree with Dave: you're trying to do too much in your forms.


I disagree. There are two options that I consider acceptable for me.
One of them is to write getters and setters for each form's field
(just like a form bean). The other one is to write a getter for a
domain bean (like getCustomer(), in the given example) and make the
form read and write values from that bean via OGNL. Indeed, writing
only one getter is much less work than writing a bunch of getters and
setters for each form's field, specially when the form has a large
number of fields. However, there's a semantic dependency between
parameter settings (the customer's id must be set before any other
parameter). As it's not possible to guarantee the ordering of the
parameter setting in a "clean" way, I'm going to stick with the first
option.

Thanks to all for the help/support/suggestions/patience!  ;-)

Célio.

-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]



Re: Make Struts set form data onto the action in same order as the form's fields

2007-01-25 Thread Christopher Schultz
-BEGIN PGP SIGNED MESSAGE-
Hash: SHA1

Célio,

Célio Cidral Junior wrote:
> The problem happens when the user
> is *altering* an existing customer (creating a new customer works
> fine), more specifically when the user is submitting changes from the
> form to an existing customer object (alongside with an existing id);
> in that case, the id must be set before getCustomer() is called,
> otherwise a new customer will be created with zero id. Loading the
> form with an existing customer works fine. Submitting changes to it is
> where the problem resides. The idea behind getCustomer() is to
> abstract the retrieving of the customer object wherever it's called
> along the action's code so that I don't have to care about whether
> it's an existing customer or not.

I agree with Dave: you're trying to do too much in your forms. You
should try to stick to a form bean that does nothing other than shuttle
data to and from the form. Your action should be invoking database
fetches and things of that nature, copying the form data from the form
bean to your DAOs, etc.

I think you're doing too much at once, and paying the price for it.

- -chris

-BEGIN PGP SIGNATURE-
Version: GnuPG v1.4.6 (MingW32)
Comment: Using GnuPG with Mozilla - http://enigmail.mozdev.org

iD8DBQFFuRdK9CaO5/Lv0PARAvrCAJ49E8WINtd8vt6wfKbXfHcIhUK/zQCeNHWI
Y+X+A0efqwOtHftlT54uj8M=
=P8ks
-END PGP SIGNATURE-

-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]



Re: Make Struts set form data onto the action in same order as the form's fields

2007-01-25 Thread Tom Schneider

I think your best bet would be to break up the parameter setting into 2
parts.  (A variation on the paramsPrepareParamsStack) The first part would
set all parameters needed to load the data from the data.  Then in the
prepare, you would have the id's needed to load the data from the database.
The next part would set all the rest of the parameters.  This would be the
approach I would take if I needed to load something from the database before
the parameters are set.
Tom

On 1/25/07, Dale Newfield <[EMAIL PROTECTED]> wrote:


Célio Cidral Junior wrote:
> Well, having Struts passing parameters in the order defined by the
> html form would solve my problem.  :-)

While setting parameters in a request struts has no idea what order they
were ordered in the originally generated form--remember that a single
action may be called from multiple forms on multiple pages that all
order the fields differently.  All struts has to work with is the order
in which the fields are present in the request, which is going to be
different for requests coming from different browsers, going through
different proxies, etc.

If you want to guarantee the order in which parameters are pulled from
the request, don't use the parameters interceptor and do all that
processing yourself in your action.  If you want to use the parameters
interceptor, but you want to ensure that a model object is loaded before
  parameters are set, either explicitly pull the key parameter out of
the request during the prepare call (using prepare in the stack before
parameters), or simply use the parameters interceptor both before and
after the prepare interceptor.

Believe us, you're not the first person to have this problem.  Believe
us, this is the simplest solution from among those that are not broken.

-Dale


-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]




Re: Make Struts set form data onto the action in same order as the form's fields

2007-01-25 Thread Dale Newfield

Célio Cidral Junior wrote:

Well, having Struts passing parameters in the order defined by the
html form would solve my problem.  :-)


While setting parameters in a request struts has no idea what order they 
were ordered in the originally generated form--remember that a single 
action may be called from multiple forms on multiple pages that all 
order the fields differently.  All struts has to work with is the order 
in which the fields are present in the request, which is going to be 
different for requests coming from different browsers, going through 
different proxies, etc.


If you want to guarantee the order in which parameters are pulled from 
the request, don't use the parameters interceptor and do all that 
processing yourself in your action.  If you want to use the parameters 
interceptor, but you want to ensure that a model object is loaded before 
 parameters are set, either explicitly pull the key parameter out of 
the request during the prepare call (using prepare in the stack before 
parameters), or simply use the parameters interceptor both before and 
after the prepare interceptor.


Believe us, you're not the first person to have this problem.  Believe 
us, this is the simplest solution from among those that are not broken.


-Dale


-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]



Re: Make Struts set form data onto the action in same order as the form's fields

2007-01-25 Thread Célio Cidral Junior

2007/1/25, Tom Schneider <[EMAIL PROTECTED]>:

Unfortunately I don't think that's possible.  The parameters get put into a
map structure, so the original parameter order is lost by the time it gets
to the servlet API.  We've run into several instances where something will
work on one app server, but break on another because we had duplicate
parameters on the url--so depending on how the app server handled it, we
would get one or the other value.  I can't imagine that any java web
framework could do this successfully.


That's sad!  :-(

Célio.

-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]



Re: Make Struts set form data onto the action in same order as the form's fields

2007-01-25 Thread Tom Schneider

Unfortunately I don't think that's possible.  The parameters get put into a
map structure, so the original parameter order is lost by the time it gets
to the servlet API.  We've run into several instances where something will
work on one app server, but break on another because we had duplicate
parameters on the url--so depending on how the app server handled it, we
would get one or the other value.  I can't imagine that any java web
framework could do this successfully.
Tom

On 1/25/07, Célio Cidral Junior <[EMAIL PROTECTED]> wrote:


2007/1/25, Tom Schneider <[EMAIL PROTECTED]>:
> This is an issue with the typical edit/save scenario.  The problem we
are
> discussing is that the domain model is needed in some form before the
> parameter can be repopulated from the form save.  The technique you are
> using is to reread the data from the database before the parameters are
> set.  An alternative technique would be to put the domain model into a
place
> in the session--so on the save, you can retrieve the the model from the
> session and then allow the parameters interceptor to populate the new
data.
> (This is referred to as detached objects in the Hibernate world)  The
> advantage of putting the model in the session is that if some else
modifies
> the data before you reread the data, but after you have displayed the
edit
> page, you will not have the original model.  This particularly a problem
> with a model where you are dealing with lists of domain objects.  In
this
> case, the edit will fail because you will be trying to set parameters on
> items that might not exist anymore.  (Or you've pulled in data that the
user
> doesn't know about)  Therefore the safer technique is to save off the
> model.  If you're concerned about putting too much into the session, you
can
> store the data in a cache, such as ehcache, that will store items to
disk if
> there are too many things in memory.  (This is the technique that we
> used--we called it a model repository and we created a couple different
> implementations)  I would love to see something like this out-of-the-box
> with struts2, but nothing currently exists.

Thanks, I really appreciate your suggestions. However, I prefer a
stateless approach because (I think) it helps to keep things simple in
this case. Using some kind of cache between page requests is more like
a stateful approach that I would like to avoid here for simplicity
reasons.

Well, having Struts passing parameters in the order defined by the
html form would solve my problem.  :-)

Regards,

Célio.

-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]




Re: Make Struts set form data onto the action in same order as the form's fields

2007-01-25 Thread Célio Cidral Junior

2007/1/25, Tom Schneider <[EMAIL PROTECTED]>:

This is an issue with the typical edit/save scenario.  The problem we are
discussing is that the domain model is needed in some form before the
parameter can be repopulated from the form save.  The technique you are
using is to reread the data from the database before the parameters are
set.  An alternative technique would be to put the domain model into a place
in the session--so on the save, you can retrieve the the model from the
session and then allow the parameters interceptor to populate the new data.
(This is referred to as detached objects in the Hibernate world)  The
advantage of putting the model in the session is that if some else modifies
the data before you reread the data, but after you have displayed the edit
page, you will not have the original model.  This particularly a problem
with a model where you are dealing with lists of domain objects.  In this
case, the edit will fail because you will be trying to set parameters on
items that might not exist anymore.  (Or you've pulled in data that the user
doesn't know about)  Therefore the safer technique is to save off the
model.  If you're concerned about putting too much into the session, you can
store the data in a cache, such as ehcache, that will store items to disk if
there are too many things in memory.  (This is the technique that we
used--we called it a model repository and we created a couple different
implementations)  I would love to see something like this out-of-the-box
with struts2, but nothing currently exists.


Thanks, I really appreciate your suggestions. However, I prefer a
stateless approach because (I think) it helps to keep things simple in
this case. Using some kind of cache between page requests is more like
a stateful approach that I would like to avoid here for simplicity
reasons.

Well, having Struts passing parameters in the order defined by the
html form would solve my problem.  :-)

Regards,

Célio.

-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]



Re: Make Struts set form data onto the action in same order as the form's fields

2007-01-25 Thread Tom Schneider

This is an issue with the typical edit/save scenario.  The problem we are
discussing is that the domain model is needed in some form before the
parameter can be repopulated from the form save.  The technique you are
using is to reread the data from the database before the parameters are
set.  An alternative technique would be to put the domain model into a place
in the session--so on the save, you can retrieve the the model from the
session and then allow the parameters interceptor to populate the new data.
(This is referred to as detached objects in the Hibernate world)  The
advantage of putting the model in the session is that if some else modifies
the data before you reread the data, but after you have displayed the edit
page, you will not have the original model.  This particularly a problem
with a model where you are dealing with lists of domain objects.  In this
case, the edit will fail because you will be trying to set parameters on
items that might not exist anymore.  (Or you've pulled in data that the user
doesn't know about)  Therefore the safer technique is to save off the
model.  If you're concerned about putting too much into the session, you can
store the data in a cache, such as ehcache, that will store items to disk if
there are too many things in memory.  (This is the technique that we
used--we called it a model repository and we created a couple different
implementations)  I would love to see something like this out-of-the-box
with struts2, but nothing currently exists.
Tom


On 1/25/07, Célio Cidral Junior <[EMAIL PROTECTED]> wrote:


2007/1/25, Dave Newton <[EMAIL PROTECTED]>:
> From my point of view it seems like your implementation is broken: if
you need to create a Customer from an ID passed via a form or URL then you
either need to implement Preparable or do the DAO operations in the (in your
case) input or save methods.

The DAO operations already do that. The problem happens when the user
is *altering* an existing customer (creating a new customer works
fine), more specifically when the user is submitting changes from the
form to an existing customer object (alongside with an existing id);
in that case, the id must be set before getCustomer() is called,
otherwise a new customer will be created with zero id. Loading the
form with an existing customer works fine. Submitting changes to it is
where the problem resides. The idea behind getCustomer() is to
abstract the retrieving of the customer object wherever it's called
along the action's code so that I don't have to care about whether
it's an existing customer or not.

Implementing Preparable does not seem to solve the problem because the
parameters are set before the prepare() method is invoked.

Célio.

-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]




Re: Make Struts set form data onto the action in same order as the form's fields

2007-01-25 Thread Célio Cidral Junior

2007/1/25, Dale Newfield <[EMAIL PROTECTED]>:

Célio Cidral Junior wrote:
> Implementing Preparable does not seem to solve the problem because the
> parameters are set before the prepare() method is invoked.

Which is needed in order to know which object to retrieve from the DB.


I think you have not read the code I included in the first email.
Please, read it carefully and you will understand why Preparable
doesn't solve my problem.


This model usually includes including the parameters interceptor twice:
  Once before prepare and once after.


I can't figure out how that would be useful in my case.

Célio.

-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]



Re: Make Struts set form data onto the action in same order as the form's fields

2007-01-25 Thread Dale Newfield

Célio Cidral Junior wrote:

Implementing Preparable does not seem to solve the problem because the
parameters are set before the prepare() method is invoked.


Which is needed in order to know which object to retrieve from the DB.
This model usually includes including the parameters interceptor twice: 
 Once before prepare and once after.


-Dale


-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]



Re: Make Struts set form data onto the action in same order as the form's fields

2007-01-25 Thread Célio Cidral Junior

2007/1/25, Dave Newton <[EMAIL PROTECTED]>:

From my point of view it seems like your implementation is broken: if you need 
to create a Customer from an ID passed via a form or URL then you either need 
to implement Preparable or do the DAO operations in the (in your case) input or 
save methods.


The DAO operations already do that. The problem happens when the user
is *altering* an existing customer (creating a new customer works
fine), more specifically when the user is submitting changes from the
form to an existing customer object (alongside with an existing id);
in that case, the id must be set before getCustomer() is called,
otherwise a new customer will be created with zero id. Loading the
form with an existing customer works fine. Submitting changes to it is
where the problem resides. The idea behind getCustomer() is to
abstract the retrieving of the customer object wherever it's called
along the action's code so that I don't have to care about whether
it's an existing customer or not.

Implementing Preparable does not seem to solve the problem because the
parameters are set before the prepare() method is invoked.

Célio.

-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]



RE: Make Struts set form data onto the action in same order as the form's fields

2007-01-25 Thread Dave Newton
From: Célio Cidral Junior
>   public Customer getCustomer() {
>   if (customer == null)
>   customer = id != 0 ? dao.get(id) : new Customer();
>   return customer;
>   }
> [...]
> The way I built both the action and the view prevents me from writing
> a lot of extra code (like getters and setters for each of the form's
> field), and that's why I would like to know whether there's a way to
> make Struts follow the fields' ordering when submitting the data into
> the action. And if there's not, may the Struts dev team implement
> that, if possible.

That seems extremely unlikely, but they may have a different take on it. 

>From my point of view it seems like your implementation is broken: if you need 
>to create a Customer from an ID passed via a form or URL then you either need 
>to implement Preparable or do the DAO operations in the (in your case) input 
>or save methods.

IMO that functionality does *not* belong in a getter.

Dave

-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]



Make Struts set form data onto the action in same order as the form's fields

2007-01-25 Thread Célio Cidral Junior

Struts don't set the form data onto the Action in the same order in
which the fields appear in the form. For instance, suppose you have a
form like this:









And its corresponding Action, which is something like:

public class CustomerAction extends ActionSupport {
private int id = 0;
private Customer customer;
private CustomerDao dao;

public int getId() {
return id;
}

public void setId(int id) {
this.id = id;
}

public Customer getCustomer() {
if (customer == null)
customer = id != 0 ? dao.get(id) : new Customer();

return customer;
}

public String input() throws Exception {
if (getCustomer() == null)
return ERROR;

return INPUT;
}

public String save() throws Exception {
if (getCustomer() == null)
return ERROR;

dao.save(getCustomer());

return SUCCESS;
}
}

You could expected that Struts, when submitting the form, would first
set the id, then customer.name, then finally custumer.phoneNumber.
However, it does not follow that order; actually, it does set the data
in random order. In this case, the order is important because, if the
user is altering an existing customer, its id must be set before
getCustomer() gets invoked. Otherwise, the action will create a new
customer with zeroed id.

The way I built both the action and the view prevents me from writing
a lot of extra code (like getters and setters for each of the form's
field), and that's why I would like to know whether there's a way to
make Struts follow the fields' ordering when submitting the data into
the action. And if there's not, may the Struts dev team implement
that, if possible.

Regards,

Célio.

-
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]