Skip to content Skip to sidebar Skip to footer

Resolving Modules Using Require.js And Java/rhino

I'm trying to get require.js to load modules on the server-side with Java 6 and Rhino. I'm able to load require.js itself just fine. Rhino can see the require() function. I can tel

Solution 1:

require.js works well with rhino. Recently, I used it in a project.

  1. You have to make sure to use r.js (not require.js) , modified version of require.js for rhino.
  2. You have to extend ScritableObject class to implement load and print function. When you call require(["a"]), the load function in this class will be called, you can tweak this function to load the js file from any location. In the below example, I load from classpath.
  3. You have to define the property arguments in the sharedscope as shown below in the sample code
  4. Optionally, you can configure the sub path using require.config, to specify the subdirectory inside classpath where js files are located.

JsRuntimeSupport

publicclassJsRuntimeSupportextendsScriptableObject {

    privatestaticfinallongserialVersionUID=1L;
    privatestaticLoggerlogger= Logger.getLogger(JsRuntimeSupport.class);
    privatestaticfinalbooleansilent=false;

    @Overridepublic String getClassName() {
        return"test";
    }

    publicstaticvoidprint(Context cx, Scriptable thisObj, Object[] args,
            Function funObj) {
      if (silent)
        return;
        for (inti=0; i < args.length; i++)
          logger.info(Context.toString(args[i]));
    }

    publicstaticvoidload(Context cx, Scriptable thisObj, Object[] args,
            Function funObj)throws FileNotFoundException, IOException {
        JsRuntimeSupportshell= (JsRuntimeSupport) getTopLevelScope(thisObj);
        for (inti=0; i < args.length; i++) {
            logger.info("Loading file " + Context.toString(args[i]));
            shell.processSource(cx, Context.toString(args[i]));
        }
    }

    privatevoidprocessSource(Context cx, String filename)throws FileNotFoundException, IOException {
        cx.evaluateReader(this, newInputStreamReader(getInputStream(filename)), filename, 1, null);
    }

    private InputStream getInputStream(String file)throws IOException {
        returnnewClassPathResource(file).getInputStream();
    }
}

Sample Code

publicclassRJsDemo {

    @TestpublicvoidsimpleRhinoTest()throws FileNotFoundException, IOException {
    Contextcx= Context.enter();

    finalJsRuntimeSupportbrowserSupport=newJsRuntimeSupport();

    finalScriptableObjectsharedScope= cx.initStandardObjects(browserSupport, true);

    String[] names = { "print", "load" };
    sharedScope.defineFunctionProperties(names, sharedScope.getClass(), ScriptableObject.DONTENUM);

    ScriptableargsObj= cx.newArray(sharedScope, newObject[] {});
    sharedScope.defineProperty("arguments", argsObj, ScriptableObject.DONTENUM);

    cx.evaluateReader(sharedScope, newFileReader("./r.js"), "require", 1, null);
    cx.evaluateReader(sharedScope, newFileReader("./loader.js"), "loader", 1, null);

    Context.exit();

  }

}

loader.js

require.config({
    baseUrl: "js/app"
});

require (["a", "b"], function(a,  b) {
    print('modules loaded');
});

js/app directory should be in your classpath.

Post a Comment for "Resolving Modules Using Require.js And Java/rhino"