Java to JavaScript Compilation with AJAX and Spring Integration

For some time I have been interested in client-centric, web-based user interfaces. These Generation IV frameworks are characterised by their component-based, event-driven programming model, and focus on the presentation logic residing entirely on the client. Targeting a web browser in this manner typically necessitates the use of JavaScript or Flash, which in itself imposes a number of unique challenges.
It is possible to address many of these challenges if we can program in Java and automatically produce a JavaScript or Flash runtime module. Two well-known products for achieving this today are Google Web Toolkit (GWT) and Open Laszlo respectively. Both are available under OSI-approved licenses and have active communities, together with their own unique complexity. One consideration is to what extent they fulfil an objective of providing a transparent Java-based development environment that targets web browser deployment. This consideration has several facets, including IDE support, debugging integration, reflective capabilities, runtime widget binding and alike. All of these are normal considerations when developing rich clients using traditional Java technologies such as Swing and Standard Widget Toolkit (SWT).
The purpose of this blog entry is not to critique GWT or Open Laszlo. Instead I would like to explore an open source Java to JavaScript compiler named Java2Script Pacemaker (J2S) and present an initial Spring integration. This interesting project is not widely known, yet addresses transparent Java to JavaScript development in an encouraging manner. J2S ships with an incremental compiler, virtually complete JavaScript version of the java.lang, java.io and java.util packages, a JavaScript version of Junit, an Eclipse SWT JavaScript implementation, plus an AJAX library. More importantly, J2S can convert any existing Java code into JavaScript, subject to the availability of source code and dependencies also being similarly converted into JavaScript.
Focusing on technical considerations, J2S is currently differentiated from GWT in several broad ways. The first is its compiler technology, which builds on Eclipse Abstract Syntax Tree (AST) and therefore requires Eclipse. However, Eclipse JDT Core supports a headless mode and thus it wouldn't be difficult to execute J2S compilation from an Ant plugin or Maven mojo. The second difference is that J2S provides comprehensive runtime reflection and widget binding capabilities. GWT prefers compile-time JavaScript optimisations, at the expense of these runtime services. J2S – on the other hand – recognises that a combination of Moore's Law, improved browser JavaScript interpreters and JNI-like JavaScript optimisations collectively provide scope for adequate performance, whilst still enjoying fuller JRE emulation and other runtime services.
Perhaps the biggest technical differentiator relates to the user interface approach. GWT provides its own Swing-like API that was designed for web browser integration. On the other hand, J2S aims to provide an implementation of SWT. There are a number of benefits evident in J2S' approach:
- Your application can target both a rich client (in a JVM) and a web UI (in a web browser), with little to no recoding;
- To develop and debug a J2S application is largely the same as developing and debugging an ordinary SWT application, which greatly reduces the learning curve for new developers;
- Organisations have a good chance of engaging people with SWT skills;
- Plenty of literature and community resources are available for SWT;
- SWT is a stable and production-proven API; and
- Both open source and commercial tools are available to help you build SWT applications.
J2S does have some limitations to consider, though. These include:
- Download speed across the Internet can be slow. Given the majority of JEE applications are for intranet deployment, I am uncertain whether this should represent a major obstacle. Further, JavaScript compression and client caching minimise these delays.
- Execution speed can be slow, although I haven't found it too bad once the code has downloaded. There are various optimisations available to improve speed. There is also the option of power users downloading a JVM-hosted SWT version of the user interface, which should impose limited additional development cost due to the shared SWT codebase.
- JFace is currently unsupported, and the full JRE is not emulated. A notable exception is java.io.File. If you depend on this class, your application will not compile natively to JavaScript. Instead you'll need to use J2S' @j2sNative capability to compile the relevant classes to JavaScript. I have also encountered a couple of minor issues with the SWT implementation, but nothing too serious.
- The J2S community is relatively small, and the framework hasn't seen wide usage to date. Still, every open source project starts small and needs to be given a chance to grow.
- Users of IDEs other than Eclipse will be unable to use J2S in its present form. As mentioned earlier, the AST compilation model allows Eclipse JDT headless support, so this is not a major issue.
The Spring community would also understandably be interested in knowing, “does it work with Spring?�. The answer really depends on what you are trying to achieve. If you're aiming to build a standard SWT or Swing application, you would generally be using those technologies in the user interface layer to access a remote services layer. As such, your main Spring integration question concerns the availability of a suitable remoting mechanism. Spring offers you a broad choice of proven infrastructure for Java-to-Java remoting, with most projects opting for synchronous HttpInvoker, RMI or SOAP.
By generating a JavaScript-based client, J2S clearly requires some form of Java-to-JavaScript remoting. It is commonplace for Java-to-JavaScript remoting implementations to adopt an asynchronous approach, which means that execution continues immediately after a remoting invocation and there is a separate callback to handle the result of the invocation upon receipt. The two major approaches for Java-to-JavaScript remoting are DWR and JSON-RPC, although both GWT and J2S offer their own independent remoting approaches. Neither the GWT nor J2S approaches offer Spring integration out-of-the-box, although Spring's flexible architecture makes it quite easy to do so (as I'll show you in the case of J2S below).
Before we look at the Spring implementation, let's review how the J2S AJAX remoting protocol operates. J2S adopts a quasi command pattern for each potential remote call. The SimpleRPCRunnable superclass provides JavaScript-to-Java and Java-to-JavaScript serialization, with the subclass indicating the remote URL, fields to serialize and logic to execute remotely:
private transient SomeServicesLayer servicesLayer; // setter omitted
public String jsContent;
public String result;
public String getHttpURL() {
return "http://localhost:8080/echotest/simplerpc";
}
public void ajaxRun() {
result = servicesLayer.computeTheAnswer(jsContent);
jsContent = null;
}
}
The field declarations are important. Every public non-transient field will be serialized by SimpleRPCRunnable. The getHttpURL() specifies the URL of the J2S servlet. The same URL can be used for any J2S command, making it the J2S front controller for your application. The ajaxRun() method contains the logic that will be executed on the server side. In this case, our ajaxRun() method is accessing a local (server-side) Spring bean. Note the servicesLayer field is declared transient, which means that SimpleRPCRunnable will not serialize it. Instead the Spring IoC container will dependency inject the SomeServicesLayer instance into our server-side command object. Thus, servicesLayer is always null on the J2S client side. For a client to asynchronously invoke the command, they would use code such as:
public void ajaxIn() {
jsContent = sourceText.getText();
}
public void ajaxOut() {
resultText.setText(result);
}
});
As shown, the ajaxIn() method is used to set the public fields to acceptable values on the client side. The ajaxOut() method is the asynchronous callback handler, meaning it is executed once the command object is returned from the server and deserialized. In this case, the command is updating a UI widget. The screen shot below shows the result of executing the command as a JVM-hosted SWT application:

The next screen shot shows the result of executing the same command as a Firefox-hosted SWT application. No code or remoting configuration needed to change between these runtime targets, illustrating the flexibility and appeal of J2S' approach:

SimpleRPCSWTRequest also offers two static methods for declaring whether an invocation should actually occur across the wire. SimpleRPCSWTRequest.switchToLocalJavaThreadMode() will cause the ajaxRun() method to be invoked locally, which may be appropriate if you are running in a JVM-hosted SWT application. To cause invocations to be serialized across the wire (and thus ajaxRun() to execute on the server), simply invoke SimpleRPCSWTRequest.switchToAJAXMode(). This mode is compatible with both browser and JVM target platforms, so using J2S to build multi-target user interfaces does not necessitate the use of an additional remoting protocol (eg HttpInvoker or RMI) for the JVM target.
Over on the server-side, we are not using the normal J2S SimpleRPCHttpServlet. Instead we are using a new class called SpringRpcHttpServlet (which is available as a ZIP attachment, along with the rest of the code referred to in this blog entry). SpringRpcHttpServlet operates the same as the normal SimpleRPCHttpServlet, except it sources server-side command objects from the Spring application context. The code is well documented, so take a look in the ZIP attachment if you are interested in understanding how it works in detail. Essentially it allows you to define the commands and their dependencies in a Spring application context file.
If your application requires additional commands, it's simply a case of creating a SimpleRPCRunnable subclass and then adding it to your application context. Those following my work on ROO may be interested to hear I intend to provide J2S remoting integration, freeing you from the need to write command objects or invoke via SimpleRPCSWTRequest.
In conclusion, J2S promises some attractive benefits for projects that require JavaScript compilation or a web browser implementation of SWT. It also interoperates successfully with a Spring backend. J2S' deliberate choice to leverage proven existing technologies such as AST and SWT make it a good example of reusing existing code and developer skills, in turn lowering adoption barriers and the prospect of material API change. If you consider yourself an early adopter, SWT devotee, or need a client-centric, web-based user interface that is built upon the mature SWT UI framework, it is definitely worth taking a closer look at J2S.
Modified

Zhou Renjian says:
Added on January 22nd, 2007 at 7:53 amNice articles.
[quote post="118"]However, Eclipse JDT Core supports a headless mode and thus it wouldn't be difficult to execute J2S compilation from an Ant plugin or Maven mojo. [/quote]
In fact, We, J2S team, haven't figured out the way of executing J2S compilation outside Eclipse. In J2S compilation, AST bindings are required. And these calculated bindings are dependent on project's classpaths, referenced projects or others things. It is not an easy job , I think. As it's not an emergent job, this headless compiler won't come out soon.
Tim N. van der Leeuw says:
Added on January 23rd, 2007 at 7:18 amTo my knowledge, GWT also uses the Eclipse AST compiler. Since GWT is now open source, perhaps some ideas can be taken from their code for making use of 'headless support'.
Cheers,
–Tim
Dalibor Topic says:
Added on January 23rd, 2007 at 12:53 pmI'd stay away from it as long as its authors seem to be misappropriating proprietary code: http://j2s.svn.sourceforge.net/viewvc/j2s/trunk/sources/net.sf.j2s.java.core/src/java/lang/StringBuffer.java?revision=141&view=markup&sortby=date
Ben Alex (blog author) says:
Added on January 24th, 2007 at 8:57 pmLicensing issues are far from black and white.
Now that Java is released under GPL, it is arguable whether parsing source code via AST creates a derivative work. If it does create a derivative work, J2S may need to be released under GPL. That may conflict with J2S' similar use of SWT and JUnit, as neither of those are GPL licensed. This issue may be overcome by distributing the project as separate subprojects, each licensed differently. Although then you'd need to be careful of specific redistribution and "mere aggregation" requirements of licenses. It's notable that the mere act of using a GPL-licensed compiler and its associated GPL-licensed compiler header files does not in itself produce GPL-licensed software, as confirmed by FSF.
The above naturally assumes that merely parsing the Java code creates a derivative, and some may strongly argue that there is an important distinction between parsing, creating an alternative representation (such as an in-memory symbol map or output class file) and linking (or "binding" as FSF now say to cover both static and dynamic links, but excluding forking or exec functions!). Some may argue AST parsing is acceptable, but not if it creates an alternative representation (in-memory or on disk) that is licensed the same as the original. In that case, most AST usages would be severely constrained on account of licensing.
The FSF Java-specific position is that merely referring to another type (as in a superclass or a field or a method parameter or an instruction etc) in Java code creates a usage depended upon by your program and thus a derivative work. This is a very all-compassing interpretation. Then there is the whole argument of whether the GPL a contract or a license, and if it's a contract it's unenforceable in certain ways (FSF argues that it is simply a license, which effectively side-steps most theoretical legal issues). FSF also state that plugins using exec or forks are not derivatives of whatever calls them, but this distinction changes if there is shared memory.
One could argue the more literary treatment of derivative works should be applied, which is where getting into the above shared memory debate perhaps stems from. In other words, it's not just a case of a direct dependency that automatically creates a derivative, but instead the nature and extent of the dependency. To that end, one could perhaps rely on more robust ways of empirically measuring how much Class A depends on Class B to operate or Class B does its own extra work independent of Class A. This is actually what I'm presently working on for a research project, thus my interest in this topic.
I am certainly not providing an opinion on J2S licensing either way. I am not qualified to do so, and open source software licensing issues are subject of continuous academic debate (ie lecturers of law debate back and forth on these issues without clear consensus). There is also limited courtroom testing and an absence of theoretical models. As such, people should be very hesitant to declare a particular open source project as "misappropriating proprietary code" or similar, as there are generally as many arguments supporting such an assertion as there are against it.
david says:
Added on January 26th, 2007 at 4:07 amHow to SimpleSerializable supported the Map data type?
Dalibor Topic says:
Added on February 1st, 2007 at 12:11 pmI'm just saying that j2s is apparently using other people's proprietary code without their permission. That has nothing to do with GPL, since the code in question is not licensed under the GPL. Instead, the copyright header of the linked file says:
1 /*
2 * @(#)StringBuffer.java 1.78 03/05/16
3 *
4 * Copyright 2003 Sun Microsystems, Inc. All rights reserved.
5 * SUN PROPRIETARY/CONFIDENTIAL. Use is subject to license terms.
6 */
And the words 'proprietary' and 'confidential' seem to be quite clear to me in their meaning.
Zhou Renjian says:
Added on February 3rd, 2007 at 6:33 pmThanks Dalibor and Ben.
At last, J2S team decided to use modified version of Apache Harmony JRE 1.5 implementation under Apache License 2.0. Please check out the latest sources from SVN repository:
http://j2s.svn.sourceforge.net/viewvc/j2s/trunk/sources/net.sf.j2s.java.core/src/java/lang/StringBuffer.java?view=markup
BTW: Sun's Java 6 sources (Released at Nov 29, 2006) were labeled as "SUN PROPRIETARY/CONFIDENTIAL".
Brandon Smith says:
Added on February 7th, 2007 at 10:46 amThanks for this analysis.
I'd like to point out that JSON-RPC is an emerging protocol and language independent. JSON-RPC-Java is the project referenced but cited as the name of the protocol.
J. Custer says:
Added on February 8th, 2007 at 8:50 pmA good question was asked here, in Spring Framework forum:
http://forum.springframework.org/showthread.php?t=34066
Cristian Ebbens says:
Added on July 11th, 2007 at 2:53 pmHi. I would suggest all of you to take a look at http://www.jseamless.org. It's a very promising web framework, but it really needs to get some momentum.
Enjoy!
Cardiff says:
Added on July 31st, 2007 at 1:06 amThanks for the run down, some pretty useful stuff
shopping says:
Added on September 6th, 2007 at 6:49 pmI have a question. I recently say that they are standardizing JavaScript and Ajax. Why has this not been done before now? It would simplify things a lot for people trying to use them and for he use of them around the world. I am surprised that this has not been done before now. If there is not one set way for something as widely used as Java, would not a lot of problems could arise from people doing even the slightest different in anything? Anyone working on it would run into a wall with just one character being any different. And now there is debate about if it should be standardized? How can anyone have any doubts about this? I just do not see the point of anyone not wanting it to be uniform. With it being as it is now, what is the advantages of that? I would love any input that you may have on this subject.
business corporate gift says:
Added on October 3rd, 2007 at 5:23 amAre there any online tutorials, activities, exercises or modules for J2S web application using java.util.* API.? I’d like to use this in my next activity for my Computer students in relation to our Java lesson.
sharp aquos says:
Added on December 19th, 2007 at 9:08 pmAt last, J2S team decided to use modified version of Apache Harmony JRE 1.5 implementation under Apache License 2.0. Please check out the latest sources from SVN repository:
custom oil painting says:
Added on May 21st, 2008 at 3:55 amIt looks like you have presented the good things about J2S very well. No questions on these. But, as you know, SPEED still matters. If J2S, as you said, has some problems on this, is there any way that we can remedy this problem?