I would like to know if it is possible, in Struts2, to map an HTML form's fields to those of an action, automatically, without getters and setters.
It is clear that by getters and setters or the ParameterAware interface and the Map, fields can be set in the action, but I just wanted to know if otherwise there was a way.
First, instead of thinking in terms of "with fields with getters and setters" you are advised to think in terms of "bean properties" here. Struts2 (and most java frameworks) think in that way, they usually don't care (and rightly so) whether those "properties" are real fields or not.
The short answer to your question is: no.
But be aware that Struts2 is very flexible - when I say "no" I mean "using the default interceptors". You could always write your own interceptor instead of the default to do that - bad idea IMO.
The interceptor that does that mapping is (basically) the parameters interceptor. From its documentation:
This interceptor gets all parameters
from ActionContext#getParameters() and
sets them on the value stack by
calling ValueStack#setValue(String, Object)
typically resulting in the values
submitted in a form request being
applied to an action in the value
stack.
And looking into ValueStack.setValue(String,Object) we read:
Attempts to set a property on a
bean in the stack with the given
expression using the default search
order.
So there you have.
ModelDriven was the correct choice :)
Related
I was wondering what the best practice is for model validation when it comes to using getters and setters. Specifically, I have nullable fields in my model that, in some use cases, should not have null values when accessed. In those cases, I would like to throw an exception from the getter, but is that an accepted practice?
This could also be the case if I received a value in a setter that was not valid.
Alternatively from throwing exceptions, I'm aware of MVC attributes that you can use to decorate fields, but have not used them very much for model validation. In the "This value shouldn't be null in my getter" scenario, is there an appropriate attribute I could use?
Also, if throwing exceptions in getters and setters is accepted, is there a recommended exception to throw, i.e. ValueNotValidException (if that were real)?
If you are going to use the object as a ViewModel you can annotate it with a [NotNullValidator] given by the Microsoft's Enterprise Library, as well as a bunch of others that give extra functionality like Regex validation, ranges, IgnoreNulls, type, etc, as shown here. It is also possible using this library to create custom validators, based on this step-by-step guide, which you can use to annotate your ViewModel.
Otherwise you are left with the more traditional MVC Data Annotation Attributes, like [Required].
You should use the standard Data Validation Attributes to validate the model. If the value is required - use [Required].
http://www.asp.net/mvc/tutorials/mvc-4/getting-started-with-aspnet-mvc4/adding-validation-to-the-model
if (ModelState.IsValid)
{
...
}
Less code maintain and improved readability.
When would be the bean tag used in struts.xml configuration file using Struts 2? What is difference between action class properties and bean tag in Struts 2 configuration file struts.xml?
Some places have strict separation of work or for what ever reason you can edit the view (JSP) but not the actions source.
In this case the bean tag becomes most useful (otherwise I agree it isn't particularly attractive). It is generally easiest to produce what is needed for the view within the action and also process that data such that it is readily displayable. As such there is not generally much need for append, generator, merge tags either... but once again if you consider the content people separate from the backend people these tags would be used more often.
In theory it is possible to use the bean tag to access things like singletons for counters and such, but if the view is acquiring resources in this way it is kind of a component way of thinking(as opposed to action based thinking). This is also why the action tag's use isn't particularly favored either. If you need it, the action class should be the main one responsible for getting it (or interceptors, but certainly not the view) at least following action based thinking.
Is it possible to assign the value to the bean property by implementing ModelDriven interface but having different name in request and bean
for eg Ajax request
DemoStruts.Action?param_a=649
the value of param_a parameter must set to the property paramAR in the bean. For doing this is there any xml configuration or annotation to specify this mapping
The normal mechanism is the alias interceptor, although I haven't used it for deep aliasing.
There are some pretty hideous games you can play with this technique. I've never been entirely sure if it's a good idea or not, though; another option is to just map parameters manually in the action itself. This is often easier to understand.
After adding a s:checkbox to my form, I get OGNL errors in the ParamsInterceptor:
WARN [OgnlValueStack] Error setting expression '__checkbox_filter.findRejected' with value '[Ljava.lang.String;#dc926f'
ognl.OgnlException: target is null for setProperty(null, "findRejected", [Ljava.lang.String;#dc926f)
I am aware that the extra hidden field with underscores in its name (__checkbox_filter.findRejected) was correctly added by Struts2.
I don't understand, however, why the ParametersInterceptor is trying to set this property, that was added by Struts2, on my Action (which obviously doesn't contain a '__checkbox_filter' property).
It is normal to see this OGNL error coming from with Struts2 checkboxes? How can I avoid it?
I've just stumble across the very same problem.
You need to place the Checkbox Interceptor BEFORE the Parameters Interceptor in your interceptor stack.
This is the case by default, so I guess that you're using a custom stack...
Most of the time the mistake in such cases is that we forget to write getters and setters for the attributes. So check whether the getters and setters are at their place.
I am trying to make a taglib to represent an object (to read and display at the UI). When creating an object (save method in the controller), I see the domain class and association are created by the auto assignment of parameter
def Book = new Book(params)
It also maps complex types (for eg: joda time). I wonder about the naming convention necessary to facilitate this mapping. Out of curiosity, can someone also point where in the grails source code I could see how grails handles this mapping. I'm still learning Spring and probably this would be a good exercise.
Thanks,
Babu.
AFAIK the naming conventions are rather straightforward. If there's a field params.foo and the object you are binding to has a field foo, it will bind the value, assuming the type conversion works properly. If there's a params.bar.id set with an Long value and your object has a complex property of type Bar, it will lookup this instance and inject it.
If you need more control over the binding process, you might want to use bindData.
If you are interested into the details of the binding process, have a look at Java's PropertyEditor as this is what is being used in the background. I wrote a blog post on how to create and register PropertyEditors a while ago, maybe it helps you getting started with that stuff.