The Nuxeo Platform has been upgraded to JSF 2 for the 6.0 version. This page provides tools and notes to help you migrate your custom Nuxeo projects to this version.
Content Application Platform (CAP) and its plug-ins have been migrated JSF 2 for 6.0. This can have a big impact on custom XHTML templates, so a migration tool has been implemented to help you to migrate your custom code base. Here you will find additional notes and instructions about this migration.
Nuxeo Helper Tools
Development Mode
Setting up the development mode can help you hot reload your files. An Ant file is also available to help you synchronize your project XHTML templates with your server, while you are working. Please refer to the page Hot Reloading XHTML templates.
Migration Tool
Using this migration module might be useful when upgrading a Nuxeo application to 6.0. The last released version of the tool can be found in the Nuxeo Maven repository at https://maven.nuxeo.org/nexus/content/groups/public/org/nuxeo/jsf2/nuxeo-jsf2-migration/1.3-6033/.
The README file on the GitHub project describes how to use the tool and how to create new rules (if you find it useful for your own migration).
When the automatic migration is set in the parameters of the tool, the migrated files will be created in the same directory as the original ones but with a .migrated extension. This allows the user to compare the migrations that have been done and to avoid overriding the JSF1.2 compliant files.
Also, the migrated files will be formatted. So using the parameter format
to true is advised, in order to have an easier comparison between the original and the migrated file.
This tool will generate a report about your project XHTML templates, and will mainly report:
- Warnings or errors when parsing XHTML templates, due to missing migration steps
- Warnings or errors when detecting override of a Nuxeo default template
Dependency Changes
Version Changes
The main dependency changes are:
- Upgrade from JSF Mojarra 1.2.12 to 2.2.6 (including a small patch on jsf-impl, see VEND-18)
- Removal of JSF Facelets 1.1.15.B1 as features are now included in JSF 2.
- Upgrade from RichFaces 3.3.1.GA-NX9.04 to 4.5.0.Alpha3 (patched, list of patches available on JIRA)
- Upgrade from Seam 2.1.0.SP1 to 2.3.1.Final (patched, list of patches available on JIRA)
- Removal of old patched Tomahawk libraries 1.1.5, as well as commons-el 1.0
- Upgrade from jboss-el 1.0_02.CR2 to 1.0_02.CR6
Maven Changes
Here is a list of maven dependency changes:
As of 5.8 (hot-fixed)
properties>
...
<nuxeo.richfaces.version>3.3.1.GA-NX9.04</nuxeo.richfaces.version>
<seam.version>2.1.0.SP1</seam.version>
<nxseam.version>2.1.0.SP1-NX3</nxseam.version>
</properties>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>javax.faces</groupId>
<artifactId>jsf-api</artifactId>
<version>1.2_12</version>
</dependency>
<dependency>
<groupId>javax.faces</groupId>
<artifactId>jsf-impl</artifactId>
<version>1.2_12</version>
</dependency>
<dependency>
<groupId>com.sun.facelets</groupId>
<artifactId>jsf-facelets</artifactId>
<version>1.1.15.B1</version>
</dependency>
<dependency>
<groupId>org.richfaces.framework</groupId>
<artifactId>richfaces-api</artifactId>
<version>3.3.1.GA</version>
</dependency>
<dependency>
<groupId>org.richfaces.framework</groupId>
<artifactId>richfaces-impl</artifactId>
<version>${nuxeo.richfaces.version}</version>
</dependency>
<dependency>
<groupId>org.richfaces.ui</groupId>
<artifactId>richfaces-ui</artifactId>
<version>${nuxeo.richfaces.version}</version>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam</artifactId>
<version>${nxseam.version}</version>
<exclusions>
<exclusion>
<groupId>javax.el</groupId>
<artifactId>el-api</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam-remoting</artifactId>
<version>${seam.version}</version>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam-ui</artifactId>
<version>${seam.version}</version>
<exclusions>
<exclusion>
<groupId>com.google.code.guice</groupId>
<artifactId>guice</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam-mail</artifactId>
<version>${seam.version}</version>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam-pdf</artifactId>
<version>${seam.version}</version>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam-rss</artifactId>
<version>${seam.version}</version>
</dependency>
<dependency>
<groupId>net.sourceforge.yarfraw</groupId>
<artifactId>yarfraw</artifactId>
<version>0.92</version>
<exclusions>
<exclusion>
<groupId>javax.xml</groupId>
<artifactId>jaxb-api</artifactId>
</exclusion>
<exclusion>
<groupId>apache-httpclient</groupId>
<artifactId>commons-httpclient</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam-excel</artifactId>
<version>${seam.version}</version>
</dependency>
<dependency>
<groupId>net.sourceforge.jexcelapi</groupId>
<artifactId>jxl</artifactId>
<version>2.6.12</version>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam-debug</artifactId>
<version>${seam.version}</version>
</dependency>
<dependency>
<groupId>org.jboss.el</groupId>
<artifactId>jboss-el</artifactId>
<version>1.0_02.CR2</version>
</dependency>
</dependencies>
</dependencyManagement>
As of 6.0
<properties>
...
<jsf.version>2.2.6</jsf.version>
<nxjsf.version>2.2.6-NX01</nxjsf.version>
<richfaces.version>4.5.0.Alpha3</richfaces.version>
<seam.version>2.3.1.Final</seam.version>
<nxseam.version>2.3.1.Final.NX01</nxseam.version>
</properties>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>com.sun.faces</groupId>
<artifactId>jsf-api</artifactId>
<version>${jsf.version}</version>
</dependency>
<dependency>
<groupId>com.sun.faces</groupId>
<artifactId>jsf-impl</artifactId>
<version>${nxjsf.version}</version>
</dependency>
<dependency>
<groupId>javax.validation</groupId>
<artifactId>validation-api</artifactId>
<version>1.0.0.GA</version>
</dependency>
<dependency>
<groupId>org.richfaces</groupId>
<artifactId>richfaces</artifactId>
<version>${richfaces.version}</version>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam</artifactId>
<version>${nxseam.version}</version>
<exclusions>
<exclusion>
<groupId>javax.el</groupId>
<artifactId>el-api</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam-remoting</artifactId>
<version>${nxseam.version}</version>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam-ui</artifactId>
<version>${seam.version}</version>
<exclusions>
<exclusion>
<groupId>com.google.code.guice</groupId>
<artifactId>guice</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam-mail</artifactId>
<version>${seam.version}</version>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam-pdf</artifactId>
<version>${seam.version}</version>
<exclusions>
<!-- dep conflicting with JSF2 -->
<exclusion>
<groupId>org.jboss.spec.javax.faces</groupId>
<artifactId>jboss-jsf-api_2.1_spec</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam-rss</artifactId>
<version>${seam.version}</version>
</dependency>
<dependency>
<groupId>net.sourceforge.yarfraw</groupId>
<artifactId>yarfraw</artifactId>
<version>0.92</version>
<exclusions>
<exclusion>
<groupId>javax.xml</groupId>
<artifactId>jaxb-api</artifactId>
</exclusion>
<exclusion>
<groupId>javax.xml.bind</groupId>
<artifactId>jsr173_api</artifactId>
</exclusion>
<exclusion>
<groupId>apache-httpclient</groupId>
<artifactId>commons-httpclient</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam-excel</artifactId>
<version>${seam.version}</version>
</dependency>
<!-- NXP-11018 -->
<dependency>
<groupId>net.sourceforge.jexcelapi</groupId>
<artifactId>jxl</artifactId>
<version>2.6.12</version>
</dependency>
<dependency>
<groupId>org.jboss.seam</groupId>
<artifactId>jboss-seam-debug</artifactId>
<version>${seam.version}</version>
</dependency>
<dependency>
<groupId>org.jboss.el</groupId>
<artifactId>jboss-el</artifactId>
<version>1.0_02.CR6</version>
</dependency>
</dependencies>
</dependencyManagement>
Note that versions stated above may vary depending on your hot-fix version.
Changes on JSF Tag Libraries
This chapter lists changes on JSF tag libraries that are used in default Nuxeo pages. If you have been using these libraries to implement custom templates, you might want to look for additional migration documentation directly on these libraries documentation. Richfaces provides a guide about migrating components from 3.3.x to 4.x version.
Migration for faces-config.xml
configuration files
If you defined a faces-config.xml
configuration file in your module, this file namespaces should be upgraded to JSF 2 standards:
<faces-config xmlns="http://java.sun.com/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-facesconfig_2_0.xsd"
version="2.0">
...
</faces-config>
Migration for A4J
namespace
- The namespace for the prefix
a4j
changed. The new value is<span class="nolink">http://richfaces.org/a4j</span>
.
a4j:form
- The component
a4j:form
does not exist anymore in the RichFaces library. It must be replaced with ah:form
element. Ajaxified behavior is supported simply by using ajaxified commands.
a4j:actionParam
- The component
a4j:actionParam
does not exist anymore in the RichFaces library. It must be replaced with ana4j:param
element.
a4j:ajaxListener
- The component
a4j:ajaxListener
does not exist anymore in the RichFaces library.
a4j:support
- The component
a4j:support
does not exist anymore in the RichFaces library. It must be replaced by ana4j:ajax
element. AttributesrequestDelay
andignoreDupResponses
should be moved to a sub elementa4j:attachQueue
. - Sample migration: https://github.com/nuxeo/nuxeo-platform-login/commit/bc33ae59fd968a896ac76ec7b32409b321089faf
attribute reRender
- The name of the parameter
reRender
in a4j tags changed torender
. - The separation character is no longer a comma but it is replaced by a space.
- You can use helper JSF function
nxu:joinRender(String, String)
to join several render ids. - Render ids sometimes need to be made absolute, the helper JSF function
nxu:componentAbsoluteId(component, localId)
can be helpful. The component variable is the current component in the JSF tree and is used as an anchor to browse the tree.
attribute ajaxSingle
- The attribute
ajaxSingle="true"
must be replaced by the attributeexecute="@this"
.
attribute event and corresponding event name
- The attribute
event="onclick"
must be replaced by the attributeevent="click"
. - Generally, all event names starting with "on" must be replaced, for instance
event="onchange"
must be replaced by the attributeevent="change"
.
Migration for RichFaces
rich:suggestbox
- The tag
rich:suggestbox
does not exist anymore in the RichFaces library. It must be replaced by aselect2
or arich:autocomplete
element.
rich:fileUpload
- The
uploadData
attrbute is not used anymore, usefileUploadListener
instead (see http://docs.jboss.org/richfaces/4.5.X/4.5.0.Beta2/vdldoc/rich/fileUpload.html). - The
listWidth
attribute does not exist anymore, usestyle
instead. - Sample migration: https://github.com/nuxeo/nuxeo-dam/commit/9ab3620742e833df446960d4fe3c6eb82073296d
rich:tree
- The
var
attribute should be moved from tagrich:treeModelRecursiveAdaptor
to the upper tagrich:tree
. - The
roots
attribute should resolve to a list (a single element will not be taken into account anymore, silently) - Sample migrations:
rich:recursiveTreeNodesAdaptor
- This tag has been replaced by
rich:treeModelRecursiveAdaptor
.
rich:modalPanel
- The tag has been replaced by rich:popupPanel
Migration for Seam JSF Tag Libraries
namespace
- The namespace for the prefix
s
changed. The new value is<span class="nolink">http://jboss.org/schema/seam/taglib</span>
.
Migration for Nuxeo JSF Tag Libraries
nxu:dataList
- This tag was previously relying on the t:dataList tag from tomahawk library, and now relies on the
rich:dataList
tag that does not handle the same attributes. As this tag is quite rare in the application, attributes migration is not handled, resulting in minor display changes (using a table or a menu instead of listing iteration elements in span tags, for instance), that can easily be migrated using ac:forEach
orui:repeat
tag.
nxdir:chainSelect*
This tag (and related subtags) behaviour has changed a little, please read HOWTO: Create a N-Level Select Widget again to adapt your custom templates if you defined chain select widget templates for more than two levels. The modification should be simple:
<nxdir:chainSelectListbox index="0" size="1" directoryName="#{widgetProperty_parentDirectory}" localize="#{widgetProperty_localize}" id="#{widget.id}_parent" ordering="#{empty widgetProperty_ordering?'label':widgetProperty_ordering}"> <a4j:ajax event="change" - render="#{widget.id}_child,#{widget.id}_message" - immediate="true"> - <a4j:ajaxListener type="org.ajax4jsf.ajax.ForceRender" /> - </a4j:ajax> + render="#{widget.id}_child #{widget.id}_message" + immediate="true" /> </nxdir:chainSelectListbox>
Migration for Core Tag Libraries
c:set tag scope
- The
page
scope does not exist in JSF2, useview
instead.
Miscellaneous Changes
h:form tag onsubmit
attribute
- The
onsubmit
attribute can refer to javascript functions, but they are not currenlty triggered anymore, so the corresponding Javascript code should be moved to the submission button(s)
Usage of selectionActions
Seam Component
The selectionActions
Seam component has been used to impact other components in the JSF tree when selecting or clicking on some elements in the page.
Since version 6.0, lookups on other components have changed_: _
The call to the method
selectionActions.onClick
must be replaced.The call to the method
selectionActions.selectedValue
must be replaced.- Follow the documentation at HOWTO: Impact Another JSF Component from a Command or Select.
- Sample migration: https://github.com/nuxeo/nuxeo-features/commit/0d76ae012408951a7f6f2b17787c4bf926918132
Fancy Boxes and Ajax Actions
- In fancyboxes (aka Javascript modal panels), an explicit subtag
<f:ajax event="click" execute="@this" render="...">
may be needed ona4j:commandButton
components and such. By default, they must execute@form
but since the fancybox moves them out of the form, this trick is needed for the request to be correctly triggered.
Trigger of Javascript Methods on Ajax Requests
Some Javascript methods may need to be triggered again on ajax render. One possibility is to surround them by a tag a4j:outputPanel
with attribute ajaxRendered="true"
, but it's actually easier to register an Ajax callback.
Here is an example to trigger again the tipsy tooltip library on Ajax render:
<ui:composition
xmlns="http://www.w3.org/1999/xhtml"
xmlns:ui="http://java.sun.com/jsf/facelets"
xmlns:a4j="http://richfaces.org/a4j">
<script type="text/javascript" src="scripts/jquery.nuxeo.tipsy.js">
</script>
<script>
jQuery(document).ready(function() {
jQuery('.tipsyShow').initTipsy(500, 5000);
});
jsf.ajax.addOnEvent(function(data) {
var ajaxstatus = data.status;
if (ajaxstatus == "success") {
// remove all existing tipsy
jQuery('.tipsy').remove();
jQuery('.tipsyShow').initTipsy(500, 5000);
}
});
</script>
</ui:composition>
Here is an example to show errors on Ajax requests:
<script type="text/javascript">
jsf.ajax.addOnError(function(data) {
jQuery.ambiance({
title: data.description,
type: "error",
className: "errorFeedback",
timeout: 0
});
});
</script>
Also, note that inline scripts that are part of the DOM updated by the Ajax render will be evaluated again.
Ajax Regions and Status
Ajax request status can be made visible to the user by using the following code:
<a4j:status>
<f:facet name="start">
<h:graphicImage value="/img/standart_waiter.gif"/>
</f:facet>
</a4j:status>
The corresponding icon used to be associated to an ajax region. It is not the case anymore, so multiple status icons could in theory be visible on the page, but all these statuses are now displayed on the top right corner of the page (using global CSS positioning) so these changes should not be visible to the end user.
Changes on Seam Components Implementation
With JSF2 new logics, the restore view phase is processed entirely again on a post, which can result in Seam factories being processed earlier than before, and not reset according to further logics. The symptom of this change results in a factory variable that's not updated correctly.
In this case, variables need to be explicitely removed from the corresponding Seam context map, so that factory is called again.
Sample fix for NXP-15566 for instance: https://github.com/nuxeo/nuxeo-features/commit/c22fcbd86a5220becf6820174ca1449f8c09cb21.
Changes on Javascript Resources
- The order of default resources has changed, so custom resources inclusion might need to be done differently to ensure proper ordering.
- Inline scripts sometimes need to be changed to be properly escaped, see for instance changes for the following scripts inclusion: https://github.com/nuxeo/nuxeo-features/commit/f3454b0e6647733f0d78c5504c6dbf21bbbd1ae5
- The
jquery.js
theme resource is not used anymore on JSF pages, as it is already provided by RichFaces
Advanced Low Level Changes
- JSF2 expects ajaxified actions performed inside a multipart for to be done in a frame. This behaviour has been patched to get back the old behaviour, see fixmultipartajax.js.
- Nuxeo is shipped with OmniFaces' view state patch for JAVASERVERFACES_SPEC_PUBLIC-790, see fixviewstate.unminified.js.
- Nuxeo is using a specific URL management system. JSF2 changes now require resources corresponding to the view id to exist (even if a specific treatment or a redirection are handled afterwards).
- The
document
variable, that used to be exposed by layout system as an alias to thevalue
variable, is not exposed anymore.