本教程介绍Struts2 JSR168 Portlet的开发,说明了开发基本内容和步骤,所实现Portlet的功能与文章《在RAD7中开发JSR168 Portlet》一致。
学习此篇教程前建议先学习developerworks上的这篇文章《基于 Struts 2 构建 WebSphere Portal 上的 Portlet 应用》,一些东西在这篇文章中介绍过在本文中就不再重复了。
http://www.ibm.com/developerworks/cn/websphere/library/techarticles/0802_yanzhid/
开发环境:Win2003+SP2,RAD 7.0.0.7
测试环境:Win2003+SP2,WebSphere Portal 6.0
Struts2版本:2.0.11.2
示例功能:在Portlet编辑视图中用户维护用户名和密码信息,在视图页面中显示保存的用户名和密码。
1. 启动RAD。
2. 新建Portlet项目。
选择“文件-》新建-》Portlet项目”。
将项目命名为Struts2DemoPortlet,因为是要部署在Portal6上的,目标运行时设置为“WebSphere Portal V6.0”,Portlet API选择“JSR 168 Portlet”。 不要选择“创建portlet”,用RAD自带向导创建的Struts Portlet还是struts1的。其它都接受默认值即可。
3.将struts-2.0.11.2/backport文件夹下的backport-util-concurrent-3.0.jar、
retrotranslator-runtime-1.2.2.jar、struts2-core-j4-2.0.11.2.jar、xwork-j4-2.0.5.jar和lib目录下的 ognl-2.6.11.jar、freemarker-2.3.8.jar 文件拷贝到portlet工程的WEB-INF/lib目录下。
在这里需要注意的是要拷j4的JAR 包,这是因为 WebSphere Portal Sever 6.0 基于 jdk1.4,j4的jar包就是Struts2支持JDK1.4的JAR文件。Portal6.1估计就能用正常的Struts jar包,有条件的人可以试试。
4.修改web.xml。双击 WEB-INF/web.xml,打开web部署描述符界面。
切换到过滤器选项卡,点击添加按钮,创建一个过滤器,名称设定为DemoFilter,URL映射为/*,并且使用现有的过滤器类org.apache.struts2.dispatcher.FilterDispatcher,如图所示,点击完成。
生成的web.xml描述文件内容如下所示:
<?xml version="1.0" encoding="UTF-8"?>
<web-app id="WebApp_ID" version="2.4" xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">
<display-name>
Struts2DemoPortlet</display-name>
<filter>
<description>
DemoFilter</description>
<display-name>
DemoFilter</display-name>
<filter-name>DemoFilter</filter-name>
<filter-class>org.apache.struts2.dispatcher.FilterDispatcher</filter-class>
</filter>
<filter-mapping>
<filter-name>DemoFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<welcome-file-list>
<welcome-file>index.html</welcome-file>
<welcome-file>index.htm</welcome-file>
<welcome-file>index.jsp</welcome-file>
<welcome-file>default.html</welcome-file>
<welcome-file>default.htm</welcome-file>
<welcome-file>default.jsp</welcome-file>
</welcome-file-list>
</web-app>
5.修改portlet.xml。双击portlet.xml,打开Portlet部署描述符界面,切换到portlet选项卡。点击添加按钮,添加一个portlet,输入portlet类型
org.apache.struts2.portlet.dispatcher.Jsr168Dispatcher,确定。编辑该portlet的其它信息,分别设定Portlet名称、显示名称、标题、简短标题、关键字。本示例中均输入Struts2DemoPortlet。如图所示。
接下来在本页中编辑受支持的方式text/html,添加portlet模式 view,edit。如图所示。
继续在本页中添加初始化参数,首先是Namespace相关的参数见表1:
名称 | 值 |
viewNamespace | /view |
editNamespace | /edit |
添加Action 相关的参数见表2:
名称 | 值 |
defaultViewAction | view |
defaultEditAction | edit |
这些参数指定了在portlet的两种模式下的默认aciton名称,进入View、Edit模式分别首先调用名称为 view、edit的action。
生成portlet.xml文件如下:
<?xml version="1.0" encoding="UTF-8"?>
<portlet-app xmlns="http://java.sun.com/xml/ns/portlet/portlet-app_1_0.xsd" version="1.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/portlet/portlet-app_1_0.xsd http://java.sun.com/xml/ns/portlet/portlet-app_1_0.xsd" id="com.ibm.portal.struts.portlet.StrutsPortlet.b72c5cb8b1">
<portlet>
<portlet-name>Struts2DemoPortlet</portlet-name>
<display-name>Struts2DemoPortlet</display-name>
<portlet-class>org.apache.struts2.portlet.dispatcher.Jsr168Dispatcher</portlet-class>
<init-param>
<name>viewNamespace</name>
<value>/view</value>
</init-param>
<init-param>
<name>editNamespace</name>
<value>/edit</value>
</init-param>
<init-param>
<name>defaultViewAction</name>
<value>view</value>
</init-param>
<init-param>
<name>defaultEditAction</name>
<value>edit</value>
</init-param>
<supports>
<mime-type>text/html</mime-type>
<portlet-mode>view</portlet-mode>
<portlet-mode>edit</portlet-mode>
</supports>
<portlet-info>
<title>Struts2DemoPortlet</title>
<short-title>Struts2DemoPortlet</short-title>
<keywords>Struts2DemoPortlet</keywords>
</portlet-info>
</portlet>
</portlet-app>
6.编辑jsp文件。在 WEB-INF下新建JSP文件夹,并生成几个jsp文件及内容如下:
view.jsp
<%@page language="java" contentType="text/html; charset=GB18030"
pageEncoding="GB18030" session="false" import="javax.portlet.*"%>
<%@ taglib prefix="s" uri="/struts-tags"%>
<%@taglib uri="http://java.sun.com/portlet" prefix="portlet"%>
<portlet:defineObjects />
<%
PortletPreferences preferences = renderRequest.getPreferences();
if( preferences!=null ) {
String username = (String)preferences.getValue("editUsername","");
String password = (String)preferences.getValue("editPassword","");
%>
<H2>用户信息</H2>
<p>用户名: <%=username%></p>
<p>密码: <%=password%></p>
<%
}
else {
%>错误:Portlet 首选项为空。<%
}
%>
edit.jsp
<%@page language="java" contentType="text/html; charset=GB18030"
pageEncoding="GB18030" session="false" import="javax.portlet.*"%>
<%@ taglib prefix="s" uri="/struts-tags"%>
<%@taglib uri="http://java.sun.com/portlet" prefix="portlet"%>
<portlet:defineObjects />
<%
PortletPreferences preferences = renderRequest.getPreferences();
if( preferences!=null ) {
String username = (String)preferences.getValue("editUsername","");
%>
<H2>请输入用户信息</H2>
<s:form action="UsrInfo" method="POST">
<s:textfield label="用户名" name="username" value="%{username}" />
<s:password label="密码" name="password" value="%{password}" />
<s:submit value="保存" />
</s:form>
<H2>已保存信息:</H2>
用户名:<%=username%>
<%
}
else {
%>错误:Portlet 首选项为空。<%
}
%>
success.jsp
<%@page language="java" contentType="text/html; charset=GB18030"
pageEncoding="GB18030" session="false"%>
<%@ taglib prefix="s" uri="/struts-tags"%>
<H2><s:property value="username" /> 信息提交成功</H2>
<p /><a href="<s:url action="edit"/>">返回编辑页面</a>
fail.jsp
<%@page language="java" contentType="text/html; charset=GB18030"
pageEncoding="GB18030" session="false"%>
<%@ taglib prefix="s" uri="/struts-tags"%>
<H2>未保存成功,请重试</H2>
<p /><a href="<s:url action="edit"/>">返回编辑视图</a>
7.建立Struts2配置文件struts.xml。
在 src 目录下建立struts.xml,工程构建之后struts.xml会被置于WEB-INF/classes下,这也是Struts2默认的配置文件路径。
从中可以看到edit视图的actoin的输入界面是edit.jsp,如果保存成功则会被转向success.jsp,失败则会被转向fail.jsp。
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE struts PUBLIC
"-//Apache Software Foundation//DTD Struts Configuration 2.0//EN"
"http://struts.apache.org/dtds/struts-2.0.dtd">
<struts>
<include file="struts-portlet-default.xml" />
<package name="view" extends="struts-portlet-default"
namespace="/view">
<action name="view">
<result>/WEB-INF/JSP/view.jsp</result>
</action>
</package>
<package name="edit" extends="struts-portlet-default"
namespace="/edit">
<action name="edit">
<result>/WEB-INF/JSP/edit.jsp</result>
</action>
<action name="UsrInfo" class="com.portlet.StrutsDemo.UsrInfo">
<result name="input">/WEB-INF/JSP/edit.jsp</result>
<result name="success">/WEB-INF/JSP/success.jsp</result>
<result name="fail">/WEB-INF/JSP/fail.jsp</result>
</action>
</package>
</struts>
8.新建java类UsrInfo.java
package com.portlet.StrutsDemo;
import javax.portlet.PortletPreferences;
import org.apache.struts2.dispatcher.DefaultActionSupport;
import org.apache.struts2.portlet.interceptor.PortletPreferencesAware;
public class UsrInfo extends DefaultActionSupport implements PortletPreferencesAware {
String username;
String password;
private PortletPreferences prefs;
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public void setPortletPreferences(PortletPreferences prefs) {
this.prefs = prefs;
}
public String execute() throws Exception {
try {
prefs.setValue("editUsername",username);
prefs.setValue("editPassword",password);
prefs.store();
return "success";
}
catch( Exception e ) {
return "fail";
}
}
}
注意在Struts中要获取PortletPreferences 的值要通过实现PortletPreferencesAware这个接口,具体方法参见代码,很简单,Struts帮我们已经实现了很多东西。
9.Struts2 的验证功能。构建项目后,在WEB-INF/classes/com/portlet/StrutsDemo/ 下创建UsrInfo-validation.xml,与UsrInfo.class 在同一目录中。
文件内容如下:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE validators PUBLIC
"-//OpenSymphony Group//XWork Validator 1.0.2//EN"
"http://www.opensymphony.com/xwork/xwork-validator-1.0.2.dtd">
<validators>
<field name="username">
<field-validator type="requiredstring">
<param name="trim">true</param>
<message>请输入用户名</message>
</field-validator>
</field>
<field name="password">
<field-validator type="requiredstring">
<param name="trim">true</param>
<message>请输入密码</message>
</field-validator>
</field>
</validators>
10.部署Portlet应用程序进行测试。
点击“个性化”进入编辑视图,在该页面中可以输入用户名和密码。如果从前有保存过用户名和密码,那么在下方会有用户名显示。
如果未填入参数值就保存,会提示用户需要输入信息,这就是Struts的验证功能。
信息提交成功会跳转到success.jsp页面。
View视图中显示用户和密码。
至此,一个简单的Struts2 Portlet就开发完成了。