更多Struts2在框架开发
1 OGNL,Struts2标签,值栈?
传统Servlet中,通常要把数据放入域对象中,然后在JSP页面使用EL表达式+JSTL标签的方法获取域对象里面的数据。在Struts2中,有类似于JSTL标签的专门的struts2标签,而且,Struts2本身提供了一种类似于域对象的存储机制,就是值栈。OGNL是一种类似于EL的一种表达式,并非Struts2特有的东西,但经常与struts2标签和值栈一起连用。
所以,在Struts2中对比传统Servlet: 在Action中将数据方法值栈中,然后在JSP页面使用OGNL表达式+struts2标签的方法获取值栈里面的数据。
2 采用OGNL+struts2标签+值栈
前记 : 案例承接自上一篇的案例快速入门Struts2(上篇)一个案例入门Struts2
案例目标: 在上篇案例(用户列表与添加功能)的基础上修改为OGNL+struts2标签的方法操作值栈,使用户列表功能和添加功能更加完美。
2.1 搭建项目环境
- OGNL表达式需要额外导入jar包: Struts2的jar包已经包含了OGNL需要的jar,所以导入Struts2的必要jar后,就不需要再去导入OGNL的jar包了。
- struts2标签的jar也已经随Struts2的必要包导入了,但是需要在JSP页面引入标签库
<!--引入struts标签库 -->
<%@ taglib uri="/struts-tags" prefix="s" %>
2.2 Action中向值栈存数据
修改UserAction.java页面的findAll()方法,更改数据的存放方法。
/**
* User web层
* @author zhaoyuqiang
*
*/
public class UserAction extends ActionSupport implements ModelDriven<User>{
/**
* 定义userList
*/
private List<User> userList ;
public List<User> getUserList() {
return userList;
}
/**
* 查询所有用户
* @return
*/
public String findAll() {
/**
* 利用Servlet的方式操作域对象 :
* 使用ServletActionContext类
* 只演示request域,session和ServletContext是类似的。
*/
/*List<User> userList = userService.findAll();
HttpServletRequest request = ServletActionContext.getRequest();
request.setAttribute("userList", userList); */
/**
* 向值栈中存放数据的三种方法之(1):最常用的方法
* 1. 给出私有变量(数值或对象或者集合)定义
* 2. 生成get方法
* 3. 该变量就是值栈
*/
userList = userService.findAll();
/**
* 向值栈中存放数据的三种方法之(2):使用set
* 1.获取值栈对象
* 2.调用set方法或者push方法
*/
/*ActionContext context = ActionContext.getContext();
ValueStack stack = context.getValueStack();
stack.set("userList",userService.findAll());
stack.push(userService.findAll());*/
return "success_findAll" ;
}
}
2.3 JSP中从值栈取数据
修改listAll.jsp页面,使用OGNL+struts2标签的形式获取值栈数据
<!--中间省略了很多代码无关代码-->
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
<!--引入struts标签库 -->
<%@ taglib uri="/struts-tags" prefix="s" %>
<table>
<tr>
<td>名字</td>
<td>年龄</td>
<td>手机</td>
</tr>
<!-- EL表达式+JSTL标签也能取到值栈中的数据 -->
<%-- <c:forEach items="${userList}" var="user">
<tr>
<td>${user.userName}</td>
<td>${user.userAge}</td>
<td>${user.userPhone}</td>
</tr>
</c:forEach> --%>
<!-- 使用OGNL+struts标签的方式取到值栈中的内容 -->
<s:iterator value="userList" var="user">
<tr>
<td><s:property value="#user.userName"/></td>
<td><s:property value="#user.userAge"/></td>
<td><s:property value="#user.userPhone"/></td>
</tr>
</s:iterator>
</table>
延伸:
如果获取一个字符串userName,则<s:property value="userName"/>
如果获取一个对象User,则<s:property value="user.userName"/>
其实,EL+JSTL也能从值栈取数据