这里使用的简单验证是Struts2中最简单的验证.
但是不得不说,struts2的验证系统还是没有JSF的好用.
首先是struts.xml文件配置
<package name="default" namespace="/" extends="struts-default"> <!-- action name is Visit URL's path,you can write 'hello.jsp' or 'hello' or 'hello.action' --> <!-- <action name="hello"> result不写name,其实name就是 name="success" <result> /hello.jsp </result> </action> --> <!-- 如果不写class,默认执行的是Action所要继承的类:ActionSupport --> <action name="index" class="org.credo.action.IndexAction"> <!-- result不写name,其实name就是 name="success" --> <result> /index.jsp </result> <result name="error"> /userinfo/success.jsp </result> </action> </package>
这里新添加了result name=error的配置.而不写默认是success.
其次是action的配置.
package org.credo.action; import com.opensymphony.xwork2.ActionSupport; public class IndexAction extends ActionSupport{ /** * 企业开发一般都必须使用继承ActionSupport接口来做. */ private static final long serialVersionUID = 1L; private String name; public String execute(){ System.out.println("name:"+name); if(name == null || !name.trim().equals("admin")){ this.addFieldError("name", "name is error"); this.addFieldError("name", "name is too long"); this.addFieldError("name2", "name is too long"); return ERROR; } return SUCCESS; } public String getName() { return name; } public void setName(String name) { this.name = name; } }
在这里,可以看到this.addFieldError这个添加验证错误的信息.
接着就是UI页面:
<form action="index" method="post"> 姓名:<input type="text" name="name"></input> <input type="submit" value="submit" /> </form> </body> </html>
这里是一个简单的文版框,submit之后,用post传入到action类中.进行自动验证.
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%> <%@ taglib uri="/struts-tags" prefix="s" %> <% String path = request.getContextPath(); String basePath = request.getScheme()+"://"+request.getServerName()+":"+request.getServerPort()+path+"/"; %> <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> <html> <head> <base href="<%=basePath%>"> <title>My JSP 'MyJsp.jsp' starting page</title> <meta http-equiv="pragma" content="no-cache"> <meta http-equiv="cache-control" content="no-cache"> <meta http-equiv="expires" content="0"> <meta http-equiv="keywords" content="keyword1,keyword2,keyword3"> <meta http-equiv="description" content="This is my page"> <!-- <link rel="stylesheet" type="text/css" href="styles.css"> --> </head> <body> <s:text name="success">Success</s:text> <s:fielderror fieldName="name" theme="simple"/><br/> 123,filedName等于this.addFieldError("name", "name is error");中的"name",样式默认就为"simple"<br/> <br/> <s:property value="errors" /><br/> <s:property value="errors.name[1]"/> //errors是map,name是数组,so.... <br/> //下面是struts ValueStack debug,s:property可以通过NAME获取值. <s:debug></s:debug> </body> </html>
上面是跳转到的错误页面.
这里使用了2个struts2的标签.一个是<s:filedName>一个是<s:property>
第一个的说明很完全了.而第二个对应的是<s:debug>中的errors(是一个map)的value(是一个数组).filedName同理.
这里就是后台你手动传入的参数.
所有的struts2的验证,这个是最基本的,也是最常用的一个.
首要的目的是获取到request,session,application. HttpServletRequest,HttpServletSession,ServletContext的引用.
取得Map类型request,session,application,真实类型 HttpServletRequest, HttpSession, ServletContext的引用:
公用代码如下:
UI界面index.jsp代码:
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%> <%@ taglib uri="/struts-tags" prefix="s" %> <html> <body> This is my login page. <br> <br> 取得Map类型request,session,application,真实类型 HttpServletRequest, HttpSession, ServletContext的引用: <br/> <form action="" name="loginForm" id="loginFormId" method="post"> 用户名:<input type="text" name="name" id="nameId" /> 密 码:<input type="password" name="pwd" id="pwdId" /><br/> <input type="button" value="submit1" onclick="javascript:document.loginForm.action='login/login1';document.loginForm.submit();" /> <input type="button" value="submit2" onclick="javascript:document.loginForm.action='login/login2';document.loginForm.submit();" /> <input type="button" value="submit3" onclick="javascript:document.loginForm.action='login/login3';document.loginForm.submit();" /> <input type="button" value="submit4" onclick="javascript:document.loginForm.action='login/login4';document.loginForm.submit();" /> </form> </body> </html>
UI界面跳转的页面代码:
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%> <%@ taglib uri="/struts-tags" prefix="s" %> <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> <html> <body> Successful~~~~! <br> s:property是用标签访问ActionContext中的值,也就是StackContext.<br/> Stack Context--->These items are available using the #key notation!<br/> 所以可以使用Struts标签,来像下面代码那样直接获取值.<br/> <s:property value="#request.r1" />||<%=request.getAttribute("r1") %><br> <s:property value="#session.s1" />||<%=session.getAttribute("s1") %><br> <s:property value="#application.a1" />||<%=application.getAttribute("a1") %><br> <s:property value="#attr.r1" /><br> <s:property value="#attr.s1" /><br> <s:property value="#attr.a1" /><br> attr这个属性用的很少,因为不确定性,你该明白你把你的数据放在什么地方了.<br/> 如果request和session都有值的name,获取会获取第一个,由此出现问题. <s:debug></s:debug> </body> </html>
struts.xml配置文件:
<package name="login" namespace="/login" extends="struts-default"> <action name="login*" class="org.credo.action.LoginAction{1}"> <result>/login/success.jsp</result> </action> </package>
(一)最常用的方法:
package org.credo.action; import java.util.Map; import org.apache.struts2.interceptor.ApplicationAware; import org.apache.struts2.interceptor.RequestAware; import org.apache.struts2.interceptor.SessionAware; import com.opensymphony.xwork2.ActionSupport; /** * 依赖注入DI/控制反转IOC,本例是最常用的方法!!!!! */ public class LoginAction2 extends ActionSupport implements RequestAware,SessionAware,ApplicationAware{ private static final long serialVersionUID = 1L; private Map<String,Object> request; private Map<String,Object> session; private Map<String,Object> application; //依赖注入(DI),request依赖于容器(Struts2)调用RequestAwre方法注入数据. //控制反转 (IOC),把自己做的事情交给了别人去做. public String execute(){ request.put("r1", "r1"); session.put("s1", "s1"); application.put("a1", "a1"); return SUCCESS; } @Override public void setApplication(Map<String, Object> application) { this.application= application; } @Override public void setSession(Map<String, Object> session) { this.session=session; } @Override public void setRequest(Map<String, Object> request) { this.request=request; } }
(二)方法2:
package org.credo.action; import java.util.Map; import com.opensymphony.xwork2.ActionContext; import com.opensymphony.xwork2.ActionSupport; //这种方法依赖于Struts2,依赖于容器. @SuppressWarnings("rawtypes") public class LoginAction1 extends ActionSupport{ /** * 首要的目的是获取到request,session,application. HttpServletRequest,HttpServletSession,ServletContext的引用. * public class ActionContext implements Serializable { * static ThreadLocal actionContext = new ThreadLocal(); *如山是ActionContext的实现,是一个实现了序列化的本地线程.也就是说Context是整个线程中的运行环境. */ private static final long serialVersionUID = 1L; private Map request; private Map session; private Map application; //ActionContext就是<s:debug>显示的StackContext. //ActionContext public LoginAction1(){ //ActionContext.getContext()不是一个单例.是一个本地线程,ThreadLocal,但是在这个线程里他是单例. request=(Map) ActionContext.getContext().get("request"); session=ActionContext.getContext().getSession(); application=ActionContext.getContext().getApplication(); //request,session,application在页面中访问的是HttpServletRequest,HttpServletSession,ServletContext } // 后台MAP形式的request,session,application, //而前台的HttpServletRequest,HttpServletSession,ServletContext是Struts2把后台数据都填充到其中. @SuppressWarnings("unchecked") public String execute(){ request.put("r1", "r1"); session.put("s1", "s1"); application.put("a1", "a1"); return SUCCESS; } }
(三)方法3:
package org.credo.action; import javax.servlet.ServletContext; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpSession; import org.apache.struts2.ServletActionContext; import com.opensymphony.xwork2.ActionSupport; //固定写法,基本不用. public class LoginAction3 extends ActionSupport{ /** * */ private static final long serialVersionUID = 1L; private HttpServletRequest request; private HttpSession session; private ServletContext application; public LoginAction3(){ request=ServletActionContext.getRequest(); session=request.getSession(); application=session.getServletContext(); } public String execute(){ request.setAttribute("r1", "r1"); session.setAttribute("s1", "s1"); application.setAttribute("a1", "a1"); return SUCCESS; } }
(四)方法4:
package org.credo.action; import javax.servlet.ServletContext; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpSession; import org.apache.struts2.interceptor.ServletRequestAware; import com.opensymphony.xwork2.ActionSupport; public class LoginAction4 extends ActionSupport implements ServletRequestAware{ /** * 这个也是IOC的,但是实现的是ServletRequestAware接口.也不常用. */ private static final long serialVersionUID = 1L; private HttpServletRequest request; private HttpSession session; private ServletContext application; @Override public void setServletRequest(HttpServletRequest request) { this.request= request; this.session=request.getSession(); this.application=session.getServletContext(); } public String execute(){ request.setAttribute("r1", "r1"); session.setAttribute("s1", "s1"); application.setAttribute("a1", "a1"); return SUCCESS; } }