1、结果集的使用方式
struts结果集的使用分为三种,指定全局结果集、普通方式指定结果集合动态指定结果集。
1.1全局结果集
当许多action都有共同的结果时,如果每个package都存在一个相同结果,比如success,error,input,needslogin等等,如果每一项都要重新配置,就显得配置文件很繁琐,所以使用全局的结果集。一个包内的全局结果集可以通过包的继承而被其它包使用。这样做的好处是:通用的结果集不用多次配置,减少struts.xml的配置量。
第一种配置方式:包继承方式配置
配置有全局结果集的包
<package name="main" namespace="/main" extends="struts-default"> <!-- 全局结果集 --> <global-results> <!-- 结果集类型为显示源代码的类型 --> <result name="error">/WEB-INF/page/error.jsp</result> </global-results> </package>
需要使用全局结果集的包需要继承该包
<package name="cn.test.action" namespace="/" extends="main" > <action name="global" class="cn.test.GlobalResult<span style="font-family: Arial, Helvetica, sans-serif;">"/> </package>
第二种配置方式直接在该包中定义全局结果集:
<package name="cn.test.action" namespace="/" extends="struts-default" > <global-results> <!-- 结果集类型为显示源代码的类型 --> <result name="error">/WEB-INF/page/error.jsp</result> </global-results> <action name="global" class="cn.test.GlobalResult" method="global"/> </package>
此时访问
package cn.test; public class GlobalResult{ public String execute(){ return "error"; } }
此时访问http://localhost:8081/struts2/global就会跳转到全局结果集配置的结果页面
1.2动态结果集
当一次访问可能会根据不同的逻辑出现不同的结果页面时,会用到动态结果集
Action类
package cn.test; public class DynamicResult { private String result; public String execute(){ if(result==null){ result="dynamicresult"; } return "success"; } public String getResult() { return result; } public void setResult(String result) { this.result = result; } }
Jsp页面
<?xml version="1.0" encoding="UTF-8"?> <%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%> <%@ taglib uri="/struts-tags" prefix="s" %> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> <title>OGNL表达式语言学习</title> </head> <body> <a href="dynamic/dynamic?result=login">login</a></br> <a href="dynamic/dynamic?result=main">main</a></br> </body> </html>
struts.xml
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE struts PUBLIC "-//Apache Software Foundation//DTD Struts Configuration 2.3//EN" "http://struts.apache.org/dtds/struts-2.3.dtd"> <struts> <package name="main" namespace="/main" extends="struts-default"> <!-- 全局结果集 --> <global-results> <!-- 结果集类型为显示源代码的类型 --> <result name="error">/WEB-INF/page/error.jsp</result> </global-results> </package> <constant name="struts.enable.DynamicMethodInvocation" value="false"/> <!-- 开启开发者模式 --> <constant name="struts.devMode" value="true"/> <!-- 开启修改struts.xml文件免启动 --> <constant name="struts.configuration.xml.reload" value="true"></constant> <!-- 开启OGNL静态方调用 --> <constant name="struts.ognl.allowStaticMethodAccess" value="true"></constant> <!-- 使用全局结果集 --> <package name="cn.test.action.global" namespace="/global" extends="main" > <action name="global" class="cn.test.GlobalResult" method="global"/> </package> <!-- 使用动态结果集 --> <package name="cn.test.action.dynamic" namespace="/dynamic" extends="main" > <action name="dynamic" class="cn.test.DynamicResult" > <result name="success">/WEB-INF/page/${result}.jsp</result> </action> </package> </struts>
2、结果集的类型
在struts2框架中,当action处理完之后,就应该向用户返回结果信息,该任务被分为两部分:结果类型和结果本身。
结果类型提供了返回给用户信息类型的实现细节。结果类型通常在Struts2中就已预定义好了(如下),或者是由插件提供,开发人员也可以自定义结果类型。默认配置的结果类型是dispatcher,该结果类型使用JSP来向用户显示结果。
struts2jar包struts-default.xml中定义的11种结果集类型
<result-types> <result-type name="chain" class="com.opensymphony.xwork2.ActionChainResult"/> <result-type name="dispatcher" class="org.apache.struts2.result.ServletDispatcherResult" default="true"/> <result-type name="freemarker" class="org.apache.struts2.views.freemarker.FreemarkerResult"/> <result-type name="httpheader" class="org.apache.struts2.result.HttpHeaderResult"/> <result-type name="redirect" class="org.apache.struts2.result.ServletRedirectResult"/> <result-type name="redirectAction" class="org.apache.struts2.result.ServletActionRedirectResult"/> <result-type name="stream" class="org.apache.struts2.result.StreamResult"/> <result-type name="velocity" class="org.apache.struts2.result.VelocityResult"/> <result-type name="xslt" class="org.apache.struts2.views.xslt.XSLTResult"/> <result-type name="plainText" class="org.apache.struts2.result.PlainTextResult" /> <result-type name="postback" class="org.apache.struts2.result.PostbackResult" /> </result-types>
其实常用的也就那么几种包括dispatcher、chain(可以理解为Action中的转发)、redirect、redirectAction、plainText和stream(下载文件的类型)。
struts.xml
<?xml version="1.0" encoding="UTF-8" ?> <!DOCTYPE struts PUBLIC "-//Apache Software Foundation//DTD Struts Configuration 2.3//EN" "http://struts.apache.org/dtds/struts-2.3.dtd"> <struts> <constant name="struts.enable.DynamicMethodInvocation" value="false"/> <!-- 开启开发者模式 --> <constant name="struts.devMode" value="true"/> <!-- 开启修改struts.xml文件免启动 --> <constant name="struts.configuration.xml.reload" value="true"></constant> <!-- 开启OGNL静态方调用 --> <constant name="struts.ognl.allowStaticMethodAccess" value="true"></constant> <package name="cn.test.action" namespace="/" extends="struts-default" > <action name="dispatcher" class="cn.test.TypeAction" method="success"> <!-- 默认情况下:type="dispatcher" --> <result name="success">/WEB-INF/page/main.jsp</result> </action> <action name="chain" class="cn.test.TypeAction" method="success"> <result type="chain" name="success">execute</result> <result name="success">/WEB-INF/page/login.jsp</result> </action> <action name="redirect" class="cn.test.TypeAction" method="success"> <!-- 类似于重定向到jsp,redirect还可以是重定向到Action了 --> <result type="redirect" name="success">login</result> </action> <action name="redirectAction" class="cn.test.TypeAction" method="success"> <!-- 类似于重定向到jsp,redirectAction只是重定向到Action了 --> <result type="redirectAction" name="success">login</result> </action> <action name="login" class="cn.test.TypeAction" method="login"> <result name="success">/WEB-INF/page/login.jsp</result> </action> <action name="execute" class="cn.test.TypeAction" method="execute"> <result name="success">/WEB-INF/page/main.jsp</result> </action> <action name="fileDown" class="cn.test.FileDown" method="execute"> <result type="stream" name="success"> <!-- 指定被下载文件的入口输入流 --> <param name="inputName">fileInputStream</param> <!-- 指定被下载文件名 --> <param name="contentDisposition">attachment;filename="${fileName}"</param> <!-- 指定被下载文件的文件类型 --> <param name="contentType">application/octet-stream</param> <!-- 指定下载文件时的缓冲大小 --> <param name="bufferSize">4096</param> </result> </action> <action name="plaintext" class="cn.test.TypeAction" method="plaintext"> <!-- 网页源代码 --> <result type="plainText" name="plaintext">/WEB-INF/page/login.jsp</result> </action> <action name="dynamic" class="cn.test.DynamicResult" > <result name="success">/WEB-INF/page/${result}.jsp</result> </action> </package> </struts>
Action类
package cn.test; import java.util.ArrayList; import java.util.HashMap; import java.util.HashSet; import java.util.List; import java.util.Map; import java.util.Set; import javax.security.auth.message.callback.PrivateKeyCallback.Request; import javax.servlet.ServletContext; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import javax.servlet.jsp.PageContext; import ognl.OgnlContext; import ognl.OgnlException; import org.apache.struts2.ServletActionContext; import com.opensymphony.xwork2.ActionContext; import com.opensymphony.xwork2.ActionSupport; import com.opensymphony.xwork2.util.ValueStack; public class TypeAction extends ActionSupport { public String success(){ System.out.println("方法为:"+"success"); HttpServletRequest request = ServletActionContext.getRequest(); request.setAttribute("key1", "测试dispatcher"); request.setAttribute("key2", "测试cahin"); request.setAttribute("key3", "测试redirect"); request.setAttribute("key4", "测试redirectAction"); System.err.println(); return SUCCESS; } public String plaintext(){ System.out.println("方法为:"+"plaintext"); HttpServletRequest request = ServletActionContext.getRequest(); request.setAttribute("key1", "测试dispatcher"); request.setAttribute("key2", "测试cahin"); request.setAttribute("key3", "测试redirect"); request.setAttribute("key4", "测试redirectAction"); System.err.println(); return "plaintext"; } public String execute() { System.out.println("方法为:"+"execute"); HttpServletRequest request = ServletActionContext.getRequest(); System.out.println(request.getAttribute("key1")); return SUCCESS; } public String login() { System.out.println("方法为:"+"login"); HttpServletRequest request = ServletActionContext.getRequest(); request.setAttribute("message","测试redirect"); System.out.println(request.getAttribute("key3")); return SUCCESS; } }
关于chain的说明:
/** * 说明 * 1)配置文件中result的type属性设置为chain, result标签内写传给的action的name属性值 * 2)action之间传递参数的实质是靠set和get方法,有没有对应的属性或属性名字叫什么其实没关系,一般情况下都是先写属性,再生成对应的set和get方法,这是 标准的做法,但不一定要这样做, 要想把action1中的参数a传递给action2中的b,只需action1中提供getXX方法返回a的值,action2中提供setXX方法给b 赋值即可 * 3)特别需要注意的一点是action1传给action2时除了拦截器chain起作用外,表单处理拦截器param也会起作用,而且param在chain之后起作用,故如果param和 chain都给同一个参数赋值的话,param会覆盖chain的效果,例如表单提交了一个c, action1里对c进行了处理, 处理结果还是保留在c上,接下来你想把处理后 的c传给action2处理,action2也用c来接收,这时候就会出现action2中的c的值是表单提交过来的值而不是action1传过来的值,给你一种参数没传递的错觉, 其实是被覆盖了,一般我的做法是action1中提供getB方法返回c的值,action2中不要提供setC而是提供setB来给c赋值 **/
关于redirectAction和redirect的说明
/** *说明 *当使用type=“redirectAction” 或type=“redirect”提交到一个action并且需要传递一个参数时。 *这里是有区别的: *1)使用type=“redirectAction”时,结果就只能写Action的配置名,不能带有后缀:“.action” *2)使用type=“redirect”时,结果应是action配置名+后缀名 * **/
原创文章,作者:奋斗,如若转载,请注明出处:https://blog.ytso.com/11187.html