You are viewing a plain text version of this content. The canonical link for it is here.
Posted to user@struts.apache.org by "J. Garcia" <jo...@gmail.com> on 2012/05/23 20:34:10 UTC

conversion error repopulation not working

Hi,

In order to implement a good user experience, I am trying to put into
practice the conversion validator, as documented here:

http://struts.apache.org/2.3.3/docs/conversion-validator.html

The ideal would be: a form with one integer field. If the user enters a non
valid integer, the value remains in the input field and the user is
informed of the error like this:
Invalid value '198o' for field 'Year'. (notice the letter at the end).

For this, I declare the conversion-validator, and have to remove the
conversionError from the interceptors stack.
While debugging, the class ConversionErrorFieldValidator builds a map, with
the full fieldName and the entered value.
The method repopulateField from
RepopulateConversionErrorFieldValidatorSupport is run, which in theory
repopulates the stack with this code:

            if (doExprOverride) {
                invocation.addPreResultListener(new PreResultListener() {
                    public void beforeResult(ActionInvocation invocation,
String resultCode) {
                        ValueStack stack =
ActionContext.getContext().getValueStack();
                        stack.setExprOverrides(fakeParams);
                    }
                });
            }

However, when showing the jsp for user input, the invalid value is not in
the form input field. It does not seem to work as documented in the
mentioned url.

Cheers,
J.

Re: conversion error repopulation not working

Posted by Łukasz Lenart <lu...@googlemail.com>.
I'll add this code as an additional example, but I'm wondering is it a
good way to base on fieldErrors as they can be also populated by
validators.
Maybe adding ConversionAware interface with specific method to
populate conversionErrors<FiledName, Message> would be better ?

Then I could extend ActionSupport with getFormatted() but base on
conversionErrors instead. WDYT ?


Regards
-- 
Łukasz
mobile +48 606 323 122 http://www.lenart.org.pl/
Warszawa JUG conference - Confitura http://confitura.pl/

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


Re: conversion error repopulation not working

Posted by "J. Garcia" <jo...@gmail.com>.
This works nicely.
Thanks!

Cheers,
J.

On Thu, May 31, 2012 at 3:07 PM, Łukasz Lenart <lukasz.lenart@googlemail.com
> wrote:

> Can be reduced to this:
>
> public String getFormatted(String key, String fieldName, List<?> args) {
>       if (getFieldErrors().isEmpty()) {
>           return getText(key, args);
>       } else {
>           return
> ActionContext.getContext().getValueStack().findString(defaultValue);
>       }
> }
>
> and it works just for one field ;-) There should check if there is a
> error for given fieldName
>
>
> Regards
> --
> Łukasz
> mobile +48 606 323 122 http://www.lenart.org.pl/
> Warszawa JUG conference - Confitura http://confitura.pl/
>

Re: conversion error repopulation not working

Posted by Łukasz Lenart <lu...@googlemail.com>.
Can be reduced to this:

public String getFormatted(String key, String fieldName, List<?> args) {
       if (getFieldErrors().isEmpty()) {
           return getText(key, args);
       } else {
           return
ActionContext.getContext().getValueStack().findString(defaultValue);
       }
}

and it works just for one field ;-) There should check if there is a
error for given fieldName


Regards
-- 
Łukasz
mobile +48 606 323 122 http://www.lenart.org.pl/
Warszawa JUG conference - Confitura http://confitura.pl/

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


Re: conversion error repopulation not working

Posted by Łukasz Lenart <lu...@googlemail.com>.
2012/5/31 J. Garcia <jo...@gmail.com>:
> The short-circuiting option sounds good. There could even be a specially
> dedicated getText() (or alternative method name) for this scenario, which
> should be rather frequent in l10n apps.

Not the best solution, but works:

<s:textfield key="user.born" value="%{getFormatted('format.number',
'user.born', {user.born})}" />

and in ExampleAction (or any other base action class):

    public String getFormatted(String key, String defaultValue, List<?> args) {
        TextProviderFactory tpf = new TextProviderFactory();
        if (container != null) {
            container.inject(tpf);
        }
        TextProvider tp = tpf.createInstance(getClass(), this);
        if (getFieldErrors().isEmpty()) {
            return tp.getText(key, args);
        } else {
            return
ActionContext.getContext().getValueStack().findString(defaultValue);
        }
    }


Regards
-- 
Łukasz
mobile +48 606 323 122 http://www.lenart.org.pl/
Warszawa JUG conference - Confitura http://confitura.pl/

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


Re: conversion error repopulation not working

Posted by Łukasz Lenart <lu...@googlemail.com>.
2012/5/31 Łukasz Lenart <lu...@googlemail.com>:
> Ok, looks like a problem is with getText() in jsp but I think there is
> no other way ... you can use String instead and check for errors in
> getter/setter but I'm not sure if it does the trick

The problem is a bit complicated here as getText(String key, String[]
args) accepts only strings, so getText("format.number", {user.born})
is converted to call getText("{0,number,#,##0.#}", String[]{"1980"}) -
notice that all params are Strings - and then MessageFormat throws
exception as it cannot format String as a Number.

Right now I don't see any bright solution, I think there should be a
short-circuit when conversion error occurs to  skip evaluating
getText() expression and just return what was specified as a key /
name property.


Regards
-- 
Łukasz
mobile +48 606 323 122 http://www.lenart.org.pl/
Warszawa JUG conference - Confitura http://confitura.pl/

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


Re: conversion error repopulation not working

Posted by Łukasz Lenart <lu...@googlemail.com>.
2012/5/31 J. Garcia <jo...@gmail.com>:
> Ok. Sorry.
> Fixed the example to match the real situation. Prepare() will only execute
> now if the request is a get method.

Ok, looks like a problem is with getText() in jsp but I think there is
no other way ... you can use String instead and check for errors in
getter/setter but I'm not sure if it does the trick


Regards
-- 
Łukasz
mobile +48 606 323 122 http://www.lenart.org.pl/
Warszawa JUG conference - Confitura http://confitura.pl/

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


Re: conversion error repopulation not working

Posted by "J. Garcia" <jo...@gmail.com>.
Ok. Sorry.
Fixed the example to match the real situation. Prepare() will only execute
now if the request is a get method.

Cheers,
Josep


On Wed, May 30, 2012 at 3:45 PM, Łukasz Lenart <lukasz.lenart@googlemail.com
> wrote:

> 2012/5/29 J. Garcia <jo...@gmail.com>:
> > Attached an example, generated from struts2 archetype and modified to
> > reproduce the situation.
> >
> > - run with mvn jetty:run. I use maven 2.2.1.
> > - on browser, type: localhost:8080/struts-test/example/Login
> > - you'll see a form, with formatted integer.
> > - modify the integer like this: AAA
> > - submit. An error msg informing of conversion error is shown. However,
> the
> > value AAA is not maintained. Instead, the current bean value is shown.
>
> But you use Preparable each time, and prepare overrides what was sent
> by user. I'm not sure if I understood that correctly but the same
> works fine in showcase application.
>
>
> Regards
> --
> Łukasz
> mobile +48 606 323 122 http://www.lenart.org.pl/
> Warszawa JUG conference - Confitura http://confitura.pl/
>

Re: conversion error repopulation not working

Posted by Łukasz Lenart <lu...@googlemail.com>.
2012/5/29 J. Garcia <jo...@gmail.com>:
> Attached an example, generated from struts2 archetype and modified to
> reproduce the situation.
>
> - run with mvn jetty:run. I use maven 2.2.1.
> - on browser, type: localhost:8080/struts-test/example/Login
> - you'll see a form, with formatted integer.
> - modify the integer like this: AAA
> - submit. An error msg informing of conversion error is shown. However, the
> value AAA is not maintained. Instead, the current bean value is shown.

But you use Preparable each time, and prepare overrides what was sent
by user. I'm not sure if I understood that correctly but the same
works fine in showcase application.


Regards
-- 
Łukasz
mobile +48 606 323 122 http://www.lenart.org.pl/
Warszawa JUG conference - Confitura http://confitura.pl/

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


Re: conversion error repopulation not working

Posted by "J. Garcia" <jo...@gmail.com>.
Attached an example, generated from struts2 archetype and modified to
reproduce the situation.

- run with mvn jetty:run. I use maven 2.2.1.
- on browser, type: localhost:8080/struts-test/example/Login
- you'll see a form, with formatted integer.
- modify the integer like this: AAA
- submit. An error msg informing of conversion error is shown. However, the
value AAA is not maintained. Instead, the current bean value is shown.

Cheers,
J.




On Tue, May 29, 2012 at 2:37 PM, Łukasz Lenart <lukasz.lenart@googlemail.com
> wrote:

> 2012/5/29 J. Garcia <jo...@gmail.com>:
> > Integer.
>
> Strange, should work. Could you post an example code ?
>
>
> Regards
> --
> Łukasz
> mobile +48 606 323 122 http://www.lenart.org.pl/
> Warszawa JUG conference - Confitura http://confitura.pl/
>

Re: conversion error repopulation not working

Posted by Łukasz Lenart <lu...@googlemail.com>.
2012/5/29 J. Garcia <jo...@gmail.com>:
> Integer.

Strange, should work. Could you post an example code ?


Regards
-- 
Łukasz
mobile +48 606 323 122 http://www.lenart.org.pl/
Warszawa JUG conference - Confitura http://confitura.pl/

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


Re: conversion error repopulation not working

Posted by "J. Garcia" <jo...@gmail.com>.
Integer.

On Mon, May 28, 2012 at 10:04 AM, Łukasz Lenart <
lukasz.lenart@googlemail.com> wrote:

> Is it int either Integer ?
>
>
> Regards
> --
> Łukasz
> mobile +48 606 323 122 http://www.lenart.org.pl/
> Warszawa JUG conference - Confitura http://confitura.pl/
>

Re: conversion error repopulation not working

Posted by Łukasz Lenart <lu...@googlemail.com>.
Is it int either Integer ?


Regards
-- 
Łukasz
mobile +48 606 323 122 http://www.lenart.org.pl/
Warszawa JUG conference - Confitura http://confitura.pl/

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


Re: conversion error repopulation not working

Posted by "J. Garcia" <jo...@gmail.com>.
Thanks Lukasz for your reply.

While preparing a minimal example, I got the reason of it all.

The real situation is:
 - The input form has an int field
 - The value already available should be formatted and localized: 43,000 /
43.000
 - In order to achive l10n, the input field tag is like this:

    <s:textfield key="mybean.value" required="false"
value='%{getText("number.format",{mybean.value})}'/>

In such a situation, the TextProviderHelper.getText() method is run, which
obtains the value from the bean, rather than obtaining it from the wrong
user input which was not possible to convert into the bean.

It would be nice if there was a specific method which would check if the
value to obtain is from an input field with conversion error. In such a
case, it would obtain the value from the user input. If no error, the value
would be from the bean.

Does it make sense?

Cheers,
J.


On Thu, May 24, 2012 at 8:10 AM, Łukasz Lenart <lukasz.lenart@googlemail.com
> wrote:

> Could you add some code example ?
>
>
> Regards
> --
> Łukasz
> mobile +48 606 323 122 http://www.lenart.org.pl/
> Warszawa JUG conference - Confitura http://confitura.pl/
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: user-unsubscribe@struts.apache.org
> For additional commands, e-mail: user-help@struts.apache.org
>
>

Re: conversion error repopulation not working

Posted by Łukasz Lenart <lu...@googlemail.com>.
Could you add some code example ?


Regards
-- 
Łukasz
mobile +48 606 323 122 http://www.lenart.org.pl/
Warszawa JUG conference - Confitura http://confitura.pl/

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