JPA开发

什么是JPA:

JPA(Java Persistence API)是Sun官方提出的Java持久化规范。它为Java开发人员提供了一种对象/关系映射工具来管理Java应用中的关系数据。他的出现主要是为了简化现有的持久化开发工作和整合ORM技术,结束现在Hibernate、TopLink等ORM框架各自为营的局面。值得注意的是,JPA是在充分吸收了现有Hibernate、TopLink等ORM框架的基础上发展而来的,具有易于使用、伸缩性强等优点。从目前的开发社区的反应上看,JPA受到了极大的支持和赞扬,其中就包括了Spring与EJB3.0的开发团队。着眼未来几年的技术走向,JPA作为ORM领域标准化整合者的目标应该不难实现。

JPA的总体思想和现有Hibernate、TopLink等ORM框架大体一致。总的来说,JPA包括以下3方面的技术:

ORM映射元数据

JPA支持XML和JDK 5.0注释(也可译作注解)两种元数据的形式,元数据描述对象和表之间的映射关系,框架据此将实体对象持久化到数据库表中。

Java持久化API用来操作实体对象,执行CRUD操作,框架在后台替我们完成所有的事情,开发者可以从繁琐的JDBC和SQL代码中解脱出来。

查询语言

这是持久化操作中很重要的一个方面,通过面向对象而非面向数据库的查询语言查询数据,避免程序的SQL语句紧密耦合。

提示: JPA不是一种新的ORM框架,他的出现只是用于规范现有的ORM技术,他不能取代现有的Hibernate、TopLink等ORM框架。相反,在采用JPA开发时,我们仍将使用到这些ORM框架,只是此时开发出来的应用不再依赖于某个持久化提供商。应用可以在不修改代码的情况下在任何JPA环境下运行,真正做到低耦合,可扩展的程序设计。

JPA工程

所需JAR包

Hiberante核心包(8个文件)

hibernate-distribution-3.3.1.GA

---------------------------------------------

hibernate3.jar

lib\bytecode\cglib\hibernate-cglib-repack-2.1_3.jar

lib\required\*.jar

Hiberante注解包(3个文件):hibernate-annotations-3.4.0.GA

------------------------------------------------------------------------------------

hibernate-annotations.jar

lib\ejb3-persistence.jar、hibernate-commons-annotations.jar

Hibernate针对JPA的实现包(3个文件):hibernate-entitymanager-3.4.0.GA

------------------------------------------------------------------------------------------------------

hibernate-entitymanager.jar

lib\test\log4j.jar、slf4j-log4j12.jar

JPA配置文件

JPA规范要求在类路径的META-INF目录下放置persistence.xml,文件的名称是固定的,配置模版如下:

<?xml version="1.0"?>
<persistence xmlns="http://java.sun.com/xml/ns/persistence" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/persistence http://java.sun.com/xml/ns/persistence/persistence_1_0.xsd" version="1.0">
  <persistence-unit name="itcast" transaction-type="RESOURCE_LOCAL">
      <properties>
         <property name="hibernate.dialect" value="org.hibernate.dialect.MySQL5Dialect"/>
         <property name="hibernate.connection.driver_class" value="org.gjt.mm.mysql.Driver"/>
         <property name="hibernate.connection.username" value="root"/>
         <property name="hibernate.connection.password" value="root"/>
         <property name="hibernate.connection.url" value="jdbc:mysql://localhost:3306/itcast?useUnicode=true&characterEncoding=UTF-8"/>
         <property name="hibernate.hbm2ddl.auto" value="update"/>
      </properties>
  </persistence-unit>
</persistence>

JPA实体类:

/**在实体bean中用注解@Entity来指定实体以让jpa知道生成数据库中的表*/
@Entity
/**在实体类的前面用注解@Table(name="xx")指定生成表的名字*/
@Table(name = "t_person")
public class Person implements Serializable {
	private Integer id;
	private String name;
	private Date birthday;

	private Gender gender = Gender.MAN;// 设置默认值

	private String info;
	private byte[] file;

	private String imagePath;

	/**Table效率不高*/
	@Id
	@GeneratedValue(strategy = GenerationType.IDENTITY)
	public Integer getId() {
		return id;
	}

	public void setId(Integer id) {
		this.id = id;
	}
	/**在实体bean中用注解@Column(length,nullable,name)指定数据库中的表的字段的长度,是否为空即字段的名字*/
	@Column(name = "person_name", nullable = true, length = 30)
	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	/**反射用,默认无参构造函数*/
	public Person() {
		super();
	}
	/**在实体类中用注解@Temporal(TemporalType.Date)指定生日的时间类型*/
	@Column(name = "birthday", nullable = true)
	@Temporal(TemporalType.DATE)
	public Date getBirthday() {
		return birthday;
	}

	public void setBirthday(Date birthday) {
		this.birthday = birthday;
	}

	@Column(length = 5, nullable = true)
	@Enumerated(EnumType.ORDINAL)
	/**@Enumerated(EmumType.STRING)注解指定枚举类型(保存到数据库中是字符串)
	   @Enumerated(EnumType.ORDINAL)注解指定枚举类型(保存到数据库中是索引,从0开始)
	 */
	public Gender getGender() {
		return gender;
	}

	public void setGender(Gender gender) {
		this.gender = gender;
	}
	/**@Lob声明属性对应的数据库字段为大文本类型,可以存放大的数据(文本和字节)*/
	@Lob
	public String getInfo() {
		return info;
	}

	public void setInfo(String info) {
		this.info = info;
	}

	@Lob
	/**是否把数据装载到内存中延迟初始化,第一次访问的时候在加载数据,一般用在大数据存放*/
	@Basic(fetch=FetchType.LAZY)
	/**FetchType.EAGER:急加载,加载一个实体时,定义急加载的属性会立即从数据库中加载*/
	public byte[] getFile() {
		return file;
	}

	public void setFile(byte[] file) {
		this.file = file;
	}
	/**指定这个字段不跟数据库字段进行映射和关联*/
	@Transient
	public String getImagePath() {
		return imagePath;
	}

	public void setImagePath(String imagePath) {
		this.imagePath = imagePath;
	}

	public Person(String name) {
		super();
		this.name = name;
	}

	@Override
	public String toString() {
		return "Person [id=" + id + ", name=" + name + "]";
	}
}

实体引用枚举

public enum Gender {
	MAN, WOMEN
}

JPA测试类

/**
 * jpa四种状态
 * 1.new 新建
 * 2.托管
 * 3.游离(脱管)
 * 4.删除
 *
 */
public class PersonTest {

	@BeforeClass
	public static void setUpBeforeClass() throws Exception {

	}

	@Test
	public void test() {
		fail("Not yet implemented");
	}
	/**
	 * 增加数据
	 */
	@Test
	public void save() {
		EntityManagerFactory factory = Persistence.createEntityManagerFactory("itcast");
		EntityManager em = factory.createEntityManager();
		/** 读取数据不要开启事务,只要有更改数据的动作才需要开启事务*/
		em.getTransaction().begin();
		//new 新建 new一个实例
		Person p=new Person("张三");
		//持久化
		em.persist(p);////插入
		em.getTransaction().commit();
		em.close();
		factory.close();
	}
	/**
	 * 删除数据
	 */
	@Test
	public void remove() {
		EntityManagerFactory factory = Persistence.createEntityManagerFactory("itcast");
		EntityManager em = factory.createEntityManager();
		em.getTransaction().begin();
		Person p=em.find(Person.class, 1);
		em.remove(p);//删除(注意有外键约束时,需要先解除外键约束才能删除)
		em.getTransaction().commit();
		em.close();
		factory.close();
	}
	/**
	 * 更新数据:方法一
	 */
	@Test
	public void updatePerson() {
		EntityManagerFactory factory = Persistence.createEntityManagerFactory("itcast");
		EntityManager em = factory.createEntityManager();
		em.getTransaction().begin();
		Person p=em.find(Person.class, 2);
		p.setName("老张test");//(1).跟事务关联在一起了(2)对象处于托管状态,可以直接保存到数据库
		em.getTransaction().commit();
		em.refresh(p);//进行数据库刷新,拿出最新的数据
		System.out.println(p);
		em.close();
		factory.close();
	}
	/**
	 * 更新数据:方法二
	 */
	@Test
	public void updatePerson2() {
		EntityManagerFactory factory = Persistence.createEntityManagerFactory("itcast");
		EntityManager em = factory.createEntityManager();
		em.getTransaction().begin();
		Person p=em.find(Person.class, 2);
		em.clear();////把事务管理器中的所有实体变成游离状态
		p.setName("老张");//现在还是不可以,实体还是处于游离状态
		em.merge(p);//把游离状态中的实体bean同步到数据库
		em.getTransaction().commit();
		em.close();
		factory.close();
	}
	/**
	 * 查看数据:方法一
	 */
	@Test
	public void getPerson() {
		EntityManagerFactory factory = Persistence.createEntityManagerFactory("itcast");
		EntityManager em = factory.createEntityManager();
		Person p=em.find(Person.class, 1);
		System.out.println(p);//如果找不到,返回null值
		em.close();
		factory.close();
	}
	/**
	 * 查看数据:方法二
	 */
	@Test
	public void getPerson2() {
		EntityManagerFactory factory = Persistence.createEntityManagerFactory("itcast");
		EntityManager em = factory.createEntityManager();
		Person p=em.getReference(Person.class, 0);//1.没有值不出现异常
		System.out.println(p);//获取属性值时,如果找不到,出现异常 //2出现异常
		em.close();
		factory.close();
	}
	/**
	 * 查看数据:返回结果集
	 */
	@Test
	public void queryAll() {
		EntityManagerFactory factory = Persistence.createEntityManagerFactory("itcast");
		EntityManager em = factory.createEntityManager();
		em.getTransaction().begin();
		Query query=em.createQuery("select o from Person o");
		List<Person> list=query.getResultList();
		for(Person p:list){
			System.out.println(p);
		}

		em.close();
		factory.close();
	}
	/**
	 * 查看数据:返回单条数据
	 */
	@Test
	public void querySigle() {
		EntityManagerFactory factory = Persistence.createEntityManagerFactory("itcast");
		EntityManager em = factory.createEntityManager();
		Query query=em.createQuery("select o from Person o where o.id=?1");//必须有select o,id=等于后面不要直接写值以免sql注入
		query.setParameter(1, 2);
		/**
		 * (1)匿名查询用:id
		   (2)未参数查询?1即:where o.id=?1//指明?的值从索引1开始
		 */
		Person p=(Person) query.getSingleResult();//获取单条记录
		System.out.println(p);
		em.close();
		factory.close();
	}
	/**
	 * 查询删除
	 */
	@Test
	public void queryDelete() {
		EntityManagerFactory factory = Persistence.createEntityManagerFactory("itcast");
		EntityManager em = factory.createEntityManager();
		em.getTransaction().begin();
		Query query=em.createQuery("delete from Person o where o.id=?1");
		query.setParameter(1, 2);//位置参数
		int i=query.executeUpdate();
		System.out.println("受影响的行数 :"+i);
		em.close();
		factory.close();
	}
	/**
	 * 查询更新
	 */
	@Test
	public void queryUpdate() {
		EntityManagerFactory factory = Persistence.createEntityManagerFactory("itcast");
		EntityManager em = factory.createEntityManager();
		em.getTransaction().begin();
		Query query=em.createQuery("update Person o set o.name=:name where o.id=:id");
		query.setParameter("name", "五五");//匿名参数
		query.setParameter("id", 3);
		int i=query.executeUpdate();
		System.out.println("受影响的行数 :"+i);
		em.close();
		factory.close();
	}
}

JPA总结

首先,JPA不是ORM框架,而是SUN官方提出的JAVA持久化规范。JPA整合了现有的Hibernate、TopLink等ORM框架,具有易于使用、伸缩性

强等优点。下面我们就来学习关于JPA的知识。

1.       JPA规范要求在类路径的META-INF目录下放置persistence.xml,文件的名称是固定的,配置模版可见hibernate-entitymanager开发包

2.       JPA ORM映射元素数据有XML和注解两种方式,这里我们学习基于注解的方式,那么我们来谈谈JPA有哪些常用的注解

1)  在实体bean中用注解@Entity来指定实体以让jpa知道生成数据库中的表

2)  在实体bean中用注解@Column(length,nullable,name)指定数据库中的表的字段的长度,是否为空即字段的名字

3)  在实体类的前面用注解@Table(name="xx")指定生成表的名字

4)  在实体类中用注解@Temporal(TemporalType.Date)指定生日的时间类型

5)  @Enumerated(EmumType.STRING//保存到数据库中是索引还是字符串)注解指定枚举类型

6)  @Lob声明属性对应的数据库字段为大文本类型,可以存放大的数据(文本和字节)

7)  @Transient不成为持久化字段及不跟数据库中的字段形成映射

8)  @Basic(fetch=FetchType.LAZY)//是否把数据装载到内存中延迟初始化,第一次访问的时候在加载数据,一般用在大数据存放

9)  @Embeddable指定联合组键

3.       JPA的增删改查:

1)  读取数据不要开启事务,只要有更改数据的动作才需要开启事务

2)  增加数据:em.persist(new Person("老黎"));//插入

3)  删除数据:em.remove(person); //删除(注意有外键约束时,需要先解除外键约束才能删除)

4)  更新数据:

方法一:Person person = em.find(Person.class,1);

person.setName("老黎");(1).跟事务关联在一起了(2)对象处于托管状态

方法二:Person person = em.find(Person.class,1);

em.clear();//把事务管理器中的所有实体变成游离状态

person.setName("老黎");//现在还是不可以,实体还是处于游离状态

em.merge(person);//把游离状态中的实体bean同步到数据库

说明:本人于ITEYE创建于2014年,现转移到CSDN

时间: 2024-11-05 02:37:57

JPA开发的相关文章

JPA开发入门实例

一. 什么是JPA JPA是sun官方提出的Java持久化规范, 它为Java开发人员提供了一种对象/关系映射工具来管理Java应用中的关系数据, 它的出现主要是为了简化现有的持久化开发工作和整合ORM技术. JPA总体思想和现有的Hibernate.TopLink等ORM框架大体一致. 总的来说, JPA包括以下3方面的技术: 1. ORM映射元数据(JPA支持XML和注解两种元数据的形式) - 元数据描述对象和表之间的映射关系. 2. Java持久化API: 用来操作实体对象, 执行CRUD

JPA开发总结&lt;二&gt;--代码整理

首先看下使用JPA规范的注解方式模板(代码中解释很详细): @Entity(name="person") public class Person { //GenerationType为AUTO是权衡mysql和oracle不同,也可以对应具体数据库选择IDENTITY或者SEQUENCE @Id @GeneratedValue(strategy=GenerationType.AUTO) private Integer id; //不能为空就设为false @Column(length=

JPA开发总结&lt;一&gt;

什么是JPA JPA(Java Persistence API)是Sun官方提出的Java持久化规范,它为Java开发人员提供了一种对象/关系映射工具来管理Java应用中的关系数据.它的出现主要是为了简化现有的持久化开发工作和整合ORM技术,结束现在HIbernate.TopLink.JDO等ORM框架各自为营的局面.值得注意的是,JPA是在充分吸收了现有HIbernate.TopLink.JDO等ORM框架的基础上发展而来的(JPA的开发就是Hibernate的创始人做的),具有易于使用.伸缩

Spring Data JPA开发手册——1.介绍

<Spring Data JPA开发手册--1.介绍> 作者:chszs,转载需注明.博客主页:http://blog.csdn.net/chszs 我发现网上几乎没有讲述Spring Data JPA原理的文章,很多Guide一上来就是如何配置,接着就是几大段代码,没有一篇文章能把Spring Data JPA原理及构成说清楚的.所以,我写了这个系列的文章. 用Java Persistence API库创建持久层是很繁琐的,也很耗时,而且需要大量的样板代码.我们可以通过以下步骤消除一些样板代

Spring Boot和JPA开发的一些坑

最近新的项目API接口基于Spring Boot和JPA开发,做了几天的学习和预研,发现使用Spring Boot开发效率上确实比较高,但也碰到了一些小坑,特别记录下. 配置文件问题 ,默认只要一个配置文件application.properties,不要再想ApplicationContent.xml等spring的配置文件了 logback配置文件路径问题,使用绝对路径读取没问题,基于classpath路径则读取不到 ,这个问题有待进一步解决 Spring-boot不能扫描到启动函数包外的b

使用 Spring Data JPA 简化 JPA 开发

从一个简单的 JPA 示例开始 本文主要讲述 Spring Data JPA,但是为了不至于给 JPA 和 Spring 的初学者造成较大的学习曲线,我们首先从 JPA 开始,简单介绍一个 JPA 示例:接着重构该示例,并引入 Spring 框架,这两部分不会涉及过多的篇幅,如果希望能够深入学习 Spring 和 JPA,可以根据本文最后提供的参考资料进一步学习. 自 JPA 伴随 Java EE 5 发布以来,受到了各大厂商及开源社区的追捧,各种商用的和开源的 JPA 框架如雨后春笋般出现,为

JPA学习---第二节:JPA开发环境和思想介绍

一.下载相关 jar http://hibernate.org/orm/ 下载 hibernate ,解压 http://www.slf4j.org/download.html 下载 slf4j,解压 http://www.apache.org/dyn/closer.cgi/logging/log4j/2.0.2/apache-log4j-2.0.2-bin.zip 下载 log4j, 解压 二.开发 JPA 依赖的jar hibernate-release-4.3.6.Final\lib\re

[z]使用 Spring Data JPA 简化 JPA 开发

文章来自http://www.ibm.com/developerworks/cn/opensource/os-cn-spring-jpa/,内容非常清晰. 从一个简单的 JPA 示例开始 本文主要讲述 Spring Data JPA,但是为了不至于给 JPA 和 Spring 的初学者造成较大的学习曲线,我们首先从 JPA 开始,简单介绍一个 JPA 示例:接着重构该示例,并引入 Spring 框架,这两部分不会涉及过多的篇幅,如果希望能够深入学习 Spring 和 JPA,可以根据本文最后提供

JPA学习---第三节:搭建JPA开发环境和全局事务介绍

一.创建 Java 项目 1.导入所需的 jar 包: 2.创建 persistence.xml 文件, 代码如下: <?xml version="1.0" encoding="UTF-8"?><persistence version="2.0"    xmlns="http://java.sun.com/xml/ns/persistence"     xmlns:xsi="http://www.w