Hot reload has been partially supported over Nuxeo versions. The following instructions mostly apply since Nuxeo 5.6 version.
Hot reload involves a lot of layers, each one handling different kinds of caches.
Sometimes hot reload needs to be very smooth, when installing Studio packages from the Admin Center for instance. In these cases, the whole application does not need to be reloaded, and the current user view needs to keep its context (authentication, current page, current document, etc...)
In other cases, when working with the Nuxeo IDE for instance, the application needs to be reloaded completely to take into account changes in Java code, and the current context cannot always be restored to its previous state.
Setting up the dev mode
Hot reload is currently mainly interesting to ease up development. Enabling it means re-building part of the application, resetting caches that are needed for the application to work efficiently, etc... For this reason, using hot reload may not be suitable for production.
Hot reload support is controlled by the Nuxeo development mode. This mode can be activated by setting a runtime property in nuxeo.conf file:
Activating this mode can also be done in the Admin Center, in the Update Center > Nuxeo Studio tab, or in the System information > Setup tab.
The development mode is checked by code whenever performing actions that would involve hot reload (when trying to install packages from the Update Center, or bypassing some caches during rendering, for instance). But some parts of the application may need the server to be started with the dev mode enabled (or disabled) for this property to be taken into account properly, so it is recommended to restart the server at least once after changing this property value.
The development mode should not be activated on a server in production.
Understanding layers involved in hot reload
When contributing a jar to the Nuxeo application, what's a stake?
- the jar should be detected by the application
- its contributions to Nuxeo extension points should be loaded
- its contributions to other resources (xhtml files, message bundles, etc...) should be detected.
- some caches should be reset
Hot reloading Nuxeo runtime components
If your bundle is already installed (you do a reload) you should first uninstall it. For this you need the
java.io.File of your bundle, and you can call:
Then to install your bundle again you can do this:
The second parameter makes sure that bundles hot-reloaded are taken into account by a specific class loader, only used in hot reload cases.
Undeploy and deploy to the runtime Framework were already possible as of Nuxeo 5.4.1: you can take example on what the ReloadService is doing to make it work in your version.
After uninstalling, installing or reloading a bundle you may want to flush all main Nuxeo caches. This can be done like this:
There is a variety of flush and reload methods available on the ReloadService, flush-like methods are mainly used to clean up caches, while reload-like methods do not rely on lazy-loading of resources when cache is reset: they tend to rebuild the cache themselves.
Calling the main flush/reload methods is important if you have parts of the application relying on receiving runtime events "reload" and "flush".
Flushing the repository cache is important if you make modifications on document types and the JAAS flush is flushing user cache (if you modify logins etc...).
Note that reloading a bundle is working correctly only if the extension point registries it holds are correctly handling the contributions merging and removal. This can be easily set up by extending the ContributionFragmentRegistry abstract class. Check out the SimpleContributionRegistry abstract class for most common use cases (a single registry using a map, not needing any merge management).
There are some registries that will not work correctly. In that case please report a bug. Anyway document types, actions and other important contributions are working.
Resetting low level caches
Low level caches are shared by all users of the application. Resetting of their cache can be done by listening to the runtime "flush" event.
Checkout the following contribution, allowing to reset the directories cache (it's relying on the ReloadService#flush method to be called):
Hot reloading the war
The war can be rebuilt, taking care of changes to jars/bundles deployed in the application:
When the war is up-to-date, it's a matter of forcing the application to detect changes. As a reminder, all this is only activated when the Nuxeo development mode is.
XHTML files can be hot reloaded from the
nuxeo.war directory. In order to activate this, the runtime property facelets.REFRESH_PERIOD can be set to "2" for instance: it will force facelets to refresh pages that have changed in the last 2s. Since 5.6, activating the development mode is enough: it will force the facelets refresh period to 2s.
Then you can directly edit the XHTML files from here or copy manually the XHTML files you edited from your IDE into this directory.
NB: do not forget to disable this option for production, as detecting changes on XHTML files is costly for the server.
Message files can be hot reloaded from the
nuxeo.war/WEB-INF directory. The resources cache needs to be reset first. This is done by listening to the runtime "flush" event (see above) and can also be triggered by the user action "Dev mode: force flush" action available in the user menu on top of all pages.
JSF navigation cases
Currently, JSF navigation cases can only be reset when the JSF development mode is activated. But when activating this, hot reload breaks the user current view, so new navigation cases are detected thanks to a hack in Nuxeo code, activated when the Nuxeo development mode is.
Other configurations (other kinds of JSF contributions to the
faces-config.xml file, contributions to the Seam
pages.xml file, contributions to the
web.xml file, etc...) are not currently hot-reloaded by activating the Nuxeo development mode.
Resetting high level caches
Seam components may hold high-level caches. Since the web session is not impacted by a simple hot reload, and since Seam components instances are not shared by users, there is no direct way to inform all users of the application that their Seam components need to reset and rebuild their cache.
For a Seam component to reset its cache correctly, it can use the following tricks:
- when dev mode is set (and only then: the rest of the time, cache invalidation should be handled as usual, regardless of hot reload support), it can check if the service it relies on has changed. This can be done only with services implementing the
org.nuxeo.runtime.service.TimestampedServiceinterface: whenever a change is done on this service, a timestamp will be changed on the service.
Here is sample code checking for changes on the type service for instance:
If your cache relies on several services, or on a service that is not implementing the
TimestampedService interface (or if you simply do not want the reset to be done only when really needed), you can also just check for a similar timestamp kept on the
ReloadService: it will track if a flush was triggered since the last time you built the cache.
This is automatically done when the Nuxeo developement mode is activated: when navigating, all users will detect that a flush was called on the
ReloadService, and a Seam flush event will be sent. So you can just add an observer for this Seam event, for instance:
Note that currently, automatic detection does not only send the "flush" seam event: it also sends a bunch of Seam events that most of Seam components already observe to reset their cache, to ease up hot reload support on this layer.
Hot reloading Webengine modules
Activating the development mode also activates hot reload for webengine modules.
TODO: explain how it's done and describe potential limitations.
Hot reloading Seam components
Seam components can also be hot redeployed. This can save a lot of time (and server restarts).
This is not controlled by the Nuxeo development mode as it relies on other configurations to be available.
To activate Seam Hot reload you need to:
- put an empty file at
nuxeo.ear/config/seam-debug.properties. Since 5.6, setting the property "org.nuxeo.seam.debug" to value "true", in the
bin/nuxeo.conffile is equivalent.
- install the suitable seam debug library for your version of nuxeo into the
nxserver/bundles/folder. The jar is named "nuxeo-platform-seam-debug-5.5.jar" for version 5.5. You can use our maven repository for selecting and downloading the jar. This will place the JBoss Seam library into folder
nxserver/nuxeo.war/WEB-INF/libat startup and activate Seam debug features on the application.
If you're using the Nuxeo IDE, these settings are not needed because they're installed by default, and the debug jar is included in the SDK.
Selecting the Seam Components that can be Hot Reloaded
Because of the way Seam Hot Reload works, you have to select what Seam Components must be hot reloadable.
This is done by telling the deployment system which bundle and what classes must be reloadable.
In your bundle, add the following lines at the end of you
This instruct the deployer for extracting all the classes suffixed by
Bean into the
nuxeo.war/WEB-INF/dev folder and to extract the others into a new
bundle-seamhotdeploy.jar folder and to rename the original jar to
For backward compability, we also include the classes selected in the
seam-debug.properties in the config folder and the bundle's
How does it work and what are the limitations?
During deployment preprocessing, the "hot reloadable jars" will be split:
- Seam classes made for hot reload will be copied into
- other jar ressources (class, xml, manifest ...) will remain in another jar that will be deployed instead of the original one
nuxeo.ear/nuxeo.war/WEB-INF/dev will be deployed by Seam in a separated class loader and will be hot-reloadable.
Since these classes are in a child classloader, they can access other Seam components, but other Seam components can not see them.
How do I reload my classes?
You have to copy your updated classes into
To trigger the hot reload, you can either:
- use the SeamReload action link that is available in the default nuxeo-dm packaging,
- or call the url :
How do I automatically hot reload with ant?
You add this code to your ant script :