在eclipse上使用Hibernate框架时,遵循以下四个步骤。
- 创建Hibernate的配置文件
- 创建持久化类
- 创建对象-关系映射文件
- 通过Hibernate API编写访问数据库的代码
慕课网上教学视频使用的是Hibernate4.x的版本,但视频比较旧了,现在我们学的时候大多数都是下载5.x以上的版本,这就不可避免地会出现许多问题,我在测试过程中也遇到了诸多问题,通过网上搜索,最终解决了这些问题,所以在此我总结一下,希望能帮到其他人。
在列出问题之前,我先给出编写第一个Hibernate例子的基本步骤,这里使用到的jar包如下:
- hibernate-release-5.2.12.Final.jar
- mysql-connector-java-5.1.30.jar
- junit-4.10.jar
- hibernatetools-Update-4.1.2.Final_2014-03-18_15-46-19-B706.zip
这些jar都可以从网上或官网下载得到。
首先需要给eclipse安装上Hibernate Tools插件
打开eclipse->help->Install New Sofaware
这里我们点add->Archive,找到下载好的Hibernate Tools插件压缩包
然后默认全选,一直点Next,最后finish,eclipse会提示你需要重启,这里我们重启,然后new project时选择other,若出现下面的Hibernate,提示插件安装成功。
然后导入上面提到的三个包,hibernate-release-5.2.12.Final.jar,mysql-connector-java-5.1.30.jar,junit-4.10.jar
接下来,我们创建一个配置文件。
创建hibernate.cfg.xml
在新建的HibernateDemo上右键new->other->Hibernate Configuration File.
放在src目录下就可以,按下next后直接finish。
然后填写hibernate.cfg.xml中的配置信息,
我们可以采用补全的方式来帮助我们完成配置,按下alt+/就会出现,若没有出现补全提示,需要手工导入dtd文档的支持。
该文档的位置在
hibernate-release-5.2.12.Final\project\hibernate-core\src\main\resources\org\hibernate\hibernate-mapping-3.0.dtd
打开hibernate.cfg.xml文件,补充配置信息
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-configuration PUBLIC
"-//Hibernate/Hibernate Configuration DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-configuration-3.0.dtd">
<hibernate-configuration>
<session-factory>
<!-- 数据库登录用户名 -->
<property name="connection.username">root</property>
<!-- 数据库登录密码 -->
<property name="connection.password">root</property>
<!-- JDBC驱动名 -->
<property name="connection.driver_class">com.mysql.jdbc.Driver</property>
<!-- localhost为连接本地数据库,hibernate是数据库名 -->
<property name="connection.url">jdbc:mysql://localhost/hibernate</property>
<!-- 配置数据库方言,注意MySQL5.7以上版本要这样填写 -->
<property name="dialect">org.hibernate.dialect.MySQL5InnoDBDialect</property>
<!-- 后台输出sql语句 -->
<property name="show_sql">true</property>
<!-- format_sql将sql语句格式化 -->
<property name="hbm2ddl.auto">create</property>
<!-- currentSession配置 -->
<property name="hibernate.current_session_context_class">thread</property>
<mapping resource="Student.hbm.xml"/>
</session-factory>
</hibernate-configuration>
创建持久化类
创建Student类作为持久化类
import java.util.Date;
public class Student {
private int id;
private String sex;
private String name;
private Date birth;
private String address;
public Student() {
}
public Student(int id, String sex, String name, Date birth, String address) {
this.id = id;
this.sex = sex;
this.name = name;
this.birth = birth;
this.address = address;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getSex() {
return sex;
}
public void setSex(String sex) {
this.sex = sex;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Date getBirth() {
return birth;
}
public void setBirth(Date birth) {
this.birth = birth;
}
public String getAddress() {
return address;
}
public void setAddress(String address) {
this.address = address;
}
@Override
public String toString() {
return "Student [id=" + id + ", sex=" + sex + ", name=" + name
+ ", birth=" + birth + ", address=" + address + "]";
}
}
创建对象——关系映射文件
在项目的src上右键new->other,选中
然后点Add Package,选择Student类选在的包,然后next->finish
Tools工具就为我们生成了映射文件
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<!-- Generated 2018-1-26 15:00:38 by Hibernate Tools 3.4.0.CR1 -->
<hibernate-mapping>
<class name="Student" table="STUDENT">
<id name="id" type="int">
<column name="ID" />
<generator class="assigned" />
</id>
<property name="sex" type="java.lang.String">
<column name="SEX" />
</property>
<property name="name" type="java.lang.String">
<column name="NAME" />
</property>
<property name="birth" type="java.util.Date">
<column name="BIRTH" />
</property>
<property name="address" type="java.lang.String">
<column name="ADDRESS" />
</property>
</class>
</hibernate-mapping>
通过Hibernate API编写访问数据库的代码
创建StudentTest类
import java.util.Date;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.cfg.Configuration;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;
public class StudentTest {
private SessionFactory sessionFactory;
private Session session;
private Transaction transaction;
@Before
public void init(){
//创建配置对象
Configuration config = new Configuration().configure();
//Hibernate5.x版本创建会话工厂对象
sessionFactory = config.buildSessionFactory();
//Hibernate5.x版本创建会话对象
session = sessionFactory.getCurrentSession();
//开启事务
transaction = session.beginTransaction();
}
@After
public void destroy(){
//提交事务
transaction.commit();
}
@Test
public void testSaveStudent(){
//实例化学生对象
Student stu = new Student(1,"男","selves",new Date(),"scau");
//保存对象进入数据库
session.save(stu);
}
}
然后右键点击Run As->JUnit Test
绿条表示没有异常,观察控制台输出
末尾处出现建表语句和插入语句
一月 26, 2018 5:10:47 下午 org.hibernate.Version logVersion
INFO: HHH000412: Hibernate Core {5.2.12.Final}
一月 26, 2018 5:10:47 下午 org.hibernate.cfg.Environment <clinit>
INFO: HHH000206: hibernate.properties not found
一月 26, 2018 5:10:47 下午 org.hibernate.boot.jaxb.internal.stax.LocalXmlResourceResolver resolveEntity
WARN: HHH90000012: Recognized obsolete hibernate namespace http://hibernate.sourceforge.net/hibernate-configuration. Use namespace http://www.hibernate.org/dtd/hibernate-configuration instead. Support for obsolete DTD/XSD namespaces may be removed at any time.
一月 26, 2018 5:10:47 下午 org.hibernate.annotations.common.reflection.java.JavaReflectionManager <clinit>
INFO: HCANN000001: Hibernate Commons Annotations {5.0.1.Final}
一月 26, 2018 5:10:47 下午 org.hibernate.boot.jaxb.internal.stax.LocalXmlResourceResolver resolveEntity
WARN: HHH90000012: Recognized obsolete hibernate namespace http://hibernate.sourceforge.net/hibernate-mapping. Use namespace http://www.hibernate.org/dtd/hibernate-mapping instead. Support for obsolete DTD/XSD namespaces may be removed at any time.
一月 26, 2018 5:10:48 下午 org.hibernate.engine.jdbc.connections.internal.DriverManagerConnectionProviderImpl configure
WARN: HHH10001002: Using Hibernate built-in connection pool (not for production use!)
一月 26, 2018 5:10:48 下午 org.hibernate.engine.jdbc.connections.internal.DriverManagerConnectionProviderImpl buildCreator
INFO: HHH10001005: using driver [com.mysql.jdbc.Driver] at URL [jdbc:mysql://localhost/hibernate]
一月 26, 2018 5:10:48 下午 org.hibernate.engine.jdbc.connections.internal.DriverManagerConnectionProviderImpl buildCreator
INFO: HHH10001001: Connection properties: {user=root, password=****}
一月 26, 2018 5:10:48 下午 org.hibernate.engine.jdbc.connections.internal.DriverManagerConnectionProviderImpl buildCreator
INFO: HHH10001003: Autocommit mode: false
一月 26, 2018 5:10:48 下午 org.hibernate.engine.jdbc.connections.internal.PooledConnections <init>
INFO: HHH000115: Hibernate connection pool size: 20 (min=1)
Fri Jan 26 17:10:48 CST 2018 WARN: Establishing SSL connection without server's identity verification is not recommended. According to MySQL 5.5.45+, 5.6.26+ and 5.7.6+ requirements SSL connection must be established by default if explicit option isn't set. For compliance with existing applications not using SSL the verifyServerCertificate property is set to 'false'. You need either to explicitly disable SSL by setting useSSL=false, or set useSSL=true and provide truststore for server certificate verification.
一月 26, 2018 5:10:49 下午 org.hibernate.dialect.Dialect <init>
INFO: HHH000400: Using dialect: org.hibernate.dialect.MySQL5InnoDBDialect
Hibernate: drop table if exists STUDENT
一月 26, 2018 5:10:50 下午 org.hibernate.resource.transaction.backend.jdbc.internal.DdlTransactionIsolatorNonJtaImpl getIsolatedConnection
INFO: HHH10001501: Connection obtained from JdbcConnectionAccess [org.hibernate.engine.jdbc.env.internal.JdbcEnvironmentInitiator$ConnectionProviderJdbcConnectionAccess@72e34f77] for (non-JTA) DDL execution was not in auto-commit mode; the Connection 'local transaction' will be committed and the Connection will be set into auto-commit mode.
Hibernate: create table STUDENT (ID integer not null, SEX varchar(255), NAME varchar(255), BIRTH datetime, ADDRESS varchar(255), primary key (ID)) engine=InnoDB
一月 26, 2018 5:10:50 下午 org.hibernate.resource.transaction.backend.jdbc.internal.DdlTransactionIsolatorNonJtaImpl getIsolatedConnection
INFO: HHH10001501: Connection obtained from JdbcConnectionAccess [org.hibernate.engine.jdbc.env.internal.JdbcEnvironmentInitiator$ConnectionProviderJdbcConnectionAccess@4a8ab068] for (non-JTA) DDL execution was not in auto-commit mode; the Connection 'local transaction' will be committed and the Connection will be set into auto-commit mode.
一月 26, 2018 5:10:50 下午 org.hibernate.tool.schema.internal.SchemaCreatorImpl applyImportSources
INFO: HHH000476: Executing import script 'org.hibernate.tool.schema.internal.exec.ScriptSourceInputNonExistentImpl@644c78d4'
Hibernate: insert into STUDENT (SEX, NAME, BIRTH, ADDRESS, ID) values (?, ?, ?, ?, ?)
打开Navicat Premium
数据库显示正常,说明Demo测试成功。
接下来是测试Demo过程中遇到的问题及解决方法,其实很多问题都是由于4.x版本与5.x版本存在很大差异造成的。
1.抛出异常
org.hibernate.MappingException: Unknown entity: Student
解决方法:
// 4.x版本中Init()方法中定义
//1.获取配置对象
Configuration configuration = new Configuration().configure();
//2.获取服务注册对象
// 需要特别注意的是:hibernate4.3.x版本中 ServiceRegistryBuilder
// 已过时--"Deprecated. Use StandardServiceRegistryBuilder instead",
// 得用StandardServiceRegistryBuilder,也就是它的父类代替
ServiceRegistry serviceRegistry = new StandardServiceRegistryBuilder().applySettings(configuration.getProperties()).build();
//3.创建会话工厂对象
sessionFactory = config.buildSessionFactory(serviceRegistry);
//4.创建会话对象
session = sessionFactory.getCurrentSession();
//5.创建事务对象
transaction = session.beginTransaction();
// 5.0及以上版本——不用通过ServiceRegistry
//1.获取配置对象
Configuration configuration = new Configuration().configure();
//2.免服务注册直接创建会话工厂对象
sessionFactory = new Configuration().configure().buildSessionFactory();
//3.创建会话对象
session = sessionFactory.getCurrentSession();
//4.创建事务对象
transaction = session.beginTransaction();
2.抛出异常
Executing import script 'org.hibernate.tool.schema.internal.exec.ScriptSourceInputNonExistentImpl
解决方法:
这其实是数据库方言配置问题,我们如果使用的是MySQL5.x的版本,那么,我们需要修改hibernate.cfg.xml中的配置:
<property name="dialect">org.hibernate.dialect.MySQL5InnoDBDialect</property>
或者是
<property name="dialect">org.hibernate.dialect.MySQL5Dialect</property>
如果使用的是MySQL4.x的版本,那么相应的配置为:
<property name="dialect">org.hibernate.dialect.MySQLDialect</property>
3.抛出异常
org.hibernate.boot.MappingNotFoundException: Mapping (RESOURCE) not found : Student.hbm.xml : origin(Student.hbm.xml)
异常提示信息告诉我们,找不到映射文件的位置,我第一次建配置文件时出现这个原因就是因为没有把Student.hbm.xml和hibernate.cfg.xml文件放在同一级目录下,所以,检查这两个是否在同一级目录下即可。
4.抛出异常
org.hibernate.HibernateException: No CurrentSessionContext configured!
没有currentSession配置错误,即在我们使用currentSession的时候要在hibernate.cfg.xml中进行相关的事务配置:
<--1.本地事务-->
<property name="hibernate.current_session_context_class">thread</property>
<--2.全局事务-->
<property name="hibernate.current_session_context_class">jta</property>
如果在获得session 对象时使用的是
session = sessionFactory.getCurrentSession();
则此处可以改成
session = sessionFactory.openSession();
这样就不用修改上面的配置文件了
一般而言,抛出
org.hibernate.HibernateException: No TransactionManagerLookup specified
没有指定的事务管理查找器,也是这个配置文件引起的错误。
上面就是我在eclipse下使用Hibernate框架创建测试用例时的基本步骤和遇到的问题,还有解决方法的总结,总的来说,版本差异挖的坑还是很多的,边学习边发现吧!
总结出来也是希望能对大家有所帮助。
共同学习,写下你的评论
评论加载中...
作者其他优质文章