JSF2 EL html output - jsf

Background
I have an existing web application that relies on JSF2. In most pages, there are expressions that output text from various property files. Some properties might contain html. However, JSF expressions escape html into plain text. The solution I found was to use <h:outputText> with escape set to false. Using this would be cumbersome due to amount of expressions that would need to be wrapped.
Question
My question is, is there a way to configure all expressions to not escape html?

If I were you I would create my own composite component wich can be called In xhtml with
<myComponents:outputText value="<STRONG>the html taged value</STRONG>">
Simply add this custom component in a new xhtml file in the defaut jsf folder src/webapp/components.
Like :
src/webapp/components/myComponents/outputText.xhtml
<!DOCTYPE composition PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<ui:composition xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:c="http://java.sun.com/jsp/jstl/core"
xmlns:cc="http://java.sun.com/jsf/composite">
<cc:interface>
<cc:attribute name="value" required="true"/>
</cc:interface>
<cc:implementation>
<h:outputText value="#{cc.attrs.value}" escape="false"/>
</cc:implementation>
</ui:composition>
Don't forget to add the folowwing namespace in your xhtml pages where the components are used xmlns:field="http://java.sun.com/jsf/composite/components/myComponents in the ui:composition tag
Hope this helps...

Related

ui:include includes wrong file in JSF 2.2

Accorrding to the documentation of ui:include tag
Use this tag—which is very similar to JSP's jsp:include—to encapsulate
and reuse content among multiple XHTML pages. There are three things
this tag can include: plain XHTML, and XHTML pages that have either a
composition tag or a component tag.
You supply a filename, through ui:include's src attribute for JSF to
include. That filename is relative to the XHTML file that was rendered
as a result of the last request. So, for example, if JSF loaded the
view login.xhtml, and that file included pageDecorations/header.xhtml,
and pageDecorations/header.xhtml included companyLogo.xhtml, then
companyLogo.xhtml will not be found if it's in the pageDecorations
directory, because companyLogo.xhtml has to be in the same directory
as login.xhtml.
I created a simple test:
webapp/login.xhtml
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:h="http://java.sun.com/jsf/html">
<h:body>
<ui:include src="pageDecorations/header.xhtml" />
</h:body>
</html>
webapp/pageDecorations/header.xhtml
<ui:include
src="logo.xhtml"
xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://xmlns.jcp.org/jsf/facelets"
/>
webapp/pageDecorations/logo.xhtml
<h:outputText
value="Logo in /pageDecorations"
xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
/>
webapp/logo.xhtml
<h:outputText value="Logo in /"
xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
/>
When I ran this test (loaded login.xhtml page) using JSF 2.2 on WildFly 10.1 , I got Logo in /pageDecorations, while according to the documentation it should be: Logo in /
What is wrong ? Is there a bug in the documentation or Mojarra implementation ? Or my understanding is wrong ?
First, you are inside webapp/ and executing webapp/login.xhtml
inside that you get src="pageDecorations/header.xhtml" and for exectuing that you are in pageDecorations and from header.xhtml you are tring to find src="logo.xhtml" which will you get in the same directory (pageDecorations) so it will print
"Logo in /pageDecorations" .
Document looks wrong in this case.

Parameter always null on ui:composite xhtml page [duplicate]

I have a simple JSF 2.0 composite component example.
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:cc="http://java.sun.com/jsf/composite"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:f="http://java.sun.com/jsf/core">
<head>
<title>
A panel box component
</title>
</head>
<body>
<cc:interface>
<cc:attribute name="model" required="true" type="at.test.Person"/>
</cc:interface>
<cc:implementation>
<h:inputText value="#{model.vorname}">
</h:inputText>
</cc:implementation>
</body>
And here is my JSF test page:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:mc="http://java.sun.com/jsf/composite/mygourmet" >
<h:body>
<h:form>
<mc:inputTest model="#{person}">
</mc:inputTest>
<h:commandButton value=""/>
<h:outputText value="#{person.vorname}"/>
</h:form>
</h:body>
</html>
I want that my composite component saves a string value in a JSF session bean with <h:inputText>. But the problem is, when I submit the form with the <h:commandButton> I see the following error:
Caused by: javax.el.PropertyNotFoundException: /resources/mygourmet/inputTest.xhtml at line 18 and column 42 value="#{model.vorname}": Target Unreachable, identifier 'model' resolved to null
at org.apache.myfaces.view.facelets.el.TagValueExpression.getType(TagValueExpression.java:73)
at org.apache.myfaces.shared_impl.renderkit._SharedRendererUtils.findUIOutputConverter(_SharedRendererUtils.java:77)
You need to reference composite component attribute values by #{cc.attrs.<name>} where <name> is the attribute name. So, this should do:
<h:inputText value="#{cc.attrs.model.vorname}">
See also:
Java EE 6 tutorial - Facelets - Composite Components
Java EE 6 tutorial - Advanced Composite Components
<composite:xxx> tag documentation
Unrelated to the concrete problem, all that <html><head><body> in the composite is unnecessary. I suggest to use <ui:component> since that's more clear. See also our composite component wiki page for examples.

Saving and reusing tag definition in PrimeFaces

Let's say I have the following construct polluting the simplicity of my JSF code in many places:
<p:calendar id="decisionDate"
effect="explode"
yearRange="2000:2100"
pattern="MM/dd/yyyy"
navigator="true" display="inline"
value=""
label="Decision Date"
maxlength="10"
size="20">
<f:convertDateTime pattern="MM/dd/yyyy" />
</p:calendar>
As can be seen, this has nine (9) attributes and a nested tag. This is an awful amount of tedious detail to consume with your eye.
Is there a way I can reuse PrimeFaces tags in a similar way as CSS: to save a complex tag definition as <px:myCalendar/> with the above parameters minus the ID ones, which should be set for each instance of use nonetheless, where px would be my namespace and then each time I need to invoke it, I would just say <px:myCalendar id="uniqueCalID"/> and ... BOOM ... there goes all the repeated clutter?
POST ANSWER EDIT: Check out this tutorial
You can define composite component. It is defined with xhtml+ jsf namespaces and, but in your case it is unnesessary, backing component, which is java class, instantiated for every composite component usage.
Within composite component interface you can define attributes, which vary its behaviour. And in implementation you then can insert needed primefaces' component with some hardcoded attributes and some passed from your composite component invocation.
Consider this tutorial: https://docs.oracle.com/javaee/6/tutorial/doc/giqzr.html
Example
Composite component is resource, so we put it below /resources folder. Let's create subfolder /resources/myCompositeComponents and create xhtml file myCalendar.xhtml there. It will be our composite component. Basically, it is xhtml file with additional namespace xmlns:cc="http://java.sun.com/jsf/composite". Here is the code. You can notice two elements: <cc:interface> and <cc:implementation>. And <cc:attribute> element inside the <cc:interface> is the input of our composite component.
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:f="http://xmlns.jcp.org/jsf/core"
xmlns:cc="http://java.sun.com/jsf/composite"
xmlns:p="http://primefaces.org/ui" xmlns:h="http://java.sun.com/jsf/html">
<cc:interface>
<cc:attribute name="label" default="Decision Date"/>
</cc:interface>
<cc:implementation>
<h2>#{cc.clientId}</h2>
<h:outputLabel
id="Label"
value="#{cc.attrs.label}"/>
<p:calendar id="Calendar"
effect="explode"
yearRange="2000:2100"
pattern="MM/dd/yyyy"
navigator="true" display="inline"
value=""
label="Label"
maxlength="10"
size="20">
<f:convertDateTime pattern="MM/dd/yyyy" />
</p:calendar>
</cc:implementation>
</html>
Then, let's use it. To be able to declare our brand new component we will put additional namespace into the using page: xmlns:my="http://java.sun.com/jsf/composite/myCompositeComponents". The last part of the namespace uri corresponds to the folder under /resources, where composite component lives. Give it any prefix you like. Here is source code:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE html
PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:my="http://java.sun.com/jsf/composite/myCompositeComponents">
<h:head>
<title>Simple JSF Facelets page</title>
</h:head>
<h:body>
<my:myCalendar id="LetsUseIt" label="MyLabel"/>
</h:body>
</html>
Have a notice of attribute "label" - that very attribute, that is declared in the "interface" element.
This is quite basic usecase, though it will help in your situation. More complex scenarios include passing typed attributes and implementing backing component - java class, instantiated every time the component is used.

param reference to bean not being passed into composite component

i'm having a bit of trouble with a composite component in JSF 2.1 vanilla (on glassfish 3.1). the simplified version of my problem is here:
[composite component]
<?xml version='1.0' encoding='UTF-8' ?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:f="http://java.sun.com/jsf/core"
xmlns:c="http://java.sun.com/jsp/jstl/core"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:p="http://primefaces.org/ui"
xmlns:cc="http://java.sun.com/jsf/composite">
<!-- INTERFACE -->
<cc:interface>
<cc:attribute name="value" required="true"/>
<cc:attribute name="title" required="false" default=""/>
<cc:editableValueHolder name="inputTarget" targets="labeledInputField"/>
</cc:interface>
<!-- IMPLEMENTATION -->
<cc:implementation>
<p:inputText id="labeledInputField"
label="#{cc.attrs.title}"
value="#{cc.attrs.value}"
title="#{cc.attrs.title}">
<cc:insertChildren/>
</p:inputText>
</cc:implementation>
</html>
[implemented in]
<!-- thisPerson is passed in via ui:param to the facelet containing this code.
it works in other (non-composite) components on the page -->
<comp:labeledInputText
id="baseUsername"
value="#{controller.username}"
title="#{bundle.Username}">
<f:validator for="inputTarget" binding="#{thisPerson.usernameValidator}"/>
<f:converter for="inputTarget" converterId="#{whiteSpaceTrimConverter}"/>
</comp:labeledInputText>
the problem is, the "thisPerson.usernameValidator" is evaluating to NULL, which then causes the com.sun.faces.facelets.tag.jsf.ValidatorTagHandlerDelegateImpl to then skip to the code that attempts to load the validator by "validatorID" which is not set because we're trying to send in the validator by "binding". is there a way to get the composite to evaluate the ui:param value, or a workaround that does not require reworking the validator (it's a huge anti-pattern and i don't have time to reverse the damage right now). assume the validator HAS to come in via binding.
i know the composite works because in a different facelet, i have the validator binding against a concrete bean reference, rather than a "soft" reference, and it works like a champ.
TIA
Without knowing your exact JSF implementation, I am going to assume Mojarra, you may be running into the following known bug.
http://java.net/jira/browse/JAVASERVERFACES-2040
Regardless if this is your exact problem or not, you can try to disable partial state saving and see if this resolves your issue. If it does then that means that you are facing this issue, which apparently was (fixed?) in later versions of Mojarra.
Another possibility would be to simply use renderFacet instead of insertChildren and insert your validators in the form of a facet.

How to create a composite of existing components in JSF?

I'd like to know if it's possible to compose my own component (or call it Widget, Object).
I mean, instead of (for example) using h:panelGroup and a h:outputLabel inside it, make my own h:panelMarkzzz, as a composition of panelGroup and outputLabel.
Is it possible on JSF?
Yes, it's possible to create a composition of existing components like that.
Kickoff example:
/resources/foo/group.xhtml
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://xmlns.jcp.org/jsf/html"
xmlns:cc="http://xmlns.jcp.org/jsf/composite">
<cc:interface>
<cc:attribute name="label" type="java.lang.String" required="true" />
</cc:interface>
<cc:implementation>
<h:panelGroup>
<h:outputLabel value="#{cc.attrs.label}" />
<cc:insertChildren />
</h:panelGroup>
</cc:implementation>
</html>
/test.xhtml
<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://xmlns.jcp.org/jsf/html"
xmlns:foo="http://xmlns.jcp.org/jsf/composite/foo">
<h:head>
<title>Test</title>
</h:head>
<h:body>
<foo:group label="Label value">
<h:outputText value="This will appear after label inside the panelgroup" />
</foo:group>
</h:body>
</html>
The /foo folder name is free to your taste and you can reference it in XML namespace as http://xmlns.jcp.org/jsf/composite/XXX. The XHTML filename is the tag name.
That said, composite components have performance implications and they should only be used when the functional requirement is not achievable using a simple include or tagfile. In your specific case, you'd better use a tagfile instead. A composite component is only worthy when you actually need it for the <cc:interface componentType="...">.
See also:
When to use <ui:include>, tag files, composite components and/or custom components?
Our composite component wiki page
JSF http://xmlns.jcp.org/jsf/composite tag documentation
Java EE 7 tutorial - Composite components
Java EE 7 tutorial - Advanced composite components
Perhaps you mean Composite Components?

Resources