4

I have been working on JSF2 with Jquery for a while. I have an issue with populating hidden fields using JSF2. I know it can be done like this

<h:inputHidden id="a" value="#{backingBean.a} />

This works fine but the only thing is I need to create getter and setter for 'a' in my backing bean. But I want to call a backing bean method by passing another parameter, this will return me an output value that has to be set in the 'inputHidden'. I tried using like this

<h:inputHidden id="a" value="#{backingBean.populateA(b)} />

But, this code gives me a warning on my browser console saying the usage is incorrect. I understand backing bean methods with parameters should be called within 'action' attributes like in <h:commandButton>. How can I use something for hidden fields using JSF2 or even Jquery?

Please note that I need this input hidden field to be populated on page load. Not sure if it can be done.

Thanks for your time in advance.

BalusC
  • 1,082,665
  • 372
  • 3,610
  • 3,555
IndoKnight
  • 1,846
  • 1
  • 21
  • 29
  • 1
    When you are binding something to value of some input, than JSF will call both getter and setter for that field. If this would be possible what you are trying to do, what do you think how JSF will set value when form is submitted? – partlov Apr 09 '13 at 08:26
  • Thanks for the reply.I understand how JSF works. I was asking how something I described can be done in JSF2. – IndoKnight Apr 09 '13 at 08:30

2 Answers2

1

Use a hidden command button to pass the value to method

<h:commandButton value="Print" id="someButton" style="visibility: hidden;"
                    action="#{backingBean.populateA(b)}">
  <f:ajax execute="@this" render="a"/>
</h:commandButton>

and a hidden input to receive the output

<h:inputHidden id="a" value="#{backingBean.a} />

use jQuery to click the button when a desired event is fired.

Johny T Koshy
  • 3,857
  • 2
  • 23
  • 40
  • Thanks for the reply. I see your solution works but I'm not inclined on simulating button clicks which otherwise could have been straight forward. +1 for seeing this as an other alternative. – IndoKnight Apr 09 '13 at 10:18
1

Elaboration on the subject

All of the tags that are designed to serve as 'value holders', i.e. tags like <h:inputText> or <h:selectOneMenu>, are backed up by UIInput classes that implement a EditableValueHolder interface. During Apply request values phase the user submitted values are extracted from request parameters and are set as submitted values of the appropriate component class by UIInput#setSubmittedValue. If necessary, the values are converted beforehand by using Converter#getAsObject.

Next, every 'value holder' component provides for a value attribute, which is bidirectionally binding the value of the component with the property of the backing bean. For example, when the binding is of the form value="#{bean.prop}", then bean.getProp() is called when component value need to be updated from a bean property and bean.setProp(value) is called with value derived from UIInput#getValue() when model values are to be updated during Update model values phase.

All in all, UIInput components require a bidirectional binding with a bean property via value attribute of the appropriate JSF tag and this binding provides for access of data in the model tier via a value expression. This leaves us with value bindings of the form value="#{bean.prop}" type.

Population of properties based on some method

How when you want to populate your bean properties not with the straight user-submitted values, but with the values modified by some method you are basically left with the following:

  1. Provide for a Converter and do a one-to-one mappings between bean properties and component values in Converter#getAsObject and Converter#getAsString. Don't forget to specify your converter in, for example, converter attribute of your tag. As a usual point of reference, you can consult Communication in JSF 2.0;
  2. Do the converter-type transformations in a getter/setter pair, like in public String getProp(String s) { return modifyPropValue(this.prop); } and public void setProp(String s) { this.prop = modifyCompValue(s); }. I would though strongly discourage to do that;
  3. Do the transformation in an action(listener) method during form submission. For this you can have a dummy binding with dummyProp bean property and do the this.prop = modifyCompValue(dummyProp) in your action(listener) method. You can also note that having a dummy roperty is redundant and you can access the necessary request parameter via FacesContext.getCurrentInstance().getExternalContext().getRequestParameterMap().get("id"). Actually, the solution proposed in another answer is a special case of this transformation where the only thing in action method is population of converted value.
skuntsel
  • 11,624
  • 11
  • 44
  • 67
  • If these are really speculations you should have posted them as questions, not answers. If they are facts you shouldn't label them as speculations. – user207421 Apr 09 '13 at 22:55
  • @EJP You've made a good point, but I meant discussion, or elaboration instead of theorizing on the grounds of disputable premises, of course. Though, if I were you I would've edited that line straight away instead of commenting. Thanks anyway! – skuntsel Apr 10 '13 at 17:21