基于 SSH 框架的 Criteria 和 DetachedCriteria 多条件查询
Hibernate 定义了 CriteriaSpecification 接口规范用来完成面向对象的条件查询,Criteria 和 DetachedCriteria 就是 CriteriaSpecification 的子接口。
在进行本篇的内容之前,我们先来大致说一说 Criteria 和 DetachedCriteria 的主要区别:
Criteria 和 DetachedCriteria 的创建的形式不一样, Criteria 是在线的,所以它是由 Hibernate Session 进行创建的;而 DetachedCriteria 是离线的,创建时无需 Session。
本篇完整实现如下:
一、导 jar 包
1 antlr-2.7.6.jar 2 asm-commons-3.3.jar 3 commons-collections-3.1.jar 4 commons-fileupload-1.3.jar 5 commons-io-2.0.1.jar 6 commons-lang3-3.1.jar 7 commons-logging-1.1.3.jar 8 dom4j-1.6.1.jar 9 freemarker-2.3.19.jar 10 hibernate3.jar 11 hibernate-jpa-2.0-api-1.0.1.Final.jar 12 javassist-3.12.0.GA.jar 13 jta-1.1.jar 14 mysql-connector-java-5.0.8-bin.jar 15 ognl-3.0.6.jar 16 slf4j-api-1.6.1.jar 17 spring-beans-4.3.8.RELEASE.jar 18 spring-context-4.3.8.RELEASE.jar 19 spring-core-4.3.8.RELEASE.jar 20 spring-expression-4.3.8.RELEASE.jar 21 spring-jdbc-4.3.8.RELEASE.jar 22 spring-orm-4.3.8.RELEASE.jar 23 spring-tx-4.3.8.RELEASE.jar 24 spring-web-4.3.8.RELEASE.jar 25 struts2-core-2.3.15.3.jar 26 struts2-spring-plugin-2.3.15.3.jar 27 xwork-core-2.3.15.3.jar
二、配置 Struts2 核心过滤器 (web.xml)
1 <filter> 2 <filter-name>struts2</filter-name> 3 <filter-class> 4 org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter 5 </filter-class> 6 </filter> 7 8 <filter-mapping> 9 <filter-name>struts2</filter-name> 10 <url-pattern>/*</url-pattern> 11 </filter-mapping>
三、Jsp 表单查询页 (list.jsp)
1 <%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%> 2 <%@ taglib uri="/struts-tags" prefix="s" %> 3 <% 4 String path = request.getContextPath(); 5 String basePath = request.getScheme()+"://"+request.getServerName() 6 +":"+request.getServerPort()+path+"/"; 7 %> 8 9 <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"> 10 <html> 11 <head> 12 <base href="<%=basePath%>"> 13 14 <title>My JSP 'index.jsp' starting page</title> 15 <meta http-equiv="pragma" content="no-cache"> 16 <meta http-equiv="cache-control" content="no-cache"> 17 <meta http-equiv="expires" content="0"> 18 <meta http-equiv="keywords" content="keyword1,keyword2,keyword3"> 19 <meta http-equiv="description" content="This is my page"> 20 <!-- 21 <link rel="stylesheet" type="text/css" href="styles.css"> 22 --> 23 </head> 24 25 <body> 26 <form action="${pageContext.request.contextPath}/queryCourseByCondition.action" 27 method="post"> 28 <table width="88%" border="0" class="emp_table" style="width:80%;"> 29 30 <tr> 31 <td width="20%">姓名:</td> 32 <td><input type="text" name="userName" size="30" value="" /></td> 33 </tr> 34 35 <tr> 36 <td >性别:</td> 37 <td > <select name="gender" id="sex"> 38 <option value="">--选择性别--</option> 39 <option value="男">男</option> 40 <option value="女">女</option> 41 </select> 42 </td> 43 </tr> 44 45 <tr> 46 <td >年龄:</td> 47 <td ><input type="text" name="ageStart" size="10" value="" /> 至 <input 48 type="text" name="ageEnd" size="10" value="" /></td> 49 </tr> 50 51 <tr> 52 <td>是否上传简历:</td> 53 <td ><select name="isUpload" id="isUpload"> 54 <option value="">--请选择--</option> 55 <option value="1">有</option> 56 <option value="2">无</option> 57 </select> 58 </td> 59 </tr> 60 61 <tr> 62 <td>信息备注:</td> 63 <td><input type="text" name="remark" size="30" value="" /></td> 64 </tr> 65 66 </table><br> 67 <input type="submit" value="查询"/> 68 <hr> 69 <table width="97%" border="1" > 70 71 <tr class="henglan" style="font-weight:bold;"> 72 <td width="14%" align="center">姓名</td> 73 <td width="13%" align="center">性别</td> 74 <td width="13%" align="center">年龄</td> 75 <td width="18%" align="center">简历</td> 76 <td width="20%" align="center">备注</td> 77 </tr> 78 79 <%--数据展示 --%> 80 <s:iterator> 81 <tr class="tabtd1"> 82 <td align="center"><s:property value="userName"/> </td> 83 <td align="center"><s:property value="gender"/></td> 84 <td align="center"><s:property value="age"/></td> 85 <td align="center"><s:property value="fileName"/></td> 86 <td align="center"><s:property value="remark"/></td> 87 </tr> 88 </s:iterator> 89 </table> 90 </form> 91 </body> 92 </html>
四、封装 UserBean (User.java)
1 package com.fhcq.bean; 2 3 import java.io.Serializable; 4 5 public class User implements Serializable { 6 7 private Integer userID; 8 private String userName; 9 private String gender; 10 private Integer age; 11 private String fileName; 12 private String remark; 13 14 public Integer getUserID() { 15 return userID; 16 } 17 public void setUserID(Integer userID) { 18 this.userID = userID; 19 } 20 public String getUserName() { 21 return userName; 22 } 23 public void setUserName(String userName) { 24 this.userName = userName; 25 } 26 public String getGender() { 27 return gender; 28 } 29 public void setGender(String gender) { 30 this.gender = gender; 31 } 32 public Integer getAge() { 33 return age; 34 } 35 public void setAge(Integer age) { 36 this.age = age; 37 } 38 public String getFileName() { 39 return fileName; 40 } 41 public void setFileName(String fileName) { 42 this.fileName = fileName; 43 } 44 public String getRemark() { 45 return remark; 46 } 47 public void setRemark(String remark) { 48 this.remark = remark; 49 } 50 51 }
五、配置数据库表生成策略 (User.hbm.xml)
1 <?xml version="1.0" encoding="UTF-8"?> 2 <!DOCTYPE hibernate-mapping PUBLIC 3 "-//Hibernate/Hibernate Mapping DTD 3.0//EN" 4 "http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd"> 5 <hibernate-mapping package="com.fhcq.bean"> 6 7 <!-- name是类名 如果有包就不用写全类名,否则要写。 table 表示对应的表名 。建议都要写 --> 8 <class name="User" table="user"> 9 10 <!--使用Id配置主键 必须配置 --> 11 <id name="userID" column="userID"> 12 <!--目前照常,主键生成策略 --> 13 <generator class="native"></generator> 14 </id> 15 16 <property name="userName" column="userName"></property> 17 <property name="gender" column="gender"></property> 18 <property name="age" column="age"></property> 19 <property name="filename" column="filename"></property> 20 <property name="remark" column="remark"></property> 21 22 </class> 23 </hibernate-mapping>
六、设置数据库连接参数 (hibernate.cfg.xml)
1 <!DOCTYPE hibernate-configuration PUBLIC 2 "-//Hibernate/Hibernate Configuration DTD 3.0//EN" 3 "http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd"> 4 5 <hibernate-configuration> 6 <session-factory name="foo"> 7 8 <!-- 配置数据库驱动 --> 9 <property name="hibernate.connection.driver_class"> 10 com.mysql.jdbc.Driver 11 </property> 12 <!-- 要连接数控的用户名 --> 13 <property name="hibernate.connection.username">root</property> 14 <!-- 密码 --> 15 <property name="hibernate.connection.password">123456</property> 16 <!-- 连接数据库的路径 那个服务器 那个数据库 --> 17 <property name="hibernate.connection.url"> 18 jdbc:mysql://localhost:3306/usermanager 19 </property> 20 21 <!-- 操作的时候显示操做过程中的sql语句 --> 22 <property name="show_sql">true</property> 23 <!-- 格式化它要显示的sql语句 --> 24 <property name="format_sql">true</property> 25 <!-- 是否要自动创建表 --> 26 <property name="hbm2ddl.auto">update</property> 27 <!-- 事务自动提交 --> 28 <property name="connection.autocommit">true</property> 29 30 <!-- 优化选项 --> 31 <property name="hibernate.dialect">org.hibernate.dialect.MySQLDialect</property> 32 <!-- 导入映射文件 --> 33 <mapping resource="com/fhcq/bean/User.hbm.xml" /> 34 35 </session-factory> 36 </hibernate-configuration>
七、配置 Struts (struts.xml)
1 <?xml version="1.0" encoding="UTF-8" ?> 2 <!DOCTYPE struts PUBLIC 3 "-//Apache Software Foundation//DTD Struts Configuration 2.3//EN" 4 "http://struts.apache.org/dtds/struts-2.3.dtd"> 5 6 <struts> 7 8 <!--修改struct2称为开发模式,修改配置之后会自动加载 --> 9 <constant name="struts.devMode" value="true"></constant> 10 11 <package name="package1" extends="struts-default"> 12 <!-- 多条件查询 --> 13 <action name="queryCourseByCondition" 14 class="com.fhcq.action.QueryUserByConditionAction" 15 method="queryCourseByCondition"> 16 <result name="success">/index.jsp</result> 17 </action> 18 </package> 19 20 </struts>
八、表示层
8.1、QueryUserByConditionAction
1 package com.fhcq.action; 2 3 import java.util.List; 4 5 import com.fhcq.bean.User; 6 import com.fhcq.service.IUserService; 7 import com.fhcq.service.UserServiceImpl; 8 import com.opensymphony.xwork2.ActionContext; 9 import com.opensymphony.xwork2.ActionSupport; 10 import com.opensymphony.xwork2.ModelDriven; 11 import com.opensymphony.xwork2.util.ValueStack; 12 13 public class QueryUserByConditionAction extends ActionSupport implements 14 ModelDriven<User>{ 15 16 User user= new User(); 17 private String ageStart; 18 private String ageEnd; 19 private String isUpload; 20 IUserService service; 21 22 public String queryCourseByCondition(){ 23 24 String userName = user.getUserName(); 25 String gender = user.getGender(); 26 String remark = user.getRemark(); 27 28 List<User> userlist = service.queryUserByCondition 29 (userName,gender,ageStart,ageEnd,isUpload,remark); 30 System.out.println("QueryUserByConditionAction queryUser() userlist= 31 "+userlist); 32 33 ActionContext context = ActionContext.getContext(); 34 ValueStack valueStack = context.getValueStack(); 35 valueStack.push(userlist); 36 37 return SUCCESS; 38 } 39 40 @Override 41 public User getModel() { 42 // TODO Auto-generated method stub 43 return user; 44 } 45 46 public User getUser() { 47 return user; 48 } 49 50 public void setUser(User user) { 51 this.user = user; 52 } 53 54 public String getIsUpload() { 55 return isUpload; 56 } 57 58 public void setIsUpload(String isUpload) { 59 this.isUpload = isUpload; 60 } 61 62 public String getAgeStart() { 63 return ageStart; 64 } 65 66 public void setAgeStart(String ageStart) { 67 this.ageStart = ageStart; 68 } 69 70 public String getAgeEnd() { 71 return ageEnd; 72 } 73 74 public void setAgeEnd(String ageEnd) { 75 this.ageEnd = ageEnd; 76 } 77 78 public IUserService getService() { 79 return service; 80 } 81 82 public void setService(IUserService service) { 83 this.service = service; 84 } 85 86 }
九、业务层
9.1、QueryUserService
1 package com.fhcq.service; 2 3 import java.util.List; 4 5 import com.fhcq.bean.User; 6 7 public interface IUserService { 8 9 List<User> queryUserByCondition(String userName, String gender,String ageStart, 10 String ageEnd, String isUpload,String remark); 11 }
9.2、QueryUserServiceImpl
1 package com.fhcq.service; 2 3 import java.util.List; 4 5 import com.fhcq.bean.User; 6 import com.fhcq.dao.IUserDao; 7 import com.fhcq.dao.UserDaoImpl; 8 9 public class UserServiceImpl implements IUserService{ 10 11 IUserDao dao; 12 13 @Override 14 public List<User> queryUserByCondition(String userName, String gender, 15 String ageStart, String ageEnd, String isUpload,String remark) { 16 // TODO Auto-generated method stub 17 List<User> queryUserByCondition = dao.queryUserByCondition 18 (userName,gender,ageStart,ageEnd,isUpload,remark); 19 return queryUserByCondition; 20 } 21 22 public IUserDao getDao() { 23 return dao; 24 } 25 26 public void setDao(IUserDao dao) { 27 this.dao = dao; 28 } 29 30 }
十、数据持久化层
10.1、QueryUserDao
1 package com.fhcq.dao; 2 3 import java.util.List; 4 5 import com.fhcq.bean.User; 6 7 public interface IUserDao { 8 9 List<User> queryUserByCondition(String userName, String gender, String ageStart, 10 String ageEnd, String isUpload, String remark); 11 12 }
Criteria 在线实现多条件查询:
10.2、配置 Spring (applicationContext.xml)
1 <?xml version="1.0" encoding="UTF-8"?> 2 <beans xmlns="http://www.springframework.org/schema/beans" 3 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 4 xsi:schemaLocation=" 5 http://www.springframework.org/schema/beans 6 http://www.springframework.org/schema/beans/spring-beans.xsd"> 7 8 <bean id="myUserDaoImpl" class="com.fhcq.dao.UserDaoImpl"></bean> 9 10 <bean id="service" class="com.fhcq.service.UserServiceImpl" > 11 <property name="dao" ref="myUserDaoImpl"></property> 12 </bean> 13 14 </beans>
10.3、HibernateUtils 方法封装
1 package com.fhcq.utils; 2 3 import org.hibernate.Session; 4 import org.hibernate.SessionFactory; 5 import org.hibernate.cfg.Configuration; 6 7 public class HibernateUtils { 8 9 static SessionFactory sessionFactory; 10 static { 11 Configuration configure = new Configuration().configure(); 12 sessionFactory = configure.buildSessionFactory(); 13 //增加 关闭虚拟机的时候自动释放 14 Runtime.getRuntime().addShutdownHook(new Thread(new Runnable(){ 15 @Override 16 public void run() { 17 // TODO Auto-generated method stub 18 System.out.println("当运行结束的时候执行!"); 19 sessionFactory.close(); 20 } 21 })); 22 } 23 24 public static Session getSession(){ 25 Session openSession = sessionFactory.openSession(); 26 return openSession; 27 } 28 29 public static Session getCurrentSession(){ 30 Session openSession = sessionFactory.getCurrentSession(); 31 return openSession; 32 } 33 }
10.4、QueryUserDaoImpl
1 package com.fhcq.dao; 2 3 import java.util.List; 4 5 import org.apache.commons.lang3.StringUtils; 6 import org.hibernate.Criteria; 7 import org.hibernate.Query; 8 import org.hibernate.Session; 9 import org.hibernate.SessionFactory; 10 import org.hibernate.cfg.Configuration; 11 import org.hibernate.criterion.Restrictions; 12 import org.springframework.orm.hibernate3.support.HibernateDaoSupport; 13 14 import com.fhcq.bean.User; 15 import com.fhcq.utils.HibernateUtils; 16 17 public class UserDaoImpl implements IUserDao{ 18 19 @Override 20 public List<User> queryUserByCondition(String userName, String gender, 21 String ageStart, String ageEnd, String isUpload, String remark) { 22 // TODO Auto-generated method stub 23 24 //如果查询页所有条件都没未填选的话,点击查询按钮则查询所有用户 25 if(StringUtils.isBlank(userName) && StringUtils.isBlank(gender) && 26 StringUtils.isBlank(ageStart) && StringUtils.isBlank(ageEnd) && 27 StringUtils.isBlank(isUpload) && StringUtils.isBlank(remark)){ 28 29 Session session = HibernateUtils.getSession(); 30 session.beginTransaction(); 31 //----------------------------- 32 Query createQuery = session.createQuery("from User"); 33 List<User> userlist = createQuery.list(); 34 //------------------------------ 35 session.getTransaction().commit(); 36 session.close(); 37 return userlist; 38 39 }else{ 40 41 Configuration configure = new Configuration().configure(); 42 SessionFactory sessionFactory = configure.buildSessionFactory(); 43 Session openSession = sessionFactory.openSession(); 44 //------------------------------ 45 46 Criteria createCriteria = openSession.createCriteria(User.class); 47 48 if(StringUtils.isNotBlank(userName)){ 49 createCriteria.add(Restrictions.like("userName", userName.replace 50 ("", ""))); 51 } 52 if(StringUtils.isNotBlank(gender)){ 53 createCriteria.add(Restrictions.eq("gender", gender)); 54 } 55 if(StringUtils.isNotBlank(ageStart)){ 56 Integer ageStart1 =Integer.parseInt(ageStart); 57 createCriteria.add(Restrictions.ge("age", ageStart1)); 58 } 59 if(StringUtils.isNotBlank(ageEnd)){ 60 Integer ageEnd1 =Integer.parseInt(ageEnd); 61 createCriteria.add(Restrictions.le("age", ageEnd1)); 62 } 63 if(StringUtils.isNotBlank(isUpload)){ 64 65 if("1".equals(isUpload)){ 66 67 createCriteria.add(Restrictions.isNotNull("fileName")); 68 69 }else{ 70 71 createCriteria.add(Restrictions.isNull("fileName")); 72 } 73 74 } 75 if(StringUtils.isNotBlank(remark)){ 76 createCriteria.add(Restrictions.like("remark", 77 remark.replace("", ""))); 78 } 79 80 List userlist = createCriteria.list(); 81 82 //------------------------------ 83 openSession.close(); 84 sessionFactory.close(); 85 return userlist; 86 87 } 88 } 89 }
DetachedCriteria 离线实现多条件查询:
10.2、配置 Spring (applicationContext.xml)
1 <?xml version="1.0" encoding="UTF-8"?> 2 <beans xmlns="http://www.springframework.org/schema/beans" 3 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 4 xsi:schemaLocation=" 5 http://www.springframework.org/schema/beans 6 http://www.springframework.org/schema/beans/spring-beans.xsd"> 7 8 <bean id="mysessionFactory" 9 class="org.springframework.orm.hibernate3.LocalSessionFactoryBean"> 10 <!-- hibernate.cfg.xml 告诉springHibernate的配置文件在哪 --> 11 <property name="configLocation" value="classpath:hibernate.cfg.xml"> 12 </property> 13 </bean> 14 15 <bean id="myHibernateTemplate" 16 class="org.springframework.orm.hibernate3.HibernateTemplate"> 17 <property name="sessionFactory" ref="mysessionFactory"></property> 18 </bean> 19 20 <bean id="myuserDaoImpl" class="com.fhcq.dao.UserDaoImpl"> 21 <property name="hibernateTemplate" ref="myHibernateTemplate"></property> 22 </bean> 23 24 <bean id="service" class="com.fhcq.service.UserServiceImpl" > 25 <property name="dao" ref="myuserDaoImpl"></property> 26 </bean> 27 28 </beans>
10.3、QueryUserDaoImpl
1 package com.fhcq.dao; 2 3 import java.util.List; 4 5 import org.apache.commons.lang3.StringUtils; 6 import org.hibernate.criterion.DetachedCriteria; 7 import org.hibernate.criterion.Restrictions; 8 import org.hibernate.criterion.MatchMode; 9 import org.springframework.orm.hibernate3.support.HibernateDaoSupport; 10 11 import com.fhcq.bean.User; 12 13 public class UserDaoImpl extends HibernateDaoSupport implements IUserDao{ 14 15 List<User> findByCriteria ; 16 17 @Override 18 public List<User> queryUserByCondition(String userName, String gender, 19 String ageStart, String ageEnd,String isUpload, String remark) { 20 // TODO Auto-generated method stub 21 //如果查询页所有条件都没未填选的话,点击查询按钮则查询所有用户 22 if(StringUtils.isBlank(userName) && StringUtils.isBlank(gender) && 23 StringUtils.isBlank(ageStart) && StringUtils.isBlank(ageEnd) && 24 StringUtils.isBlank(isUpload) && StringUtils.isBlank(remark)){ 25 26 findByCriteria = (List<User>) getHibernateTemplate().findByCriteria 27 (DetachedCriteria.forClass(User.class)); 28 29 }else{ 30 31 DetachedCriteria forClass = DetachedCriteria.forClass(User.class); 32 if(StringUtils.isNotBlank(userName)){ 33 forClass.add(Restrictions.like("userName", userName.replace 34 ("", ""), MatchMode.ANYWHERE)); 35 } 36 if(StringUtils.isNotBlank(gender)){ 37 forClass.add(Restrictions.eq("gender", gender)); 38 } 39 if(StringUtils.isNotBlank(ageStart)){ 40 Integer ageStart1 =Integer.parseInt(ageStart); 41 forClass.add(Restrictions.ge("age", ageStart1)); 42 } 43 if(StringUtils.isNotBlank(ageEnd)){ 44 Integer ageEnd1 =Integer.parseInt(ageEnd); 45 forClass.add(Restrictions.le("age", ageEnd1)); 46 } 47 if(StringUtils.isNotBlank(isUpload)){ 48 49 if("1".equals(isUpload)){ 50 51 forClass.add(Restrictions.isNotNull("fileName")); 52 }else{ 53 54 forClass.add(Restrictions.isNull("fileName")); 55 } 56 } 57 if(StringUtils.isNotBlank(remark)){ 58 forClass.add(Restrictions.like("remark",remark.replace 59 ("", ""), MatchMode.ANYWHERE)); 60 } 61 62 findByCriteria = (List<User>) getHibernateTemplate().findByCriteria 63 (forClass); 64 } 65 if(findByCriteria.size()>0){ 66 return findByCriteria; 67 } 68 return null; 69 } 70 71 }