1.JPAの多くは
多くの関係では、我々は、メインテーブルの当事者、テーブルからマルチパーティコールそれを呼び出すために使用されます。データベース内対多の関係は、外部キー制約データベースを使用する必要があります。
外部キーとは何ですか?
プライマリ・テーブルのプライマリ・キー値を参照し、列が外部キーであり、テーブルの列を指します。
2.エンティティ・クラス関係の確立、ならびにマッピング構成
顧客が少ないの一つであるので、次のようにEntityクラス、それは、複数のコンタクトで顧客情報を反映するために、エンティティクラスを複数のコンタクトが含まれている必要があります。
パーティのお客様
/ **
* 1エンティティクラスとのマッピング関係テーブル
* @Eitity
* @Table
テーブル内の属性フィールドのための*マッピングとクラス2
* @Id
* @GeneratedValue
* @Column
* /
@Entity
@Table(名 = "cst_customer" )
パブリック クラスカスタマー{
@Id
@GeneratedValue(戦略 = GenerationType.IDENTITYを)
@Column(名前 = "CUST_ID" )
プライベートロングCUSTID。
@Column(名前 = "CUST_ADDRESS" )
プライベート文字列custAddress。
@Column(名 = "cust_industry" )
プライベートCustIndustry文字列;
@Column(名前 = "cust_level" )
プライベート文字列custLevel。
@Column(名前 = "CUST_NAME" )
プライベート文字列CUSTNAME。
@Column(名前 = "cust_phone" )
プライベート文字列custPhone。
@Column(名前 = "cust_source" )
プライベート文字列custSource;
// のconfigure関係(顧客との接点の間に、多くの関係)
/ **
マルチテーブル構成関係の形で*使用注釈
* 1宣言の関係
* @OneToMany:のconfigure対多の関係
* targetEntity :バイトコードオブジェクト、他のオブジェクト
*設定外部キー(センターテーブル)
* @JoinColumn:外部キーが配置されました
*名前:外部キーフィールド名
* referencedColumnNameとは:主テーブルの主キーのフィールド名を参照して
*
* *クライアントエンティティクラス(パーティ)を追加しました外部キーの設定のため、顧客のために、だけでなく、外部キーのメンテナンスを含み役割
*
* /
// @OneToMany(targetEntity = LinkMan.class)
// @JoinColumn(名前= "lkm_cust_id"、referencedColumnNameと= "CUST_ID")
/ **
*外部キーを維持する権利を放棄
* mappedBy:他の構成プロパティの関係名\
*カスケード:カスケード構成は、(ノートの複数のマッピングテーブルを設定するように構成することができます)
* CascadeType.ALL:すべて
* MERGE:更新
* PERSIST:保存
* REMOVE:削除
* EAGER:ロード今
*
*フェッチ:ローディング設定関連オブジェクト
* LAZY:延迟加载
* /
@OneToMany(mappedBy = "顧客"、カスケード= CascadeType.ALL)
プライベート設定<総合司会> linkMans = 新しい HashSetの<>();
マルチパーティの総合司会者
@Entity
@Table(name = "cst_linkman")
public class LinkMan {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "lkm_id")
private Long lkmId; //联系人编号(主键)
@Column(name = "lkm_name")
private String lkmName;//联系人姓名
@Column(name = "lkm_gender")
private String lkmGender;//联系人性别
@Column(name = "lkm_phone")
private String lkmPhone;//联系人办公电话
@Column(name = "lkm_mobile")
private String lkmMobile;//联系人手机
@Column(name = "lkm_email")
private String lkmEmail;//联系人邮箱
@Column(name = "lkm_position")
private String lkmPosition;//联系人职位
@Column(name = "lkm_memo")
private String lkmMemo;//联系人备注
/**
* 配置联系人到客户的多对一关系
* 使用注解的形式配置多对一关系
* 1.配置表关系
* @ManyToOne : 配置多对一关系
* targetEntity:对方的实体类字节码
* 2.配置外键(中间表)
*
* * 配置外键的过程,配置到了多的一方,就会在多的一方维护外键
*
*/
@ManyToOne(targetEntity = Customer.class,fetch = FetchType.LAZY)
@JoinColumn(name = "lkm_cust_id",referencedColumnName = "cust_id")
private Customer customer;
3.映射的注解说明
@OneToMany:
作用:建立一对多的关系映射
属性:
targetEntityClass:指定多的多方的类的字节码
mappedBy:指定从表实体类中引用主表对象的名称。
cascade:指定要使用的级联操作
fetch:指定是否采用延迟加载
orphanRemoval:是否使用孤儿删除
@ManyToOne
作用:建立多对一的关系
属性:
targetEntityClass:指定一的一方实体类字节码
cascade:指定要使用的级联操作
fetch:指定是否采用延迟加载
optional:关联是否可选。如果设置为false,则必须始终存在非空关系。
@JoinColumn
作用:用于定义主键字段和外键字段的对应关系。
属性:
name:指定外键字段的名称
referencedColumnName:指定引用主表的主键字段名称
unique:是否唯一。默认值不唯一
nullable:是否允许为空。默认值允许。
insertable:是否允许插入。默认值允许。
updatable:是否允许更新。默认值允许。
columnDefinition:列的定义信息。
4.JPA中的一对多测试
RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = "classpath:applicationContext.xml")
public class OneToManyTest {
@Autowired
private CustomerDao customerDao;
@Autowired
private LinkManDao linkManDao;
/**
* 保存一个客户,保存一个联系人
* 效果:客户和联系人作为独立的数据保存到数据库中
* 联系人的外键为空
* 原因?
* 实体类中没有配置关系
*/
@Test
@Transactional //配置事务
@Rollback(false) //不自动回滚
public void testAdd() {
//创建一个客户,创建一个联系人
Customer customer = new Customer();
customer.setCustName("百度");
LinkMan linkMan = new LinkMan();
linkMan.setLkmName("小李");
/**
* 配置了客户到联系人的关系
* 从客户的角度上:发送两条insert语句,发送一条更新语句更新数据库(更新外键)
* 由于我们配置了客户到联系人的关系:客户可以对外键进行维护
*/
customer.getLinkMans().add(linkMan);
customerDao.save(customer);
linkManDao.save(linkMan);
}
@Test
@Transactional //配置事务
@Rollback(false) //不自动回滚
public void testAdd1() {
//创建一个客户,创建一个联系人
Customer customer = new Customer();
customer.setCustName("百度");
LinkMan linkMan = new LinkMan();
linkMan.setLkmName("小李");
/**
* 配置联系人到客户的关系(多对一)
* 只发送了两条insert语句
* 由于配置了联系人到客户的映射关系(多对一)
*
*
*/
linkMan.setCustomer(customer);
customerDao.save(customer);
linkManDao.save(linkMan);
}
/**
* 会有一条多余的update语句
* * 由于一的一方可以维护外键:会发送update语句
* * 解决此问题:只需要在一的一方放弃维护权即可
*
*/
@Test
@Transactional //配置事务
@Rollback(false) //不自动回滚
public void testAdd2() {
//创建一个客户,创建一个联系人
Customer customer = new Customer();
customer.setCustName("百度");
LinkMan linkMan = new LinkMan();
linkMan.setLkmName("小李");
linkMan.setCustomer(customer);//由于配置了多的一方到一的一方的关联关系(当保存的时候,就已经对外键赋值)
customer.getLinkMans().add(linkMan);//由于配置了一的一方到多的一方的关联关系(发送一条update语句)
customerDao.save(customer);
linkManDao.save(linkMan);
}
}
5.级联操作
级联操作:指操作一个对象同时操作它的关联对象
使用方法:只需要在操作主体的注解上配置cascade
/**
* cascade:配置级联操作
* CascadeType.MERGE 级联更新
* CascadeType.PERSIST 级联保存:
* CascadeType.REFRESH 级联刷新:
* CascadeType.REMOVE 级联删除:
* CascadeType.ALL 包含所有
*/
@OneToMany(mappedBy="customer",cascade=CascadeType.ALL)
6.级联添加和级联删除
/**
* 级联添加:保存一个客户的同时,保存客户的所有联系人
* 需要在操作主体的实体类上,配置casacde属性
*/
@Test
@Transactional //配置事务
@Rollback(false) //不自动回滚
public void testCascadeAdd() {
Customer customer = new Customer();
customer.setCustName("百度1");
LinkMan linkMan = new LinkMan();
linkMan.setLkmName("小李1");
linkMan.setCustomer(customer);
customer.getLinkMans().add(linkMan);
customerDao.save(customer);
}
/**
* 级联删除:
* 删除1号客户的同时,删除1号客户的所有联系人
*/
@Test
@Transactional //配置事务
@Rollback(false) //不自动回滚
public void testCascadeRemove() {
//1.查询1号客户
Customer customer = customerDao.findOne(1l);
//2.删除1号客户
customerDao.delete(customer);
}
————你是我自罚三杯也不能开口的秘密