JavaWeb上的Hibernate,最基本最基础的Hibernate工程,建立在Struts之前。
Hibernate是一个改写原来JDBC操作数据库的Java代码的一个东西。相当于Struts改写Html与Jsp等前台代码一样。
说白了,就是一个操作数据库增删改查的东西。
下面以一个账号注册系统来说明Hibernate如何查表,如何插入数据。当然,这东西完全可以用Java代码写,使用SQL语句,但SSH另立HQL语句与Hibernate也是没办法的事情。
一、目标
首先在Mysql的test数据库里面存在着一张表test,里面记录着账号信息
编写一个注册页面,输入用户名与密码按注册
如果帐号名已经存在,则返回这个注册页面,用Struts2输出错误信息
如果账号名不存在,说明注册成功,跳转至成功注册的页面
Hibernate对于这类的前台不起任何作用,仅在后台对Struts2的用户名与密码,对数据库中的表起条件查询、插入的操作。
二、基本思想
如图,
Hibernate其实就是对之前后台JDBC对于数据库的操作进行了规范化的改造。
三、基本过程
1.建立好前台的Struts工程,除了package com.hibernate.dao.*;package com.hibernate.po.*;hibernate.cfg.xml其余都是struts.xml的部分。
不赘述,详细可以看之前的文章《【Struts2】创造一个最简单、最基本的Struts2工程》(点击打开链接)
此乃本工程的struts.xml
<?xml version="1.0" encoding="GBK"?> <!DOCTYPE struts PUBLIC "-//Apache Software Foundation//DTD Struts Configuration 2.1.7//EN" "http://struts.apache.org/dtds/struts-2.1.7.dtd"> <struts> <package name="struts2" extends="struts-default"> <action name="register" class="com.hibernate.dao.usrRegister"> <result name="go">/WEB-INF/success.jsp</result> <result name="error">/index.jsp</result> </action> </package> </struts>
除了后台的Action不写,指定index.jsp中的表单的动作为register:
此乃本工程的index.jsp:
package com.hibernate.dao.*<%@ 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>注册页面</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> <strong><font color="red"><s:property value="error"/></font></strong> <s:form action="register" method="post"> <s:textfield name="username" label="用户名" /> <s:password name="password" label="密码" /> <s:submit value="注册" /> </s:form> <br> </body> </html>
至于success.jsp,就“注册成功”4个大字。
2.放入关于Hibernate的包与JDBC数据库链接驱动
将下载好的Hibernate中hibernate3.jar和lib路径下的required、jpa下的所有jar包,与JDBC数据库链接驱动mysql-connector-java-XXX.jar(XXX为版本号)都扔到网页工程文件夹里面的WEB-INF\lib。这是可以观察到WEB-INF\lib下有两个版本号不同的javassist.jar,这是没有影响的,不会产生版本冲突。
3.在...\src下,根据自己数据库的情况编写hibernate.cfg.xml
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE hibernate-configuration PUBLIC "-//Hibernate/Hibernate Configuration DTD 3.0//EN" "http://www.hibernate.org/dtd/hibernate-configuration-3.0.dtd"> <hibernate-configuration> <session-factory> <!--所用的数据库驱动 --> <property name="hibernate.connection.driver_class">com.mysql.jdbc.Driver</property> <!--所用的数据库登陆密码 --> <property name="hibernate.connection.password">root</property> <!--所用的数据库名称为test,根据实际更改 --> <property name="hibernate.connection.url">jdbc:mysql://localhost:3306/test</property> <!--所用的数据库用户名 --> <property name="hibernate.connection.username">root</property> <!--所用的数据库方言,与所用数据库驱动一样,可以在网上查到,这里是mysql --> <property name="hibernate.dialect">org.hibernate.dialect.MySQLInnoDBDialect</property> <property name="hibernate.format_sql">true</property> <!--如果是update表明Hibernate将保留原来的数据记录,插入时把新记录添加到已有的表,--> <!--如果是create,则总是创建新的表,如果原来数据库已有的这个表,则这个表的记录会被全部清洗 --> <property name="hibernate.hbm2ddl.auto">update</property> <!--罗列表与Java文件有多少个映射文件,这里仅有Usr.java与Usr.hbm.xml的一对,所以就写一个 --> <mapping resource="com/hibernate/po/Usr.hbm.xml" /> </session-factory> </hibernate-configuration>
4.创建package com.hibernate.po,然后在里面创建Usr.java与Usr.hbm.xml。这两个文件的文件名的首字母最好大写。文件名最好是一样的。
(1)关于Usr.java
package com.hibernate.po; public class Usr { private int id; private String username; private String password; public int getId() { return id; } public void setId(int id) { this.id = id; } public String getUsername() { return username; } public void setUsername(String username) { this.username = username; } public String getPassword() { return password; } public void setPassword(String password) { this.password = password; } }
这个文件与之前Struts工程的完全相似,里面充斥要操作的成员变量与getter,setter,只是成员变量需要进一步规范,都改成private,届时的DAO文件,也就是以前的Action类的Java文件,同样要创建相关的private类的成员变量。然后创建新的Usr类来操作相关的属性。
(2)关于Usr.hbm.xml
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN" "http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd"> <hibernate-mapping> <!-- 指定test表会映射到com.hibernate.po包下的Usr.java,然后对所有成员变量进行罗列 --> <class name="com.hibernate.po.Usr" table="test"> <!-- 自增的主键ID注意这样写,其余的变量类型必须写全java.lang.*否则可能读不到这个变量类型 --> <id name="id" type="java.lang.Integer"> <column name="id" /> <generator class="identity" /> </id> <property name="username" type="java.lang.String"> <column name="username" /> </property> <property name="password" type="java.lang.String"> <column name="password" /> </property> </class> </hibernate-mapping>
5.最后一步,也是最关键的一步,编写com.hibernate.dao包下的usrRegister.java,这个文件建议至少一个英文字母是大写的,否则struts.xml可能读不到
package com.hibernate.dao; import java.util.*;//下面要用到list类型 import org.hibernate.*; import org.hibernate.cfg.*; //这两个包不可或缺,轻重org.hibernate.*不代表其属下的所有文件,仅代表其下一级的文件, //所以org.hibernate.cfg.*同样必要 import com.hibernate.po.*; //把所有的PO拉过来 public class usrRegister { // 需要用到什么样的变量,则必须首先在这里声明,然后创建相关的getter与setter private String username; private String password; // 用来输出错误信息到前台 private String error = null; public String getError() { return error; } public void setError(String error) { this.error = error; } public String getUsername() { return username; } public void setUsername(String username) { this.username = username; } public String getPassword() { return password; } public void setPassword(String password) { this.password = password; } public String execute() throws Exception { SessionFactory sf = new Configuration().configure() .buildSessionFactory(); Session sess = sf.openSession(); Transaction tx = sess.beginTransaction(); //以上是数据库的固定链接语句,以下是固定的HQL查询语句。 //HQL查询语句是要从Usr这个类里面查,就是数据库中的整个表都映射到Usr这个类中 //“:username”与后面的setString方法想对应,getUsername()所产生的字符串,也就是前台传过来的username将会完全代替:username //为了不用想普通的JDBC一样,查询语句被用过量的字符串连接符打断不美观 //之后的list()与之前的sess是固定的方法。 List list = sess .createQuery("from Usr as u where u.username=:username") .setString("username", getUsername()).list(); //是否查到结果用list.size()>0来判断,返回true则查到结果,否则什么都没有查到 if (list.size() > 0) { setError("用户名已经存在!"); //以下三条是固定的数据库关闭语句 tx.commit(); sess.close(); sf.close(); //不成功,则返回一个error给前台 return "error"; } else { //以下是4条固定的HQL插入语句,把前台传过来的username,password插入到表中 Usr u = new Usr(); u.setUsername(getUsername()); u.setPassword(getPassword()); sess.save(u); tx.commit(); sess.close(); sf.close(); //成功,则返回一个go给前台 return "go"; } } }
至此,整个Hibernate工程的开发就全部完成,当然,实际开发的过程中不一定按照这个顺序,先用Struts开放前台的一部分,再用Hibernate写完整个后台,再用Struts完成前台。