JRebel with JDeveloper and ADF

This tutorial has been created and will hopefully provide input for JDeveloper and ADF users who might be struggling with JRebel.


Things to consider

Working with JDeveloper and ADF follows its own peculiarities. For reloading to work, you should consider these simple guidelines:

  • Turn off fast swap when enabled.
  • Always make your project after modifying the code. JRebel reloads only compiled classes – and JDeveloper does not have an auto-compile function (whereas Eclipse does). Making the project is necessary for the changes in Java code to be reloaded. Changes in non-java files might or might not require making the project to be reloaded. This depends on the project structure and rebel.xml content.
  • Changes such as modifications of page definitions require a new JSF view to be created. The easiest method to achieve this is to reload the page URL without any GET parameters. It is recommended to always reload the page this way.
  • Avoid rebuilding projects when a container is running with JRebel enabled. Rebuilding modifies all files, causing JRebel to reload them which can be quite time-consuming.

Reloading does not work

Once you have successfully activated JRebel, generated a rebel.xml and the JRebel banner is shown in the console when starting WebLogic – but reloading does not work, there are several things you should check.

  • Enable JRebel log. You can find this via Tools > Preferences > JRebel. Choose debug level logging and enable request log.
  • After starting your application and opening a test page, open the JRebel log and search for rebel.xml. You should see all your rebel.xml files. If some of them are missing from the log, please refer to the I don’t see my rebel.xml in JRebel log section below. If you do see all your rebel.xml files, continue to the next step.
  • The correct rebel.xml is rather complex for ADF applications, so it is strongly recommended to start with an automatically generated rebel.xml. To do this, open Project Properties > JRebel > Generate now!
  • The automatically generated rebel.xml should be tweaked manually. Some ADF projects that contain web resources are deployed as JARs. The “web” element in rebel.xml does not work for JARs, so if your rebel.xml was generated with this element, just move the “dir” element(s) from “web” to “classpath” and remove the “web” element.
  • If you follow all the JDeveloper specific rules and have gone through all the previous steps, but reloading still does not work, write to support@zeroturnaround.com. Provide a detailed description of your setup and the changes that you expect to be reloaded. Attach your JRebel log to the email. If possible, create and send a small application that can be used to reproduce the issue. Having such application is immensely helpful for bug fixing.

I cannot see my rebel.xml in JRebel log

JRebel is operating in the application server, not within the IDE. Therefore it knows nothing about the IDE projects. What’s important is what the deployed application looks like. Usually you can find the deployed application in USER_HOME\AppData\Roaming\JDeveloper\JDEV_VERSION\o.j2ee\drs\APP_NAME.

  • In the case of JDeveloper, multiple projects are sometimes packaged into a single archive. In this case only one project should have rebel.xml, in which resources from both or all projects are mapped.
  • If your project has separate folders for application and test sources (as is usually the case with Maven applications), rebel.xml might be generated in the test folder. It will then be ignored when packaging/deploying the application! In this case you simply need to move the file to the application sources folder. Also make sure that you don’t include the folder containing test classes in your rebel.xml.

Example of rebel.xml configuration for typical ADF application

Let us configure JRebel for a typical ADF application. Our application consists of 3 projects:

  • Model – which has a single deployment profile and is deployed as a JAR.
  • ViewController – which has a single deployment profile and is deployed as WAR.
  • CompanyViewController – which has a single deployment profile and is also deployed as a JAR.

However, if we created rebel.xml files based on this information, we would be in for an unpleasant surprise. In reality only Company_adflib.jar created from CompanyViewController is present in WEB-INF/lib of the WAR module.

The Model project is configured as a dependency for both ViewController and CompanyViewController projects. Therefore classes and resources from the Model project are included in both Company_adflib.jar and WEB-INF/classes of the WAR module.

The whole WAR module is loaded by one classloader – as duplicate classes and resources won’t cause any problem. Since we have two physical modules (WAR and Company_adflib.jar) we shall need two rebel.xml files: in ViewController and CompanyViewController projects respectively. Content of these files is pasted below. Note that classes and resources from Model project are mapped in the rebel.xml that is in ViewController (WAR module). Also notice that there is no element in the rebel.xml that is inside CompanyViewController. Folder public_html that contains web resources is mapped in classpath.


rebel.xml from ViewController project

<?xml version = '1.0' encoding = 'UTF-8'?>
<application
      xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
      xsi:schemaLocation="http://www.zeroturnaround.com/alderaan/rebel-2_0.xsd"
      xmlns="http://www.zeroturnaround.com">
   <classpath>
      <dir name="C:\workspaces\jdev_ws1\11.1.2.0\JRebel\ViewController\adfmsrc"/>
      <dir name="C:\workspaces\jdev_ws1\11.1.2.0\JRebel\ViewController\classes">
         <include name="**/*.class"/>
         <exclude name=".wlsjsps/**"/>
      </dir>
      <dir name="C:\workspaces\jdev_ws1\11.1.2.0\JRebel\ViewController\src">
         <exclude name="**/*.java"/>
      </dir>
      <dir name="C:\workspaces\jdev_ws1\11.1.2.0\JRebel\Model\classes">
         <include name="**/*.class"/>
         <exclude name=".wlsjsps/**"/>
      </dir>
   </classpath>
   <web>
      <link target="/">
         <dir name="C:\workspaces\jdev_ws1\11.1.2.0\JRebel\ViewController\public_html"/>
      </link>
   </web>
</application>

rebel.xml from CompanyViewController project

<?xml version = '1.0' encoding = 'UTF-8'?>
<application
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://www.zeroturnaround.com/alderaan/rebel-2_0.xsd"
    xmlns="http://www.zeroturnaround.com">
  <classpath>
    <dir name="C:\workspaces\jdev_ws1\11.1.2.0\JRebel\CompanyViewController\adfmsrc"/>
    <dir name="C:\workspaces\jdev_ws1\11.1.2.0\JRebel\CompanyViewController\classes">
      <include name="*.class"/>
      <exclude name=".wlsjsps/**"/>
    </dir>
    <dir name="C:\workspaces\jdev_ws1\11.1.2.0\JRebel\CompanyViewController\src">
      <exclude name="*.java"/>
    </dir>
    <dir name="C:\workspaces\jdev_ws1\11.1.2.0\JRebel\CompanyViewController\public_html"/>
  </classpath>
</application>