In this tutorial, we will show you how to develop Struts 2 web application in Google App Engine (GAE) environment.

Tools and technologies used :

  1. JDK 1.6
  2. Eclipse 3.7 + Google Plugin for Eclipse
  3. Google App Engine Java SDK
  4. Struts
Before proceed on this tutorial, make sure you read this – GAE + Java example and Struts 2 hello world example.

1. New Web Application Project

In Eclipse, create a new Web Application project, named as “Struts2GoogleAppEngine”.

gae struts2 example new project

Google Plugin for Eclipse will generate a sample of GAE project structure. Later, we will show you how to integrate Struts2 with this generated GAE project.

gae struts2 example sample project

2. Integrate Struts 2 Libraries

Get following Struts 2 dependency libraries, download Struts2 here.

  • asm-3.3.jar
  • asm-commons-3.3.jar
  • asm-tree-3.3.jar
  • commons-fileupload-1.2.2.jar
  • commons-io-2.0.1.jar
  • commons-lang-2.5.jar
  • freemarker-2.3.18.jar
  • javassist-3.11.0.GA.jar
  • ognl-3.0.4.jar
  • struts2-core-
  • xwork-core-

Put all in “war/WEB-INF/lib” folder.

gae struts2 example libraries

Right click on the project folder, select “Properties” -> “Java Build Path” -> “Libraries” tab, click “Add Jars” button and select above 11 jars from “war/WEB-INF/lib” folder into the build path.

gae struts2 example java build path

3. Integrate Struts 2 Code

3.1 Delete the generated, you don’t need this.

3.2 Create a new Struts 2 Action class.

File : src/com/mkyong/user/action/

package com.mkyong.user.action;

public class WelcomeUserAction {

	private String username;

	public String getUsername() {
		return username;

	public void setUsername(String username) {
		this.username = username;

	public String execute() {

		return "SUCCESS";


3.3 Create a listener class, and set ognl security to null.

Struts 2 need this listener to run in GAE environment. Read this – Issues when deploying Struts 2 on GAE and Error: result ‘null’ not found

File : src/com/mkyong/listener/

package com.mkyong.listener;

import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;
import javax.servlet.http.HttpSessionAttributeListener;
import javax.servlet.http.HttpSessionBindingEvent;
import javax.servlet.http.HttpSessionEvent;
import javax.servlet.http.HttpSessionListener;

import ognl.OgnlRuntime;

public class Struts2ListenerOnGAE implements ServletContextListener,
		HttpSessionListener, HttpSessionAttributeListener {

	public void contextInitialized(ServletContextEvent sce) {

	public void contextDestroyed(ServletContextEvent arg0) {
		// TODO Auto-generated method stub


	public void sessionCreated(HttpSessionEvent arg0) {
		// TODO Auto-generated method stub


	public void sessionDestroyed(HttpSessionEvent arg0) {
		// TODO Auto-generated method stub


	public void attributeAdded(HttpSessionBindingEvent arg0) {
		// TODO Auto-generated method stub


	public void attributeRemoved(HttpSessionBindingEvent arg0) {
		// TODO Auto-generated method stub


	public void attributeReplaced(HttpSessionBindingEvent arg0) {
		// TODO Auto-generated method stub



3.4 To run Struts2 project in local GAE environment, you have to create a TextBlock class and overload the original TextBlok class, otherwise you will hit “javax.swing.tree.TreeNode is a restricted class” error message. Hope Struts2 team can fix this in future released.

TextBlock Source Code
Go this URL to download TextBlock source code.

3.5 Review project directory structure.

gae struts2 example directory

4. Integrate Struts 2 Pages

4.1 Create a login.jsp page, to accept user input.

File : war/User/pages/login.jsp

<%@ page contentType="text/html; charset=UTF-8" %>
<%@ taglib prefix="s" uri="/struts-tags" %>
<h1>GAE + Struts 2 Example</h1>

<s:form action="Welcome">
	<s:textfield name="username" label="Username"/>
	<s:password name="password" label="Password"/>


4.2 Create a welcome_user.jsp page.

File : war/User/pages/welcome_user.jsp

<%@ page contentType="text/html; charset=UTF-8" %>
<%@ taglib prefix="s" uri="/struts-tags" %>
<h1>GAE + Struts 2 Example</h1>

<h2>Hello <s:property value="username"/></h2>


4.3 Review project directory structure again.

gae struts2 example directory

5. Struts XML configuration

Create a struts.xml file, and put in “src/struts.xml“.

File : struts.xml

<?xml version="1.0" encoding="UTF-8" ?>
"-//Apache Software Foundation//DTD Struts Configuration 2.0//EN"


  <package name="user" namespace="/User" extends="struts-default">
	<action name="Login">
	<action name="Welcome" class="com.mkyong.user.action.WelcomeUserAction">
		<result name="SUCCESS">pages/welcome_user.jsp</result>


6. web.xml

Update web.xml, integrate Struts2 and configure ognl security listener.

File : web.xml

<?xml version="1.0" encoding="utf-8"?>
<web-app xmlns:xsi=""



7. Directory Structure

Review the final directory structure.

gae struts2 example final directory

8. Run on Local

Done, time to perform testing. Right click on the project, run as “Web Application“.

URL : http://localhost:8888/User/Login.action

gae struts2 example run on local
gae struts2 example run on local

9. Deploy on GAE

Update appengine-web.xml, put your App Engine application ID.

<?xml version="1.0" encoding="utf-8"?>
<appengine-web-app xmlns="">

  <!-- Configure java.util.logging -->
    <property name="java.util.logging.config.file" value="WEB-INF/"/>

Select project, click on Google icon, “Deploy to App Engine“. Google Plugin for Eclipse will deploy all necessary files to GAE production automatically.

gae struts2 example deploy to GAE

During deployment, following similar messages will be displayed in Eclipse console view.

------------ Deploying frontend ------------

Preparing to deploy:
	Created staging directory at: 'C:\Users\mkyong\AppData\Local\Temp\appcfg7432687551.tmp'
	Scanning for jsp files.
	Compiling jsp files.
	Scanning files on local disk.
	Initiating update.
	Cloning 2 static files.
	Cloning 46 application files.

	Uploading 12 files.
	Uploaded 3 files.
	Uploaded 6 files.
	Uploaded 9 files.
	Uploaded 12 files.
	Initializing precompilation...
	Sending batch containing 11 file(s) totaling 44KB.
	Sending batch containing 1 blob(s) totaling 1KB.
	Deploying new version.

Verifying availability:
	Will check again in 1 seconds.
	Will check again in 2 seconds.
	Will check again in 4 seconds.
	Closing update: new version is ready to start serving.

Updating datastore:
	Uploading index definitions.

Deployment completed successfully


gae struts2 example run on GAE
Finally, finished this long article. The overall integration is not much difficult, just need to fix Struts2 ognl security and TextBlock issues, hope Struts2’s team can fix this in future.

Download Source Code

Due to large file size, all Struts2 jars are excluded, you need to download it manually.

Download – (23 KB)


  1. Struts2 hello world example
  2. Google App Engine + Java hello world example, using Eclipse
  3. Apache Struts
  4. Struts 2 on GAE