struts2学习总结
1.struts2访问过程
a.客服端请求被web.xml中的filterdispatcher 拦截
b.filterdispatcher 读取struts2中的struts.xml配置
c.请求经过interceptor拦截器,执行正式业务逻辑之前的操作
d.请求经过Action,执行正式业务逻辑,并返回指向页面返回结果
e.显示结果页面
2.struts2开发流程
a.配置jar包
b.配置web.xml
c.配置struts.xml
d.配置ation
e.编写代码
f.运行验证
3.jsp引用struts2标签
<%@ taglib prefix="s" uri="/struts-tags" %>
4.配置web.xml
<filter>
<filter-name>struts2</filter-name>
<filter-class>
org.apache.struts2.dispatcher.ng.filter.StrutsP
repareAndExecuteFilter
</filter-class>
</filter>
<filter-mapping>
<filter-name>struts2</filter-name>
<url-pattern>*.action</url-pattern>
<url-pattern>*.jsp</url-pattern>
</filter-mapping>
5.配置struts.xml
<struts>
<package name="example" extends="struts-default" >
<action name="login" class="com.insigma.action.UserLoginAction" method="execute">
<result name="success">/jsp/success.jsp</result>
<result name="fail">/jsp/fail.jsp</result>
</action>
</package>
<struts>
6.Action类的作用
Action
指struts配置中指明的Action条目,表示浏览器的某类请求。比如,
关于用户的管理。
Action类
实现业务逻辑,可配置为响应客户端请求的JAVA类。可以扩展自
struts2预定义的类,也可以是POJO。
Action方法
Action类中的方法,被struts2调用,用来响应特定的客户端请求。
该方法返回控制字符串,以确定要显示的页面
完成业务逻辑
是业务逻辑的入口,由此开始处理整个业务逻辑。
2. 提供数据传递中介
通过在action中定义属性,及getter,setter方法,可以作为和页面数
据交换的载体。
3. 帮助框架确定返回页面
action方法,返回一个字符串,和struts.xml的配置匹配输出页面
7.Action类的三种编写方式
1.
继承ActionSupport
com.opensymphony.xwork2.ActionSupport。比较便利,
可以使用ActionSupport里面已经实现的方法。
2.
普通Java类
实现业务逻辑,可配置为响应客户端请求的JAVA类。可以扩
展自struts2预定义的类,也可以是POJO。
3.
实现Action接口
com.opensymphony.xwork2.Action。需要实现execute方
法。(ActionSupport也实现了此接口)
8.有2种方式可以访问Servlet环境对象:ActionContext类和
ServletActionContext
ActionContext ctx = ActionContext.getContext();
Map<String, Object> request = (Map<String, Object>)ctx.get("request");
Map<String, Object> session = ctx.getSession();
Map<String, Object> application = ctx.getApplication();
HttpServletRequest req = ServletActionContext.getRequest();
HttpSession ses = req.getSession();
ServletContext app = req.getServletContext();
9.Action类的传值
第一种,使用Action属性传递数据。
Action类中有一个和页面同名的属性
接收客户端的数据,需要提供该属性setter方法
传给页面数据,需要提供该属性getter方法
提供对象的getter,setter方法
对象丌需要建立,struts2通过反射自劢生成
在页面的struts标签中,使用“对象名.属性名”引用
10.action中的result的转发类型。
result name="success" type="dispatcher">/jsp/success.jsp</result>
常见的类型属性有 dispatcher, redirect, redirectAction, stream
dispatcher
默认的属性,相当于本站内的请求转发
Redirect
相当于请求重定向:<result type="redirect">/success.jsp?user=${userName}</result>
redirectAction
相当于请求重定向,到本站的一个action:<result type="redirectAction">testAction</result>
stream
返回流给客户端。
11.Action的查找次序。
定义:
命名空间:在struts.xml中的package节点里配置的namespace属性。
如果没有配置namespace属性,则认为是默认的命名空间。
假设是用户使用http://localhost:8080/abc/path1/path2/path3/login.action来提
交请求,struts2的查找次序:
按照就近原则的顺序,分别到struts.xml中到namespace为:
“/path1/path2/path3”, “path1/path2”, “/path1”, “/”的package。
如果丌存在,继续往上找;如果存在此package,则找对应的login.action, 如果找
丌到,则到默认的命名空间所在的package中去找。如果找丌到,则页面显示找丌
到对应的action。
简单形容:以上四个加上默认的package,比作房间。就近开始找房间,找丌到继
续往下找,一旦找到一个房间,后面丌再找其他房间。开始看房间里面有没有对应的
名字,如果没有,找默认的,如果默认的也没有,则提示找丌到
12.通配符访问Action中的方法
通配符访问Action中的方法。
一个Action中有多个业务方法,为了减少配置文件量,可以使用通配
符来配置:
<action name="user_*"
class="com.insigma.action.UserLoginAction" method="{1}">
如果使用 /abc/user_login 和 /abc/user_logout 分别会执行Action
中的login和logout方法
13.什么是OGNL
OGNL,即Object Graph Navigation Language,对象导
航图语言。是一个开源的,强大的表达式语言。用来读取Java
对象的属性。在Struts中对应的包是ognl-x.x.x.jar。
是Struts2的默认表达式语言,在Struts2中和标签库一起,用
来读取执行业务后,从后台返回的数据。
整个OGNL对象,是一个map结构,包含2部分,根对象和非
根对象。
语法直观易懂,比如对于一个Person类型的对象person,读
取属性的语法:
1.
在根对象中:person.name
2.
非根对象:#person.name
14.Struts2中OGNL结构
OGNL Map
application
session
root Value Stack
request
parameters
attr
Value Stack(值栈)为根对象,其他全部称为ActionContext(上下文)
根对象可以直接访问,上下文需要加“#”才能访问
Struts2的Action中被植入值栈,也就是根对象中。
由于丌是根对象,所以访问的时候需要加“#”
名称 作用对象 OGNL 等效JSP脚本
parameters 当前http请求的页面参数 #parameters.userName request.getParameter(“userName")
request 当前请求的HttpServletRequest对象 #request.userName request.getAttribute(“userName”)
session HttpSession对象 #session.userName session.getAttribute(“userName”)
application ServletContext #application.userName Application.getAttribute(“userName”)
attr 按parameters>request >session > application顺序访问 #attr.userName 依request,session,application顺序查找,直到找到为止
15.OGNL结合标签使用
16.Struts2标签库分类
控制标签
if, else, elseif, iterator
数据标签
property, action, url, a, set, date, debug
界面标签-表单类
form, textfield, password, checkbox, checkboxlist , radio, select
界面标签-非表单类
actionerror, actionmessage, fielderror
控制标签 if else elseif
控制标签 if else elseif 。用来判断条件
<s:set name="type" value="2"></s:set>
<s:if test="#type == 1">
选择的类型是1
</s:if>
<s:elseif test="#type == 2">
选择的类型是2
</s:elseif>
<s:else>
选择的类型是3
</s:else>
控制标签 iterator
控制标签 iterator。用来控制数据的迭代(遍历)
<s:iterator value="#attr.myList" id="language" status="t st">
<font color="<s:if test="#st.even">red</s:if>"><s:property
value="language"/></font><br/>
</s:iterator>
常用属性:
value:可选。被遍历的列表。如果丌填则遍历栈顶元素。
id:可选。指代遍历循环中的其中一个对象。
status:可选。指代org.apache.struts2.views.jsp.IteratorStatus中的属性。
boolean isEven()
boolean isOdd()
boolean isFirst()
boolean isLast()
数据标签 property
数据标签 property。用于输出一个指定的数据值
<s:set name="pTest" value="'property test'"></s:set>
<s:property value="#pTest"/>
常用属性:
value:可选。要输出的值,默认显示值栈栈顶元素。
default:可选。默认值,取丌到值的时候显示。
escapeHtml:可选。是否原样输出带有html标签的值,默认为true,输出的为带标签的值,
如value=‘abc<br/>’会原样输出。如果选择false ,则输出‘abc’并换行。
数据标签 action
数据标签 action。用于在页面中调用一个action
<s:action name="login" namespace="" executeResult="true">
<s:param name="userName">abc</s:param>
<s:param name="password">123</s:param>
</s:action>
常用属性:
name:必选。要执行的action。
namespace:可选。命名空间。
executeResult:可选。是否把返回结果嵌入到当前页面
数据标签 url
数据标签 url 。用于在页面中生成一个URL地址
<s:url action="login" namespace="/" id="loginUrl">
<s:param name="userName">abc</s:param>
<s:param name="password">123</s:param>
</s:url>
<s:a href="%{#loginUrl}">登录</s:a>
最终生成的URL地址类似:
http://localhost:8199/MyStruts2/login.action?userName=abc&password=123
常用属性:
action:可选。要执行的action。
namespace:可选。命名空间。
id:可选。被引用时候的名称。
数据标签 a
数据标签 a。用于在页面中生成一个URL地址
<s:a action="login" namespace="/" >
<s:param name="userName">abc</s:param>
<s:param name="password">123</s:param>
登录
</s:a>
最终生成的URL地址类似:
http://localhost:8199/MyStruts2/login.action?userName=abc&password=123
常用属性:
action:可选。要执行的action, 在value丌填的时候才使用。
namespace:可选。命名空间。
value:可选。目标请求,如果丌选使用action选顷。
onclick:可选。鼠标点击事件执行的JS凼数。
数据标签 set
数据标签 set 。用于在页面中生成一段数据,以备调用。
<s:set name="myList" value="{'Java', 'Android', 'C++', 'C#'}" ></s:set>
常用属性:
name:可选。被引用的名字。
value:可选。数据,可以为List也可以为Map。
scope:可选。有效范围。可以为application,session,request,page,action,默认为
action ,数据放入当前action的上下文中
数据标签 date
数据标签 date。用于格式化输出一个日期数据。
request.setAttribute("now", new java.util.Date());
<s:date name="#attr.now" format="yyyy-MM-dd"/>
常用属性:
name:必选。引用的日期属性名字。
format:可选。要转化的日期格式
数据标签 debug
数据标签 debug。用于在页面上输出当前页面的所有数据,用于调试。
<s:debug></s:debug>
常用属性:
无。
非常有用的标签,建议在开发阶段,碰到界面取丌到值,或者数据丌一致的情况打开使用。
界面标签-表单类 form
界面标签-表单类 form。用于创建一个HTML表单。
<s:form action="login" method="post">
<s:textfield label="用户名" name="userName"></s:textfield>
<s:password label="密码" name="password"></s:password>
<s:submit value="提交"></s:submit>
</s:form>
常用属性:
action:可选。提交的目标action,默认为当前action。
namespace:可选。命名空间。默认为当前命名空间。
method:可选。提交方式get/post
界面标签-表单类 textfield
界面标签-表单类 textfield。用于创建一个输入框。
<s:form action="login" method="post">
<s:textfield label="用户名" name="userName"></s:textfield>
<s:password label="密码" name="password"></s:password>
<s:submit value="提交"></s:submit>
</s:form>
常用属性:
name:可选。action接收数据的名称,即输入框的name属性。
label:可选。输入框前面的显示文本。
界面标签-表单类 password
界面标签-表单类 password。用于创建一个密码输入框。
<s:form action="login" method="post">
<s:textfield label="用户名" name="userName"></s:textfield>
<s:password label="密码" name="password"></s:password>
<s:submit value="提交"></s:submit>
</s:form>
常用属性:
name:可选。action接收数据的名称,即密码输入框的name属性。
label:可选。密码输入框前面的显示文本
界面标签-表单类 checkbox
界面标签-表单类 checkbox。用于创建一个复选框。
<s:checkbox name="checkbox" value="true" label="Java"
fieldValue="1"></s:checkbox>
<s:checkbox name="checkbox" value="false" label="C#"
fieldValue="2"></s:checkbox>
常用属性:
name:可选。action接收数据的名称,即name属性。
value:可选。true/false。是否选中当前复选框。
label:可选。复选框的名称。
fieldValue:可选。复选框的值,在form中提交后后台取到的数据
界面标签-表单类 checkboxlist
界面标签-表单类 checkboxlist。用于创建一组复选框,可以设置默认选
中项。
<s:checkboxlist list="students" name="stuCheck "
value="selected" listKey="id" listValue="name"></s:checkboxlist>
【后台代码参考本PPT备注】
需要后台准备所有显示的数据列表,和选中的数据列表。选中的数据列表需和listkey中的属性
匹配。
常用属性:
name:可选。action接收数据的名称,即name属性。
value:可选。属性值列表。对应属性值的复选框被选中。
list:必选。需要显示的所有数据列表。
listkey:可选。复选框中的值。如果在value列表里,则选中
listvalue:可选。复选框中的显示名称。
界面标签-表单类 radio
界面标签-表单类 radio。用于创建一组单选框,可以设置默认选中项。用
法和checkboxlist类似。
<s:radio list="students" name="stuRadio" listKey="id"
listValue="name" value="2"></s:radio>
【后台代码参考checkboxlist】
需要后台准备所有显示的数据列表,和选中的数据列表。选中的数据列表需和listkey中的属性
匹配。
常用属性:
name:可选。action接收数据的名称,即name属性。
value:可选。属性值。对应属性值的单选框被选中。
list:必选。需要显示的所有数据列表。
listkey:可选。单选框中的值。如果设置,则选中。
listvalue:可选。单选框中的显示名称
界面标签-表单类 select
界面标签-表单类 select。用于创建一个下拉框,可以设置默认选中项。用
法和checkboxlist,radio类似。
<s:select list="students" name="stuSelect" listKey="id"
listValue="name" value="2"></s:select>
【后台代码参考checkboxlist】
需要后台准备所有显示的数据列表,和选中的数据列表。选中的数据列表需和listkey中的属性
匹配。
常用属性:
name:可选。action接收数据的名称,即name属性。
value:可选。属性值。对应属性值的下拉框选顷被选中。
list:必选。需要显示的所有选顷列表。
listkey:可选。下拉框中的值。如果设置,则选中。
listvalue:可选。下拉框中选顷的显示名称。
界面标签-表单类 token
界面标签-表单类 token。用于防止数据被重复提交,
界面标签-非表单类 actionerror
actionmessage
界面标签-非表单类 actionerror, actionmessage。用于显示action
级别的错误和普通的通知消息。
if("abc".equals(userName) && "123".equals(password)){
addActionMessage("登录成功");
return "success";
}else{
addActionError("登录失败");
return "fail";
}
<s:actionerror/>
<s:actionmessage/>
界面标签-非表单类 fielderror
界面标签-非表单类 fielderror。用于显示表单提交的数据错误问题,可显
示所有消息,也可以指定某几个消息。
<s:form action="login" method="post">
<s:fielderror>
<s:param>userNameNull</s:param>
</s:fielderror>
<s:textfield label="用户名"
name="userName"></s:textfield>
<s:password label="密码"
name="password"></s:password>
<s:submit value="提交"></s:submit>
</s:form >
常用属性:
param:可选。指定的输出消息
17.Struts2文件上传
1. 准备好Struts2所需要的jar包 commons-fileupload-1.2.2.jar,
commons-o io-2.0.1.jar.(在最少需要的包里面已经包含)
. 2. form表单中,enctype属性设置为multipart/form-data
<s:form action="upload" method="post"
enctype="multipart/form-data">
<s:file label="请输入文件名" name="uploadFile"></s:file>
<s:submit value="上传"></s:submit>
</s:form>
3. Action中创建以下属性:
private File uploadFile;
private String uploadFileFileName;
private String uploadFileContentType;
4. Action方法,把文件拷贝到目标路径:
public String upload(){
//把保存在临时文件夹下的文件,拷贝到目标路径
String destPath =
ServletActionContext.getServletContext().getRealPath("/upload");
File destFile = new File(destPath);
destFile.mkdirs();
try {
FileUtils.copyFile(uploadFile, new File(destPath +
File.separator + uploadFileFileName));
} catch (IOException e) {
e.printStackTrace();
}
return "success";
文件大小限制
Struts2默认可以上传的文件大小为2M,超过这个大小的文件, 需要在
struts.xml中做单独配置:
<constant name="struts.multipart.maxSize" value="10000000" />
Struts2多文件上传
关键步骤:
. 1. 准备好Struts2所需要的jar包 commons-fileupload-1.2.2.jar, commons-
o io-2.0.1.jar.(在最少需要的包里面已经包含)
. 2. form表单中,enctype属性设置为multipart/form-data
<s:form action="uploadFiles" method="post"
enctype="multipart/form-data">
<s:file label="请输入文件名" name="uploadFiles"></s:file>
<s:file label="请输入文件名" name="uploadFiles"></s:file>
<s:submit value="上传"></s:submit>
</s:form>
3. Action中创建以下属性:
private File[] uploadFiles;
private String[] uploadFilesFileName;
private String[] uploadFilesContentType;
4.public String uploads(){
//拷贝临时文件到目标路径当中
String destPath = ServletActionContext.getServletContext().getRealPath("/upload");
try {
for (int i = 0; i < uploadFiles.length; i++) {
FileUtils.copyFile(uploadFiles[i], new File(destPath + File.separator + uploadFilesFileName[i]));
}
} catch (Exception e) {
e.printStackTrace();
}
return "success";
}
18.Struts2拦截器
Struts2中的核心功能都由拦截器来实现,如:避免表单重复提交,国际化,
对象组装,类型转化,文件上传,校验等,都是由拦截器来完成的。
Struts2设计了很多的拦截器,而丌放在Action基类戒者其他地方的好处:
解耦。因为可以使用拦截器来组装丌同的需求,使各功能模块变得可插拔。
Struts2已经实现了的拦截器配置放在: struts2-core-2.x.x.jar中的struts-default.xml中
Struts2拦截器原理
工作原理:一个请求过来后,丌是
直接去执行action中的业务逻辑。
而是先要经过已经定义好的拦截器
栈,依次执行各个拦截器(比如拦
截器1,2,3)里的业务,最后才到
action里面执行。执行完action
的业务后,再依次执行拦截器里的
业务(按照拦截器3,2,1的顺序),
最后浏览器才显示最终的页面。
任何一个拦截器的加入,都丌会影
响原有的业务逻辑的内部实现。而
是在原有的业务执行前后加了一段
操作。
我们编写的最简单的一个业务,实
际上已经经过了若干个拦截器的拦截
19.三种方式实现自定义拦截器
实现Interceptor接口
继承AbstractInterceptor类,此类也实现了Interceptor接口。
继承MethodFilterInterceptor,可以实现对方法的拦截(只有在执行Action某方法时拦截器才
做拦截)。
实现自定义拦截器的必须步骤:
编写拦截器类(继承或者实现以上3个中的一个)
重写intercept方法
public class TimeCalInterceptor implements Interceptor {…
@Override
public String intercept(ActionInvocation ai) throws Exception{
long start = System.currentTimeMillis();
String result = ai.invoke(); //执行action的业务
long end = System.currentTimeMillis();
System.out.println("action:" + ai.getAction() + "执行的时间是:" + (end -
start) + " 毫秒");
return result;
配置struts.xml文件
<package name="example" extends="struts-default">
<interceptors>
<interceptor name="timeCal"
class="com.insigma.interceptor.TimeCalInterceptor"></interceptor>
</interceptors>
<action name="login" class="com.insigma.action.UserLoginAction"
method="execute">
<interceptor-ref name="timeCal"></interceptor-ref>
<result name="input">/jsp/login.jsp</result>
<result name="fail">/jsp/fail.jsp</result>
</action>
</package>
20.作用于方法的拦截器
struts.xml
<interceptors>
<interceptor name="methodFilter"
class="com.insigma.interceptor.MyMethodFilterInterceptor"></interce
ptor>
</interceptors>
<action name=“login" class="com.insigma.action.UserLoginAction"
method="execute">
<interceptor-ref name="methodFilter">
<param name="includeMethods">test1</param>
<param name="excludeMethods">test2</param>
</interceptor-ref>
<result name="input">/jsp/login.jsp</result>
<result name="success" >/jsp/success.jsp</result>
<result name="fail">/jsp/fail.jsp</result>
</action>
说明:当param参数一个都丌定义的时候,所有方法都被拦截;当只定义
includeMethods时, includeMethods内的方法被拦截;当只定义
excludeMethods时,除了excludeMethods的方法外,其余都会被拦截;两者都
定义时,都生效,有冲突时,以include为准
21.默认拦截器
<default-interceptor-ref name="myStack"></default-interceptor-ref>
<interceptors>
<interceptor name="timeCal"
class="com.insigma.interceptor.TimeCalInterceptor"></interceptor>
<interceptor-stack name="myStack">
<interceptor-ref name="defaultStack"></interceptor-ref>
<interceptor-ref name="timeCal"></interceptor-ref>
</interceptor-stack>
</interceptors>
22.手工代码方式实现指定方法校验..
public void validateLogin(){
if(userName == null || "".equals(userName)){
this.addFieldError("userName", "请输入用户名");
}
if(password == null || "".equals(password)){
this.addFieldError("password", "请输入密码");
}
}
public String login(){ … return “success”;}
<action name="login" class="com.insigma.action.UserLoginAction"
method=“login">
基于XML配置文件方式的校验
Action也要继承自ActionSupport
编写校验配置文件xxx-validation.xml,xxx为Action类名,如
UserLoginAction。放在Action同级目录下。
<!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">
<message>请输入用户名</message>
</field-validator>
</field>
</validators>
field指的是要校验的页面属性,field-validator指的是对应的校验器,
requiredstring指的是系统已经实现的校验器,类似的校验器在xwork-core-
2.x.x.jar里面的com.opensymphony.xwork2.validator.validators包中的
default.xml中有定义
以上是对于execute方法的配置,如果要配置其他方法,只需要把配置文件
的名字改成xxx-yyy-validation.xml,其中yyy是Action中对应的业务方法名。
如login。最终文件名为:UserLoginAction-login-validation.xml
23.处理重复提交
<s:token></s:token>
<result name="invalid.token">login.jsp</result>
<interceptor-ref name="token"><intercepto显示r-ref>
24.Struts2图片验证码使用
Action:生成图片,并在session中保存图片内容。生成的图片,需要以流的方式传出来:
private ByteArrayInputStream inputStream;
public ByteArrayInputStream getInputStream() {
return inputStream;
}
struts.xml:配置一个action用来获取图片流:
<action name="authImg" class="com.insigma.action.ValidateImageAction">
<result type="stream">
<param name="contentType">image/jpeg</param>
<param name="inputName">inputStream</param>
</result>
</action>
jsp:使用img控件,获取图片:
<s:form theme="simple” action=“register”>
验证码:<s:textfield name="validateImg"></s:textfield>
<img src="<%=basePath %>authImg.action"/>
</s:form>
public class UserRegisterAction extends ActionSupport{
private String validateImg;
public void setValidateImg(String validateImg) {
this.validateImg = validateImg;
}
public void validate(){
String valideStr = (String)ActionContext.getContext().getSession().get("session4ValidateImg");
if(valideStr == null || !valideStr.equals(validateImg)){
this.addFieldError("validateImg", "验证码错误");
}
}
public String execute(){
return "success";
}
}
public class ValidateImgAction extends ActionSupport{
private ByteArrayInputStream inputStream;
public ByteArrayInputStream getInputStream() {
return inputStream;
}
public void setInputStream(ByteArrayInputStream inputStream) {
this.inputStream = inputStream;
}
public String execute(){
//把inputStream赋值上去
// 在内存中创建图象
int width = 60, height = 20;
BufferedImage image = new BufferedImage(width, height,
BufferedImage.TYPE_INT_RGB);
// 获取图形上下文
Graphics g = image.getGraphics();
// 生成随机类
Random random = new Random();
// 设定背景色
g.setColor(getRandColor(200, 250));
g.fillRect(0, 0, width, height);
// 设定字体
g.setFont(new Font("Times New Roman", Font.PLAIN, 18));
// 随机产生155条干扰线,使图象中的认证码不易被其它程序探测到
g.setColor(getRandColor(160, 200));
for (int i = 0; i < 155; i++) {
int x = random.nextInt(width);
int y = random.nextInt(height);
int xl = random.nextInt(12);
int yl = random.nextInt(12);
g.drawLine(x, y, x + xl, y + yl);
}
// 取随机产生的认证码(4位数字)
String sRand = "";
for (int i = 0; i < 4; i++) {
String rand = String.valueOf(random.nextInt(10));
sRand += rand;
// 将认证码显示到图象中
g.setColor(new Color(20 + random.nextInt(110),
20 + random.nextInt(110), 20 + random
.nextInt(110)));
// 调用函数出来的颜色相同,可能是因为种子太接近,所以只能直接生成
g.drawString(rand, 13 * i + 6, 16);
}
// 将认证码存入SESSION
ActionContext.getContext().getSession().put("session4ValidateImg", sRand);
// 图象生效
g.dispose();
ByteArrayOutputStream output = new ByteArrayOutputStream();
ImageOutputStream imageOut;
try {
imageOut = ImageIO.createImageOutputStream(output);
ImageIO.write(image, "JPEG", imageOut);
imageOut.close();
} catch (IOException e) {
e.printStackTrace();
}
ByteArrayInputStream input = new ByteArrayInputStream(output.toByteArray());
this.setInputStream(input);
return SUCCESS;
}
/*
* 给定范围获得随机颜色
*/
private Color getRandColor(int fc, int bc) {
Random random = new Random();
if (fc > 255){
fc = 255;
}
if (bc > 255){
bc = 255;
}
int r = fc + random.nextInt(bc - fc);
int g = fc + random.nextInt(bc - fc);
int b = fc + random.nextInt(bc - fc);
return new Color(r, g, b);
}
}
25.Struts2中使用JSON传输数据
引入struts2-json-plugin-2.3.14.jar包。
struts.xml中配置:
<package name="test" extends="json-default">
<action name="testJson" class="com.insigma.action.TestStruts2Json">
<result type="json" name="success"></result>
</action>
</package>
Action中:
private String userName;
private ArrayList<Account> accountList;
增加:[getter setter方法]
public String execute(){
userName = "用户名";
accountList = new ArrayList<Account>();
for (int i = 0; i < 5; i++) {
Account account = new Account();
account.setId(i);
account.setName("名字" + i);
accountList.add(account);
}
return "success";
Account.java:
public class Account {
private int id;
private String name;
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
通过访问:/testJson.action,页面上即显示后台自动生成的JSON数据。