`
suhuanzheng7784877
  • 浏览: 701463 次
  • 性别: Icon_minigender_1
  • 来自: 北京
博客专栏
Ff8d036b-05a9-33b5-828a-2633bb68b7e6
读金庸故事,品程序人生
浏览量:47681
社区版块
存档分类
最新评论

JavaEE5实战笔记02JPA持久层的一些问题

阅读更多

1.       JPA关联实体的级联操作问题

在此次联系中需求是这样的,用户实体会关联一个自己的操作记录明细(消费、充值)实体,操作记录明细实体也是双向关联着用户实体。当删除用户的时候,操作明细记录是能随之(这里的能是允许的意思)级联删除的。而操作记录也是要删除的(操作记录这里仅仅是将用户与操作明细做一个桥梁)。主要类关系是:用户实体面对多个操作记录,一个操作记录面对一个操作记录明细实体、并且面对一个用户实体,一个操作记录明细实体面对一个操作记录。实体Bean代码如下

用户实体:UserDTO

package ejb.dto;

import java.io.Serializable;
import java.sql.Timestamp;
import java.util.List;

import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.OneToMany;
import javax.persistence.Table;

import org.hibernate.annotations.GenericGenerator;

/**
 * 用户实体
 * 
 * @author liuyan
 */
@Entity
@Table(name = "webbank_user")
public class UserDTO implements Serializable {

	private static final long serialVersionUID = 1L;

	public UserDTO() {

	}

	@Id
	@GeneratedValue(generator = "system-uuid")
	@GenericGenerator(name = "system-uuid", strategy = "uuid")
	// 主键
	private String id;

	@Column(name = "userName")
	// 用户名
	private String userName;

	@Column(name = "password")
	// 密码
	private String password;

	@Column(name = "userStates")
	// 用户状态
	private int userStates;

	@Column(name = "money")
	// 用户余钱
	private double money;

	@Column(name = "registeTime")
	// 注册时间
	private Timestamp registeTime;

	@OneToMany(cascade = CascadeType.REMOVE, fetch = FetchType.LAZY, mappedBy = "userDTO")
	private List<DealDTO> deals;

//省去setter和getter
}
 操作记录实体:DealDTO

package ejb.dto;

import java.io.Serializable;

import javax.persistence.CascadeType;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.OneToOne;
import javax.persistence.Table;

import org.hibernate.annotations.GenericGenerator;

/**
 * 交易记录信息
 * @author liuyan
 */
@Entity
@Table(name = "webbank_deal")
public class DealDTO implements Serializable {
	
	public DealDTO(){
		
	}
	private static final long serialVersionUID = 4210820165040311694L;

	@Id 
	@GeneratedValue(generator="system-uuid")
	@GenericGenerator(name="system-uuid",strategy = "uuid")
	private String id;

	@ManyToOne(optional = true, cascade = CascadeType.REFRESH)
	@JoinColumn(name = "user_ID")
	private UserDTO userDTO;

	@OneToOne(optional = true, cascade = CascadeType.ALL)
	@JoinColumn(name = "dealInfo_ID")
	private DealInfoDTO dealInfoDTO;

//省去setter和getter

}

 操作记录明细实体: DealInfoDTO

package ejb.dto;

import java.io.Serializable;
import java.sql.Timestamp;

import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.OneToOne;
import javax.persistence.Table;

import org.hibernate.annotations.GenericGenerator;

/**
 * 交易详细信息
 * @author liuyan
 */
@Entity
@Table(name = "webbank_dealInfo")
public class DealInfoDTO implements Serializable {
	
	public DealInfoDTO(){
		
	}

	private static final long serialVersionUID = -2266758318775332821L;

	@Id 
	@GeneratedValue(generator="system-uuid")
	@GenericGenerator(name="system-uuid",strategy = "uuid")
	private String id;

	@Column(name = "dealDate")
	private Timestamp dealDate;

	@Column(name = "dealStatue")
	private int dealStatue;

	@Column(name = "dealMessage")
	private String dealMessage;

	@OneToOne(optional = true, cascade = CascadeType.ALL)
	private DealDTO dealDTO;

//省去setter和getter

}

 UserDTO实体中的标记:

@OneToMany(cascade = CascadeType.REMOVE, fetch = FetchType.LAZY, mappedBy = "userDTO")
private List<DealDTO> deals;

 翻译成咱们通俗易懂的话就是:“如果JPAUserDTO实体进行了操作,那么在所有的操作中如果涉及到了删除UserDTO实体的话,也要将UserDTO实体有关系的DealDTO实体一并、级联地、株连九族地、毫不留情地删除掉”;“加载用户实体的同时也加载操作记录实体集合,不过是延迟加载”;“在多的一端——DealDTO实体有一个字段是维系2者关系的字段。也就是说让多的那一端记住1VSN的关系罢了。”

DealDTO实体中的标记:

	@ManyToOne(optional = true, cascade = CascadeType.REFRESH)
	@JoinColumn(name = "user_ID")
	private UserDTO userDTO;

 用普通话来说就是:“在用户实体与操作记录实体中,操作实体作为多的一端N中每一条操作记录对象必须有一个与之对应的用户记录”;“当对操作记录实体进行更新操作的时候,相应的在一级缓存中对用户实体也要进行级联的更新”;另一个要说明的就是在多的一端维系了1VSN的关系,在底层数据库中维系的字段就是user_ID

此实体的另一个标记

	@OneToOne(optional = true, cascade = CascadeType.ALL)
	@JoinColumn(name = "dealInfo_ID")
	private DealInfoDTO dealInfoDTO;

 咱们也来用普通话说就是:“对DealDTO实体的任何操作都会影响着操作明细实体DealInfoDTO的生存状态。保存DealDTO实体,别忙,它相应的明细实体也得享受这种保存的待遇。删除DealDTO实体,连累着明细实体也难闹厄运!”;“同时,DealDTO实体维系着这种1VS1的关系的字段。”

DealInfoDTO实体中的标记:

	@OneToOne(optional = true, cascade = CascadeType.ALL)
	private DealDTO dealDTO;

 他就比较舒服了~~自己的所有操作都会影响着DealDTO实体,除此之外没别的意思。当然了DealDTO实体与DealInfoDTO实体,双方互相都不能为空。双方就像杨过和小龙女一样,共同进退、如荣誉共、谁也缺不了谁、你死我也不能独生、你坠崖16年,我就等你16年!

基于以上的JPA配置就能按照先前的需求进行实体的操作了。

2.       UUID的主键生成策略

这次用的是Oracle10g数据库,一般的Oracle是通过索引进行主键的生成的策略,这里想换一种方式就是采用UUID的方式进行主键生成。

在实体注解中加入

	@Id
	@GeneratedValue(generator = "system-uuid")
	@GenericGenerator(name = "system-uuid", strategy = "uuid")
	private String id;

 即是使用UUID生成主键,并且就是在新增保存实体的时候千万不要自己生成主键,底层的Hibernate框架已经为你做了主键的生成和赋值工作。

3.       某些不需要事务传播的需求

需求如下,比如在用户消费的过程中发生了异常信息,那么需要记录到日志记录中。这里存在个问题,遇到消费发生运行时异常的过程需要事务回滚,那么日志实体的持久化操作就不能与消费业务共享同一个事务,当遇到执行保存日志实体的时候需要另开辟一个新的事务。在异常日志实体中的Service层的代码如下

 

 

@Stateless
@TransactionManagement(TransactionManagementType.CONTAINER)
@TransactionAttribute(TransactionAttributeType.REQUIRES_NEW)
public class ExceptionLogServiceImpl extends
		BaseServiceImpl<ExceptionLogDTO, String> implements ExceptionLogService {
	
	/**
	 * 注入其他EJB组件
	 */
	@EJB(beanName = "ExceptionLogEAOImpl")
	private ExceptionLogEAO exceptionLogEAO;
	
	public ExceptionLogServiceImpl() {
		super();
		System.out.println("ExceptionLogServiceImpl初始化");
	}
}

 REQUIRES_NEW代表另开辟一个新的事物,具体的事务传播介绍请参考:http://suhuanzheng7784877.iteye.com/blog/908382

1.Required:共享型
若1处在一个事务中调用了2,则2直接和1在同一个事务中。若1没有任何事务,则系统会默认给2创建一个新事务。此策略适合大多数情况。
2.RequiredNew:独立型
若1在一个事务中调用了2,则系统先将1的事务挂起,不管、之后为2设置一个新事务,执行完毕后恢复1的事务。若1没有事务,则会为2新开一个事务。
3.Mandatory:强制共享型
若1处在一个事务中调用了2,则2直接和1在同一个事务中。若1没有任何事务,直接抛出异常——Transaction RequiredException。
4.NotSupported:无助独立型
若1在一个事务中调用了2,则系统先将1的事务挂起,不管、之后2不开启任何事务,执行完毕后恢复1的事务。若1没有事务,2也直接执行。
5. Supported:啃老型
若1处在一个事务中调用了2,则2直接和1在同一个事务中。若1没有任何事务,直接执行2。
6.Never:捣乱型
若1处在一个事务中调用了2,则抛出RemoteException。若1没有任何事务,直接执行2也不会为它开启任何事务。

 

 

4
0
分享到:
评论

相关推荐

    JavaEE5学习笔记01-JTA和数据库事务

    ### JavaEE5学习笔记01-JTA和数据库事务:深入解析与应用 #### 一、JavaEE5概览与核心组件 JavaEE5是Java Enterprise Edition的第五个版本,标志着企业级Java应用的一个重要里程碑。它引入了一系列重要的新特性,...

    Javaee课堂笔记精华总结就业必备

    这个"Javaee课堂笔记精华总结就业必备"显然是一份针对求职者或初入职场的开发者准备的学习材料,旨在帮助他们掌握JavaEE的核心概念和技术,以提升就业竞争力。 JavaEE平台包括一组服务、APIs和协议,用于构建分布式...

    JavaEE基础笔记.zip

    6. **JPA(Java Persistence API)**:JPA是JavaEE提供的ORM(Object-Relational Mapping)规范,简化了Java应用与数据库之间的对象关系映射,替代了传统的EJB实体Bean。 7. **JSF(JavaServer Faces)**:JSF是一...

    JavaEE学习笔记

    ### JavaEE 学习笔记概览 #### 一、JavaEE 概念及发展历程 JavaEE(Java Platform, Enterprise Edition)是Sun Microsystems公司为简化企业级应用开发而提出的一套标准化平台,它提供了构建分布式系统的基本框架和...

    达内javaSE,javaEE个人学习所有基础笔记

    "达内javaSE,javaEE个人学习所有基础笔记"是一个针对初学者的全面学习资源,涵盖了从Java Standard Edition (Java SE)的基础知识到Java Enterprise Edition (Java EE)的高级概念。 Java SE是Java的核心部分,它...

    J2EE三大框架_笔记(个人收藏)

    此外,Spring还包含了AOP(面向切面编程)、MVC(模型-视图-控制器)框架、数据访问/集成、事务管理、缓存等功能,支持多种持久化策略,如JDBC、JPA、Hibernate等。 2. **Hibernate框架** Hibernate是一个对象关系...

    达内培训笔记

    - **JPA(Java Persistence API)与ORM**:JPA是JavaEE中的持久化标准,ORM(Object-Relational Mapping)框架如Hibernate和OpenJPA提供对象关系映射,将Java对象与数据库表对应。 - **JMS(Java Message Service...

    jdbc笔记(自写)

    JPA:JavaEE的规范,Java persistence api: Java的持久化API. Hibernate实现了该规范.(xml/注解) --------------------------------------------------------------------------------------------------------------...

    Java百万年薪架构师完整版.zip

    "JavaEE完整版.png"可能是一个课程的完成标志或者教学成果展示,强调了对JavaEE技术栈的全面掌握,包括Web层、业务逻辑层和持久层的开发技能,以及相关的工具和框架,如Maven、IntelliJ IDEA、Git等。 "Java百万年...

    JavaNotes:Java重新学习笔记。包括Linux,maven,git,互联网架构,大数据体系等

    - **MyBatis**:持久层框架,简化SQL操作,提供动态SQL支持。 以上知识点构成了Java开发者在实际工作中需要掌握的关键技能,涵盖了从基础到高级的全方位知识体系。通过深入学习和实践,可以提升个人技术水平,应对...

    JAVA-EE-master (4).zip

    5. **JTA**:Java Transaction API提供了统一的事务管理接口,确保在分布式环境下多个操作的原子性、一致性、隔离性和持久性(ACID属性)。 6. **JPA**:Java Persistence API简化了对象关系映射(ORM),使得Java...

Global site tag (gtag.js) - Google Analytics