Using the f attribute: inside a composite component

we have (in our oppinion) a very simple scenario. But we somehow got stuck on the composite components and attribute tags f :. I will try to make the code as simple as possible.

Compound component:

<cc:interface name="button"> ... <cc:attribute name="actionListener" required="true" method-signature="void f(javax.faces.event.ActionEvent)" target="button" shortDescription="The action listener for this button." /> ... </cc:interface> <cc:implementation> <ice:commandButton ... actionListener="#{cc.attrs.actionListener}" ...> <cc:insertChildren /> </ice:commandButton> </cc:implementation> 

... now we use this component as follows:

 <ctrl:button ... actionListener="#{bean.method}" ...> <f:attribute name="objectId" value="#{someObject.id}" /> </ctrl:button> 

Now we need to access the "objectId" attribute inside the action listener method. We have already tried something like this:

 public void method(ActionEvent event) { ... event.getComponent().getAttributes().get("objectId"); ... } 

But the attribute map does not contain objectId. Is there something wrong with this approach? What is the recommended way to solve this problem?

It would be nice if someone helped us.

Thanks! Slimshady

+4
source share
2 answers

This <f:attribute> hack remains aloof from JSF 1.0 / 1.1 when it is not possible to pass objects as additional arguments to command buttons / links. With JSF 1.2, you should use <f:setPropertyActionListener> for this.

 <ctrl:button action="#{bean.method}"> <f:setPropertyActionListener target="#{bean.objectId}" value="#{someObject.id}" /> </ctrl:button> 

Since EL 2.2 (which is a standard part of Servlet 3.0, but for Servlet 2.5 is implemented using JBoss EL ), you can instead pass the entire object in the same way as the method argument:

 <ctrl:button action="#{bean.method(someObject.id)}" /> 
+5
source

I was able to read the attribute passed to cc in the next setup.

 <test:inner> <f:attribute name="fAttribute" value="myAttributeValue" /> </test:inner> 

 <cc:implementation> <h:commandButton value="button" actionListener="#{testBean.actionListener}" > <f:attribute name="innerAttribute" value="innerAttributeValue" /> <cc:insertChildren /> <!-- not necessary, I hoped it would pass the outer attribute ---> </h:commandButton> </cc:implementation> 

 public void actionListener(ActionEvent event) { event.getComponent().getNamingContainer().getAttributes().get("fAttribute") // > myAttributeValue event.getComponent().getAttributes().get("innerAttribute") // > innerAttributeValue } 

The trick was to search in the button names container. Thus, cc is always a named container, you can be sure that you will get into the internal component.

I'm not sure if that was the way it was intentional, but as I understand it, naming smoothing collects such attributes for its children.

Q: Does anyone know if not passing attributes to the button is considered an error in Mojarra / JSF?

+3
source

Source: https://habr.com/ru/post/1393343/


All Articles