2012-03-29 55 views
14

我正在使用Hibernate刪除具有兩個級聯級別的對象,而我的問題在於查詢對象時非常慢,然後刪除,而且我有興趣看到如果有更快的方法。我的代碼,這大約需要15-30秒,刪除15個Statement物體看起來是這樣的:在休眠中刪除級聯多個對象的最快方法

public void deleteStatement(Long batchId) { 
    List<Statement> statements = session.createQuery("from Statement where batchId = ?").setParameter(0, batchId).list(); 
    for(Statement statement : statements) { 
     session.delete(statement); 
     logger.debug("Deleted statement"); 
    } 
} 

我知道我可能只是這樣做:

session.createQuery("delete from Statement where batchId = ?").setParameter(0, batchId).executeUpdate(); 

但問題是,刪除級聯不用這種方法發生。有沒有一種有效的方法來刪除我的對象,並仍然發生級聯,或有什麼我做錯了?

感謝您的幫助!

更新
針對davidfrancis,下面是休眠生成SQL的闡釋。這是瘋狂的,數千行長,相信與否!請注意,我的域對象Statement包含一組Invoice,其中包含一組Transaction。我很懶加載所有的集合,順便說一句。首先有很多數據檢索,這,相信與HQL選擇查詢發生的:

org.hibernate.hql.ast.QueryTranslatorImpl - HQL: from com.myapp.domain.cc.Statement where batchId = ? 
org.hibernate.hql.ast.QueryTranslatorImpl - SQL: select statement0_.id as id2_, statement0_.batchId as batchId2_ from statement statement0_ where batchId=? 
org.hibernate.loader.Loader - result row: EntityKey[com.myapp.domain.cc.Statement#393] 
org.hibernate.loader.Loader - result row: EntityKey[com.myapp.domain.cc.Statement#394] 
... 
org.hibernate.SQL - select invoices0_.statementId as stateme12_2_1_, invoices0_.id as id1_, invoices0_.id as id3_0_, invoices0_.statementId as stateme12_3_0_ from invoice invoices0_ where invoices0_.statementId=? 
org.hibernate.loader.Loader - result row: EntityKey[com.myapp.domain.cc.Invoice#48987] 
org.hibernate.loader.Loader - found row of collection: [com.myapp.domain.cc.Statement.invoices#393] 
org.hibernate.loader.Loader - result row: EntityKey[com.myapp.domain.cc.Invoice#48988] 
org.hibernate.loader.Loader - found row of collection: [com.myapp.domain.cc.Statement.invoices#393] 
... 
org.hibernate.SQL - select transactio0_.invoiceId as invoiceId3_1_, transactio0_.id as id1_, transactio0_.id as id4_0_, transactio0_.invoiceId as invoiceId4_0_ from transactions transactio0_ where transactio0_.invoiceId=? 
org.hibernate.loader.Loader - result row: EntityKey[com.myapp.domain.cc.Transaction#306534] 
org.hibernate.loader.Loader - found row of collection: [com.myapp.domain.cc.Invoice.transactions#48996] 
... 

現在,刪除:

org.hibernate.persister.entity.AbstractEntityPersister - Static SQL for entity: com.aa.itfs.mcla.domain.cc.Transaction 
org.hibernate.persister.entity.AbstractEntityPersister - Version select: select id from transactions where id =? 
org.hibernate.persister.entity.AbstractEntityPersister - Snapshot select: select transactio_.id, transactio_.ccNumber as ccNumber4_, transactio_.approvalCode as approval3_4_, transactio_.saleAmount as saleAmount4_, transactio_.installmentNumber as installm5_4_, transactio_.numberOfInstallments as numberOf6_4_ from transactions transactio_ where transactio_.id=? 
org.hibernate.persister.entity.AbstractEntityPersister - Insert 0: insert into transactions (ccNumber, approvalCode, saleAmount, installmentNumber, numberOfInstallments, invoiceId, id) values (?, ?, ?, ?, ?, ?, ?) 
org.hibernate.persister.entity.AbstractEntityPersister - Update 0: update transactions set ccNumber=?, approvalCode=?, saleAmount=?, installmentNumber=?, numberOfInstallments=? where id=? 
org.hibernate.persister.entity.AbstractEntityPersister - Delete 0: delete from transactions where id=? 
org.hibernate.persister.entity.AbstractEntityPersister - Identity insert: insert into transactions (ccNumber, approvalCode, saleAmount, installmentNumber, numberOfInstallments, invoiceId) values (?, ?, ?, ?, ?, ?) 
org.hibernate.persister.entity.AbstractEntityPersister - Static SQL for entity: com.myapp.domain.cc.Statement 
org.hibernate.persister.entity.AbstractEntityPersister - Version select: select id from statement where id =? 
org.hibernate.persister.entity.AbstractEntityPersister - Snapshot select: select statement_.id, statement_.statementNumber as statemen2_2_, statement_.filename as filename2_, statement_.statementType as statemen4_2_ from statement statement_ where statement_.id=? 
org.hibernate.persister.entity.AbstractEntityPersister - Insert 0: insert into statement (statementNumber, filename, statementType, batchId, id) values (?, ?, ?, ?, ?) 
org.hibernate.persister.entity.AbstractEntityPersister - Update 0: update statement set statementNumber=?, filename=?, statementType=? where id=? 
org.hibernate.persister.entity.AbstractEntityPersister - Delete 0: delete from statement where id=? 
org.hibernate.persister.entity.AbstractEntityPersister - Identity insert: insert into statement (statementNumber, filename, statementType, batchId) values (?, ?, ?, ?) 
org.hibernate.persister.collection.AbstractCollectionPersister - Static SQL for collection: com.myapp.domain.cc.Statement.invoices 
org.hibernate.persister.collection.AbstractCollectionPersister - Row insert: update invoice set statementId=? where id=? 
org.hibernate.persister.collection.AbstractCollectionPersister - Row delete: update invoice set statementId=null where statementId=? and id=? 
org.hibernate.persister.collection.AbstractCollectionPersister - One-shot delete: update invoice set statementId=null where statementId=? 
org.hibernate.persister.collection.AbstractCollectionPersister - Static SQL for collection: com.myapp.domain.cc.Invoice.transactions 
org.hibernate.persister.collection.AbstractCollectionPersister - Row insert: update transactions set invoiceId=? where id=? 
org.hibernate.persister.collection.AbstractCollectionPersister - Row delete: update transactions set invoiceId=null where invoiceId=? and id=? 
org.hibernate.persister.collection.AbstractCollectionPersister - One-shot delete: update transactions set invoiceId=null where invoiceId=?  

隨機選擇....

org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Invoice [NONE]: select invoice0_.id as id3_0_, invoice0_.invoiceNumber as invoiceN2_3_0_, invoice0_.merchantNumber as merchant3_3_0_, invoice0_.installmentNumber as installm4_3_0_, invoice0_.saleDate as saleDate3_0_, invoice0_.paymentDate as paymentD6_3_0_, invoice0_.amount as amount3_0_, invoice0_.amountType as amountType3_0_, invoice0_.saleType as saleType3_0_, invoice0_.ccType as ccType3_0_, invoice0_.statementType as stateme11_3_0_, invoice0_.statementId as stateme12_3_0_ from invoice invoice0_ where invoice0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Invoice [READ]: select invoice0_.id as id3_0_, invoice0_.invoiceNumber as invoiceN2_3_0_, invoice0_.merchantNumber as merchant3_3_0_, invoice0_.installmentNumber as installm4_3_0_, invoice0_.saleDate as saleDate3_0_, invoice0_.paymentDate as paymentD6_3_0_, invoice0_.amount as amount3_0_, invoice0_.amountType as amountType3_0_, invoice0_.saleType as saleType3_0_, invoice0_.ccType as ccType3_0_, invoice0_.statementType as stateme11_3_0_, invoice0_.statementId as stateme12_3_0_ from invoice invoice0_ where invoice0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Invoice [UPGRADE]: select invoice0_.id as id3_0_, invoice0_.invoiceNumber as invoiceN2_3_0_, invoice0_.merchantNumber as merchant3_3_0_, invoice0_.installmentNumber as installm4_3_0_, invoice0_.saleDate as saleDate3_0_, invoice0_.paymentDate as paymentD6_3_0_, invoice0_.amount as amount3_0_, invoice0_.amountType as amountType3_0_, invoice0_.saleType as saleType3_0_, invoice0_.ccType as ccType3_0_, invoice0_.statementType as stateme11_3_0_, invoice0_.statementId as stateme12_3_0_ from invoice invoice0_ with (updlock, rowlock) where invoice0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Invoice [UPGRADE_NOWAIT]: select invoice0_.id as id3_0_, invoice0_.invoiceNumber as invoiceN2_3_0_, invoice0_.merchantNumber as merchant3_3_0_, invoice0_.installmentNumber as installm4_3_0_, invoice0_.saleDate as saleDate3_0_, invoice0_.paymentDate as paymentD6_3_0_, invoice0_.amount as amount3_0_, invoice0_.amountType as amountType3_0_, invoice0_.saleType as saleType3_0_, invoice0_.ccType as ccType3_0_, invoice0_.statementType as stateme11_3_0_, invoice0_.statementId as stateme12_3_0_ from invoice invoice0_ with (updlock, rowlock) where invoice0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Invoice [FORCE]: select invoice0_.id as id3_0_, invoice0_.invoiceNumber as invoiceN2_3_0_, invoice0_.merchantNumber as merchant3_3_0_, invoice0_.installmentNumber as installm4_3_0_, invoice0_.saleDate as saleDate3_0_, invoice0_.paymentDate as paymentD6_3_0_, invoice0_.amount as amount3_0_, invoice0_.amountType as amountType3_0_, invoice0_.saleType as saleType3_0_, invoice0_.ccType as ccType3_0_, invoice0_.statementType as stateme11_3_0_, invoice0_.statementId as stateme12_3_0_ from invoice invoice0_ where invoice0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Invoice [PESSIMISTIC_READ]: select invoice0_.id as id3_0_, invoice0_.invoiceNumber as invoiceN2_3_0_, invoice0_.merchantNumber as merchant3_3_0_, invoice0_.installmentNumber as installm4_3_0_, invoice0_.saleDate as saleDate3_0_, invoice0_.paymentDate as paymentD6_3_0_, invoice0_.amount as amount3_0_, invoice0_.amountType as amountType3_0_, invoice0_.saleType as saleType3_0_, invoice0_.ccType as ccType3_0_, invoice0_.statementType as stateme11_3_0_, invoice0_.statementId as stateme12_3_0_ from invoice invoice0_ with (holdlock, rowlock) where invoice0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Invoice [PESSIMISTIC_WRITE]: select invoice0_.id as id3_0_, invoice0_.invoiceNumber as invoiceN2_3_0_, invoice0_.merchantNumber as merchant3_3_0_, invoice0_.installmentNumber as installm4_3_0_, invoice0_.saleDate as saleDate3_0_, invoice0_.paymentDate as paymentD6_3_0_, invoice0_.amount as amount3_0_, invoice0_.amountType as amountType3_0_, invoice0_.saleType as saleType3_0_, invoice0_.ccType as ccType3_0_, invoice0_.statementType as stateme11_3_0_, invoice0_.statementId as stateme12_3_0_ from invoice invoice0_ with (updlock, rowlock) where invoice0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Invoice [PESSIMISTIC_FORCE_INCREMENT]: select invoice0_.id as id3_0_, invoice0_.invoiceNumber as invoiceN2_3_0_, invoice0_.merchantNumber as merchant3_3_0_, invoice0_.installmentNumber as installm4_3_0_, invoice0_.saleDate as saleDate3_0_, invoice0_.paymentDate as paymentD6_3_0_, invoice0_.amount as amount3_0_, invoice0_.amountType as amountType3_0_, invoice0_.saleType as saleType3_0_, invoice0_.ccType as ccType3_0_, invoice0_.statementType as stateme11_3_0_, invoice0_.statementId as stateme12_3_0_ from invoice invoice0_ where invoice0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Invoice [OPTIMISTIC]: select invoice0_.id as id3_0_, invoice0_.invoiceNumber as invoiceN2_3_0_, invoice0_.merchantNumber as merchant3_3_0_, invoice0_.installmentNumber as installm4_3_0_, invoice0_.saleDate as saleDate3_0_, invoice0_.paymentDate as paymentD6_3_0_, invoice0_.amount as amount3_0_, invoice0_.amountType as amountType3_0_, invoice0_.saleType as saleType3_0_, invoice0_.ccType as ccType3_0_, invoice0_.statementType as stateme11_3_0_, invoice0_.statementId as stateme12_3_0_ from invoice invoice0_ where invoice0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Invoice [OPTIMISTIC_FORCE_INCREMENT]: select invoice0_.id as id3_0_, invoice0_.invoiceNumber as invoiceN2_3_0_, invoice0_.merchantNumber as merchant3_3_0_, invoice0_.installmentNumber as installm4_3_0_, invoice0_.saleDate as saleDate3_0_, invoice0_.paymentDate as paymentD6_3_0_, invoice0_.amount as amount3_0_, invoice0_.amountType as amountType3_0_, invoice0_.saleType as saleType3_0_, invoice0_.ccType as ccType3_0_, invoice0_.statementType as stateme11_3_0_, invoice0_.statementId as stateme12_3_0_ from invoice invoice0_ where invoice0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for action ACTION_MERGE on entity com.myapp.domain.cc.Invoice: select invoice0_.id as id3_0_, invoice0_.invoiceNumber as invoiceN2_3_0_, invoice0_.merchantNumber as merchant3_3_0_, invoice0_.installmentNumber as installm4_3_0_, invoice0_.saleDate as saleDate3_0_, invoice0_.paymentDate as paymentD6_3_0_, invoice0_.amount as amount3_0_, invoice0_.amountType as amountType3_0_, invoice0_.saleType as saleType3_0_, invoice0_.ccType as ccType3_0_, invoice0_.statementType as stateme11_3_0_, invoice0_.statementId as stateme12_3_0_ from invoice invoice0_ where invoice0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for action ACTION_REFRESH on entity com.myapp.domain.cc.Invoice: select invoice0_.id as id3_0_, invoice0_.invoiceNumber as invoiceN2_3_0_, invoice0_.merchantNumber as merchant3_3_0_, invoice0_.installmentNumber as installm4_3_0_, invoice0_.saleDate as saleDate3_0_, invoice0_.paymentDate as paymentD6_3_0_, invoice0_.amount as amount3_0_, invoice0_.amountType as amountType3_0_, invoice0_.saleType as saleType3_0_, invoice0_.ccType as ccType3_0_, invoice0_.statementType as stateme11_3_0_, invoice0_.statementId as stateme12_3_0_ from invoice invoice0_ where invoice0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Transaction [NONE]: select transactio0_.id as id4_0_, transactio0_.ccNumber as ccNumber4_0_, transactio0_.approvalCode as approval3_4_0_, transactio0_.saleAmount as saleAmount4_0_, transactio0_.installmentNumber as installm5_4_0_, transactio0_.numberOfInstallments as numberOf6_4_0_, transactio0_.invoiceId as invoiceId4_0_ from transactions transactio0_ where transactio0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Transaction [READ]: select transactio0_.id as id4_0_, transactio0_.ccNumber as ccNumber4_0_, transactio0_.approvalCode as approval3_4_0_, transactio0_.saleAmount as saleAmount4_0_, transactio0_.installmentNumber as installm5_4_0_, transactio0_.numberOfInstallments as numberOf6_4_0_, transactio0_.invoiceId as invoiceId4_0_ from transactions transactio0_ where transactio0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Transaction [UPGRADE]: select transactio0_.id as id4_0_, transactio0_.ccNumber as ccNumber4_0_, transactio0_.approvalCode as approval3_4_0_, transactio0_.saleAmount as saleAmount4_0_, transactio0_.installmentNumber as installm5_4_0_, transactio0_.numberOfInstallments as numberOf6_4_0_, transactio0_.invoiceId as invoiceId4_0_ from transactions transactio0_ with (updlock, rowlock) where transactio0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Transaction [UPGRADE_NOWAIT]: select transactio0_.id as id4_0_, transactio0_.ccNumber as ccNumber4_0_, transactio0_.approvalCode as approval3_4_0_, transactio0_.saleAmount as saleAmount4_0_, transactio0_.installmentNumber as installm5_4_0_, transactio0_.numberOfInstallments as numberOf6_4_0_, transactio0_.invoiceId as invoiceId4_0_ from transactions transactio0_ with (updlock, rowlock) where transactio0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Transaction [FORCE]: select transactio0_.id as id4_0_, transactio0_.ccNumber as ccNumber4_0_, transactio0_.approvalCode as approval3_4_0_, transactio0_.saleAmount as saleAmount4_0_, transactio0_.installmentNumber as installm5_4_0_, transactio0_.numberOfInstallments as numberOf6_4_0_, transactio0_.invoiceId as invoiceId4_0_ from transactions transactio0_ where transactio0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Transaction [PESSIMISTIC_READ]: select transactio0_.id as id4_0_, transactio0_.ccNumber as ccNumber4_0_, transactio0_.approvalCode as approval3_4_0_, transactio0_.saleAmount as saleAmount4_0_, transactio0_.installmentNumber as installm5_4_0_, transactio0_.numberOfInstallments as numberOf6_4_0_, transactio0_.invoiceId as invoiceId4_0_ from transactions transactio0_ with (holdlock, rowlock) where transactio0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Transaction [PESSIMISTIC_WRITE]: select transactio0_.id as id4_0_, transactio0_.ccNumber as ccNumber4_0_, transactio0_.approvalCode as approval3_4_0_, transactio0_.saleAmount as saleAmount4_0_, transactio0_.installmentNumber as installm5_4_0_, transactio0_.numberOfInstallments as numberOf6_4_0_, transactio0_.invoiceId as invoiceId4_0_ from transactions transactio0_ with (updlock, rowlock) where transactio0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Transaction [PESSIMISTIC_FORCE_INCREMENT]: select transactio0_.id as id4_0_, transactio0_.ccNumber as ccNumber4_0_, transactio0_.approvalCode as approval3_4_0_, transactio0_.saleAmount as saleAmount4_0_, transactio0_.installmentNumber as installm5_4_0_, transactio0_.numberOfInstallments as numberOf6_4_0_, transactio0_.invoiceId as invoiceId4_0_ from transactions transactio0_ where transactio0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Transaction [OPTIMISTIC]: select transactio0_.id as id4_0_, transactio0_.ccNumber as ccNumber4_0_, transactio0_.approvalCode as approval3_4_0_, transactio0_.saleAmount as saleAmount4_0_, transactio0_.installmentNumber as installm5_4_0_, transactio0_.numberOfInstallments as numberOf6_4_0_, transactio0_.invoiceId as invoiceId4_0_ from transactions transactio0_ where transactio0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for entity com.myapp.domain.cc.Transaction [OPTIMISTIC_FORCE_INCREMENT]: select transactio0_.id as id4_0_, transactio0_.ccNumber as ccNumber4_0_, transactio0_.approvalCode as approval3_4_0_, transactio0_.saleAmount as saleAmount4_0_, transactio0_.installmentNumber as installm5_4_0_, transactio0_.numberOfInstallments as numberOf6_4_0_, transactio0_.invoiceId as invoiceId4_0_ from transactions transactio0_ where transactio0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for action ACTION_MERGE on entity com.myapp.domain.cc.Transaction: select transactio0_.id as id4_0_, transactio0_.ccNumber as ccNumber4_0_, transactio0_.approvalCode as approval3_4_0_, transactio0_.saleAmount as saleAmount4_0_, transactio0_.installmentNumber as installm5_4_0_, transactio0_.numberOfInstallments as numberOf6_4_0_, transactio0_.invoiceId as invoiceId4_0_ from transactions transactio0_ where transactio0_.id=? 
org.hibernate.loader.entity.EntityLoader - Static select for action ACTION_REFRESH on entity com.myapp.domain.cc.Transaction: select transactio0_.id as id4_0_, transactio0_.ccNumber as ccNumber4_0_, transactio0_.approvalCode as approval3_4_0_, transactio0_.saleAmount as saleAmount4_0_, transactio0_.installmentNumber as installm5_4_0_, transactio0_.numberOfInstallments as numberOf6_4_0_, transactio0_.invoiceId as invoiceId4_0_ from transactions transactio0_ where transactio0_.id=? 
... 

對不起!問,你應該收到:)

+0

您是否啓用了SQL日誌記錄/調試,以便您可以查看正在運行的SQL語句? – davidfrancis 2012-03-29 22:07:16

+0

看到我的更新調試細節。 – 2012-03-30 19:18:55

+0

夢魘......!我很驚訝它不會在hql上級聯刪除,我認爲這是這些實體映射引擎的一部分?很高興看到你排序雖然 – davidfrancis 2012-03-30 22:28:03

回答

7

最快的方法是手動刪除。您必須爲每個孩子使用單獨的刪除語句,而不是依賴級聯。您還需要先刪除孩子,以避免暫時違反外鍵關係。

或者,您可以使用代理抓取加速它。很可能大部分時間都花費在獲取不需要的數據上。當你使用代理獲取時,Hibernate只會獲取id並創建代理對象,這些對象會在第一次使用時自我實例化。但是,由於您立即刪除它們,因此不需要實例化。

+0

感謝您的答案。這就是我的想法,對我來說,看起來很奇怪,沒有一種有效的方式來以更類似於Hibernate的方式進行級聯刪除。我將代碼更改爲三個帶連接的HQL刪除語句。在一秒之內執行! – 2012-03-30 18:11:08