[置頂] 持久化API(JPA)系列(五)控制實(shí)體Bean的生命周期
來(lái)源:程序員人生 發(fā)布時(shí)間:2015-05-26 07:47:20 閱讀次數(shù):3837次
上篇文章《持久化API(JPA)系列(4)管理器EntityManager--履行數(shù)據(jù)庫(kù)更新》中我們講授了使用實(shí)體管理器的各種函數(shù)操作數(shù)據(jù)庫(kù)的方法。
本文主要講:控制實(shí)體Bean的生命周期。
預(yù)會(huì)話Bean類似,實(shí)體Bean也有自己的生命周期,分別對(duì)應(yīng)不同的狀態(tài)。
下面我們首先來(lái)說(shuō)解實(shí)體Bean的狀態(tài)和生命周期事件:
1、實(shí)體Bean生命周期的4種狀態(tài)
2、實(shí)體Bean的事件:
@PostLoad
@PrePersist和@PostPersist
@PreUpdate和@PostUpdate
@PreRemove和@PostRemove。
3、事件回調(diào)的兩種方法:
外部回調(diào):編寫(xiě)外部監(jiān)聽(tīng)器。
=============================================================================
1、實(shí)體Bean生命周期的4種狀態(tài)
實(shí)體分為被容器管理和不被容器管理兩種。可以通過(guò)實(shí)體管理器的的兩個(gè)方法進(jìn)行檢測(cè):
contains()用來(lái)檢查實(shí)體是不是被管理。
clear()分離實(shí)體。

實(shí)際上,實(shí)體共有4種狀態(tài)。
new--新實(shí)體:實(shí)體由利用產(chǎn)生,和實(shí)體管理器沒(méi)有任何聯(lián)系,也沒(méi)有唯1的標(biāo)識(shí)符。
managed--持久化實(shí)體:新實(shí)體和實(shí)體管理器產(chǎn)生關(guān)聯(lián)(通過(guò)persist()、merge()等方法),在實(shí)體管理器中存在和被管理,標(biāo)志是在實(shí)體管理器中有1個(gè)唯1的標(biāo)識(shí)符。
detached--分離的實(shí)體:實(shí)體有唯1的標(biāo)識(shí)符,但它的標(biāo)識(shí)符不被實(shí)體管理器管理。
removed--刪除的實(shí)體:實(shí)體被remove()方法刪除,對(duì)應(yīng)的記錄將會(huì)在當(dāng)前事務(wù)提交的時(shí)候從數(shù)據(jù)庫(kù)中刪除。
=============================================================================
2、實(shí)體Bean生命周期的回調(diào)事件
當(dāng)你在履行各種持久化方法的時(shí)候,實(shí)體的狀態(tài)會(huì)隨之改變,狀態(tài)的改變會(huì)引發(fā)不同的生命周期事件。這些事件可使用不同的注釋符來(lái)唆使產(chǎn)生時(shí)的回調(diào)函數(shù)。
@PostLoad 加載后
@PrePersist和@PostPersist 持久化前后
@PreUpdate和@PostUpdate 更新前后
@PreRemove和@PostRemove 刪除前后
以上的7種事件對(duì)應(yīng)了數(shù)據(jù)庫(kù)的4種操作。

1)數(shù)據(jù)庫(kù)查詢
@PostLoad事件在以下情況下觸發(fā):
履行EntityManager.find()或getreference()方法載入1個(gè)實(shí)體后。
履行JPQL查詢后。
EntityManager.refresh()方法被調(diào)用后。
2)數(shù)據(jù)庫(kù)插入
@PrePersist和@PostPersist事件在實(shí)體對(duì)象插入到數(shù)據(jù)庫(kù)的進(jìn)程中產(chǎn)生:
@PrePersist事件在調(diào)用persist()方法后立刻產(chǎn)生,此時(shí)的數(shù)據(jù)還沒(méi)有真正插入進(jìn)數(shù)據(jù)庫(kù)。
@PostPersist事件在數(shù)據(jù)已插入進(jìn)數(shù)據(jù)庫(kù)后產(chǎn)生。
3)數(shù)據(jù)庫(kù)更新
@PreUpdate和@PostUpdate事件的觸發(fā)由更新實(shí)體引發(fā):
@PreUpdate事件在實(shí)體的狀態(tài)同步到數(shù)據(jù)庫(kù)之前觸發(fā),此時(shí)的數(shù)據(jù)還沒(méi)有真正更新到數(shù)據(jù)庫(kù)。
@PostUpdate事件在實(shí)體的狀態(tài)同步到數(shù)據(jù)庫(kù)以后觸發(fā),同步在事務(wù)提交時(shí)產(chǎn)生。
4)數(shù)據(jù)庫(kù)刪除
@PreRemove和@PostRemove事件的觸發(fā)由刪除實(shí)體引發(fā):
@PreRemove事件在實(shí)體從數(shù)據(jù)庫(kù)刪除之前觸發(fā),即在調(diào)用remove()方法刪除時(shí)產(chǎn)生,此時(shí)的數(shù)據(jù)還沒(méi)有真正從數(shù)據(jù)庫(kù)中刪除。
@PostRemove事件在實(shí)體從數(shù)據(jù)庫(kù)中刪除后觸發(fā)。
=============================================================================
3、外部回調(diào)--編寫(xiě)外部監(jiān)聽(tīng)器
對(duì)以上7種事件類型,我們可以用兩種方法來(lái)實(shí)現(xiàn)回調(diào)。
外部回調(diào):即編寫(xiě)1個(gè)實(shí)體監(jiān)聽(tīng)器,實(shí)現(xiàn)對(duì)某1個(gè)實(shí)體Bean的回調(diào)。
內(nèi)部回調(diào):通過(guò)在實(shí)體Bean內(nèi)部的監(jiān)聽(tīng)進(jìn)行回調(diào)。
1)外部回調(diào):
A.首先編寫(xiě)1個(gè)回調(diào)的監(jiān)聽(tīng)器類,該類需要使用@javax.persistence.EntityListeners注釋符綁定目標(biāo)實(shí)體Bean,實(shí)現(xiàn)實(shí)體Bean的監(jiān)聽(tīng)。
B.在該類中可以編寫(xiě)多個(gè)回調(diào)方法,通過(guò)在方法前添加不同的回調(diào)注釋符實(shí)現(xiàn)事件的攔截。
C.回調(diào)方法需要返回void型值,并且具有1個(gè)Object參數(shù)。
這類通過(guò)編寫(xiě)外部監(jiān)聽(tīng)器的方法,類似于AOP的功能,可以通過(guò)外部類實(shí)現(xiàn)對(duì)系統(tǒng)中目標(biāo)類和函數(shù)的監(jiān)聽(tīng)。
Demo演示
2)內(nèi)部回調(diào)步驟:
A.回調(diào)方法寫(xiě)在實(shí)體Bean中。直接寫(xiě)在實(shí)體Bean中的回調(diào)方法不需帶任何參數(shù)。
B.直接寫(xiě)在實(shí)體Bean中的回調(diào)方法不需帶任何參數(shù)。
C.不同的回調(diào)函數(shù)也是通過(guò)回調(diào)注釋符進(jìn)行注釋來(lái)標(biāo)注的。
Demo演示
生活不易,碼農(nóng)辛苦
如果您覺(jué)得本網(wǎng)站對(duì)您的學(xué)習(xí)有所幫助,可以手機(jī)掃描二維碼進(jìn)行捐贈(zèng)
------分隔線----------------------------
------分隔線----------------------------