JPA简单使用

2018-02-25  本文已影响0人  咻咻咻i

JPA是java中的持久层API,sun公司希望通过jpa整合orm技术,实现天下归一。JPA作为orm的规范,我是很有兴趣的把它学习了一遍。先说说jpa单独的使用,在介绍jpa与springdata的整合。

1、创建java项目

呃、这不就过了吧,也可以用eclipse建立jpa项目,学习测试嘛,都一样。

2、导入jar包

jpa作为接口,其自身是没有任何实现的,这里我们使用hibernate作为实现产品。lib/require下的所有jar文件。我使用的hibernate版本是5.2.10的。


还要导入mysql驱动,加入build path。如下图:

3、编写配置文件

主要设置jpa实现产品,继承javax.persistence.spi.PersistenceProvider接口的类,实体类的引用路径。
jpa的基本参数(数据库驱动账号密码等),实现产品的配置参数(如hibernate中的显示sql语句)。

<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.0" ......>
    <persistence-unit name="jpa" transaction-type="RESOURCE_LOCAL">
        <!-- jpa的实现产品 -->
        <provider>org.hibernate.jpa.HibernatePersistenceProvider</provider>
        
        <!-- 两个实体类 -->
        <class>cn.lkangle.entity.Student</class>
        <class>cn.lkangle.entity.Clazz</class>
        
        <properties>
            <!-- 数据库连接配置 -->
            <property name="javax.persistence.jdbc.driver" value="com.mysql.jdbc.Driver"/>
            <property name="javax.persistence.jdbc.url" value="jdbc:mysql:///jpa"/>
            <property name="javax.persistence.jdbc.user" value="root"/>
            <property name="javax.persistence.jdbc.password" value="root"/>
            
            <!-- hibernate的配置 -->
            <property name="hibernate.dialect" value="org.hibernate.dialect.MySQL55Dialect"/>
            <property name="hibernate.show_sql" value="true"/>
            <property name="hibernate.format_sql" value="true"/>
            <property name="hibernate.hbm2ddl.auto" value="update"/>
        </properties>
    </persistence-unit>
</persistence>

4、创建学生和班级实体类

Student.java

package cn.lkangle.entity;

import java.util.Date;

import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.Table;

/**
 * 学生的实体类
 * @author lbxx
 * 常用注解解释:
 * @Entity 用来标示这个类是实体类
 * @Table  实体类与数据表的映射,通过name确定在表名(默认类名为表名)
 * @Id         主键注解,表示该字段为主键
 * @GeneratedValue 定义主键规则,默认AUTO
 * @Column 类属性与表字段映射注解,其中可以设置在字段名,长度等信息
 * @ManyToOne  多对一,可以设置数据加载方式等 默认加载方式是EAGER 就是使用left join
 * @OneToMany  一对多 默认加载方式是 LAZY 懒加载
 * @JoinColumn 与*对*配合使用,用来设置外键名等信息
 * @Basic  实体类中会默认为每一个属性加上这个注解,表示与数据表存在关联,
 *              没有使用Column注解的类属性会以属性名作为字段名,驼峰命名需要转为_
 * @Temporal 对于Date属性的格式化注解,有 TIME,DATE,TIMESTAMP 几个选择
 * @Transient 若存在不想与数据表映射的属性,则需要加上该注解
 */
@Entity
@Table(name = "t_student")
public class Student {
    @Id@GeneratedValue(strategy = GenerationType.IDENTITY)
    private Integer id;
    private String  name;
    private String  tel;
    private Date    date;
    
    @JoinColumn(name = "clz_id")
    @ManyToOne(fetch = FetchType.EAGER)
    private Clazz clazz;
    ...get set省略...
}

Clazz.java

package cn.lkangle.entity;

import java.util.Date;

import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;
import javax.persistence.Temporal;
import javax.persistence.TemporalType;

@Entity
@Table(name = "t_clazz")
public class Clazz {
    
    @Id@GeneratedValue(strategy = GenerationType.IDENTITY)
    private Integer id;
    private String  name;
    
    @OneToMany(mappedBy = "clazz")
    private Set<Student> stus = new HashSet<>();
    
    @Temporal(TemporalType.DATE)
    private Date    date;
    ...get set省略...
}

5、测试CRUD

因为就是学习使用,这里就使用junit进行测试。

使用jpa首先要通过Persistence创建一个EntityManagerFactory实例,,然后利用它创建EntityManage实例,在通过EntityManage获取事务,开始事务进行crud操作,提交事务、、、一个基本流程就这样子。

package cn.lkangle.test;

import javax.persistence.EntityManager;
import javax.persistence.EntityManagerFactory;
import javax.persistence.EntityTransaction;
import javax.persistence.Persistence;

import org.junit.After;
import org.junit.Before;
import org.junit.Test;

public class JpaTest {
    private EntityManagerFactory entityManagerFactory;
    private EntityManager entityManager;
    private EntityTransaction transaction;
    
    @Before
    public void init() {
        /**
         * 通过Persistence获取EntityManagerFactory,
         * 传入参数对应配置文件中持久化单元persistence-unit的name
         * 通过EntityManagerFactory创建EntityManager
         * 获取EntityTransaction
         * 开启事务
         */
        entityManagerFactory = Persistence.createEntityManagerFactory("jpa");
        entityManager = entityManagerFactory.createEntityManager();
        transaction = entityManager.getTransaction();
        transaction.begin();
    }
    
    @After
    public void distory() {
        /**
         * 提交事务
         * 关闭entityManager
         * 关闭entityManagerFactory
         */
        transaction.commit();
        entityManager.close();
        entityManagerFactory.close();
    }
    
    @Test
    public void test() {
        
    }
}

运行test可以看见控制台输出了hibernate的键表语句,数据库中也创建了数据表

    /**
     * 添加操作
     * 在设置学生班级的时候这个班级必须是被jpa管理的持久化对象才能被设置成功
     * 需要先保存班级在保存学生
     */
    @Test
    public void testAdd() {
        Clazz clz1 = new Clazz();
        clz1.setName("计科1601");
        clz1.setDate(new Date());
        
        Student stu1 = new Student();
        stu1.setName("mary");
        stu1.setTel("18866005544");
        stu1.setDate(new Date());
        stu1.setClazz(clz1);
        
        entityManager.persist(clz1);
        entityManager.persist(stu1);
    }

6、总结

  JPA的entityManager和hibernate中的Session是有许多不同的地方的,记得删除就是不一样的,hibernate可以直接通过托管态的对象删除,而JPA是不可以的。JPA作为的是一个标准,Hibernate进行扩展了很多,哇,编不下去了,hibernate学完就没怎么用了,不熟悉就不多说了,这个JPA我会一直跟下去的。
  有时间在整理一份JPA中缓存的使用,还有那个级联处理,各种各样的关系着。然后再着重写一份与SpringData整合的,这个是真的好用,这大概才是JPA真正发挥威力的地方了~~
  其实实在的,我还是比较喜欢ActiveRecord这种模式的ORM框架,python的peewee用着那是真的舒服,奈何java中一直没有找到类似的功能完善,知名度大的(大概是我没认真找吧)。简单看了mybaits plus好像是支持这种模式,有时间要研究研究,不知道大家有没有好的推荐、、、(假装有很多人看我的文章)

上一篇 下一篇

猜你喜欢

热点阅读