Using JSF 1.2 with Facelets on Google App Engine for Java
June 5th, 2009 by Christos Fragoulides

On April Google announced the support for Java on Google App Engine. I became aware of this last week and rushed to create an account and check it out. Since this is an ‘early look’ release, I had to wait until the guys at Google grant me the rights to use the service. Meanwhile I downloaded the SDK and started building a test application to check if the frameworks I mostly use are supported. My minimum requirements are JSF 1.2 with Facelets for templating (I also use ICEfaces but I can live without them). The results where positive while using the SDK on my computer but when I’ve uploaded the application on App Engine (my account was activated two days ago) I received a nasty error thrown during the initialization phase of JSF.

After hours of searching and debugging I finally managed to get it up and running. Now I’m going to list the steps involved. The most interesting and insightful resource I found is this post, which describes how to setup JSF on App Engine as a step in configuring JBoss Seam.
As the post author states, you’ll have to enable sessions in appengine-web.xml, then configure JSF as usually, then set it up to use JBoss’s EL implementation and finally use those patched classes in order to avoid API calls that are restricted by the security policy of App Engine. I only used the patched classes under ‘jboss-el’ and ‘jsf_mojarra’ since I don’t use Seam.

After this I added Facelets and gone through the necessary configuration steps, built the application and tried to run it on App Engine.

Problems Occurred (yes, of course, Murphy’s Law dictates it):

1) FacesServlet was not properly initialized. This is probably because App Engine does not initialize servlets at startup, instead initialization is postponed until the first request. As a result an IllegalStateException was thrown. To resolve the issue I had to add the following to web.xml:
<listener>
    <listener-class>
        com.sun.faces.config.ConfigureListener
    </listener-class>
</listener>

Error Message:
javax.servlet.ServletException: java.lang.IllegalStateException: Application was not properly initialized at startup, could not find Factory: javax.faces.context.FacesContextFactory

2) An error was thrown during FacesServlet initialization due to the use of a restricted class. After examining the stack trace I realized that JSF was trying to perform some XML validation and failed throwing a NoClassDefFoundError. I had no other option but to deactivate XML validation by setting the following at web.xml:
<context-param>
    <param-name>com.sun.faces.validateXml</param-name>
    <param-value>false</param-value>
</context-param>

Error Message:
java.lang.NoClassDefFoundError: com.sun.org.apache.xalan.internal.xsltc.runtime.BasisLibrary is a restricted class. Please see the Google App Engine developer’s guide for more details.

3) EL API classes were missing, had to include the EL API class library to the project.

Error Message:
java.lang.ClassNotFoundException: javax.el.CompositeELResolver
 

One last upload of the application after all the above tweaks and voilĂ ! The homepage loaded without any errors! The fact is that I didn’t have time to perform any further tests and for sure I cannot tell if all the features of JSF and Facelets will work normally. I’m waiting for your feedback on this. Good Luck!

Posted in JavaServer Faces, Web Applications

DecisiveGaming

So after you have made these changes have you seen any other problems? I am considering trying this out. Thanks for the info by the way!

Posted at June 29th, 2009 - 8:24 am

xfrag

@DecisiveGaming: No, as I state on the post I didn’t have the time to test further and I’m still pretty busy. But there were no errors in the application’s logs during the application’s startup phase and that’s a good sign.
If you have the time I’d be glad to know about any problems that you may encounter.

Posted at June 29th, 2009 - 10:26 am

Pankaj Soni

I am not using google app engine.
But faced FacesContext Factory and I am able to resolve that with

com.sun.faces.config.ConfigureListener

Thanks a lot

Posted at September 28th, 2012 - 11:16 pm

Post a Comment Below »
Please note: Comment moderation is enabled and may delay your comment. There is no need to resubmit your comment.

Java and all Java-based marks are trademarks or registered trademarks of Sun Microsystems, Inc. in the United States and other countries.