2014-04-30 3 views
0

현재 트랜잭션이 수동으로 롤업되는 일부 레거시 코드로 작업하고 있습니다. (문법/설계 문제를 무시하고, 단지 설명을위한 예) 다음 사항을 고려하십시오최대 절전 모드 : 상위 트랜잭션 내에서 커밋

import org.springframework.transaction.TransactionStatus; 
import org.springframework.transaction.support.DefaultTransactionDefinition; 

private PlatformTransactionManager transactionManager; 
private DefaultTransactionDefinition txDefRequired = new DefaultTransactionDefinition(TransactionDefinition.PROPAGATION_REQUIRED); 
private DefaultTransactionDefinition txDefRequiresNew new DefaultTransactionDefinition(TransactionDefinition.PROPAGATION_REQUIRES_NEW); 


void createPosts(Map<String, String> posts){ 

    TransactionStatus status = transactionManager.getTransaction(txDefRequiresNew) 
    try { 
     // posts Map is made up for username:posttext key pair 
     for (Map.Entry<String, String> entry : posts.entrySet()) { 
      // Construct online post 
      createPost(entry.getKey(), entry.getValue()); 
     } 
     transactionManager.commit(status); 
    } finally { 
     if (!status.isCompleted()) { 
      transactionManager.rollback(status); 
     } 

    } 
} 

void createPost(String username, String text){ 

    TransactionStatus status = transactionManager.getTransaction(txDefRequired) 

    // Construct online post 
    OnlinePost p = new OnlinePost(text); 
    User u = resolveUser(username); 
    p.setUser(u); 

    transactionManager.commit(status); // flush the session 
} 

User resolveUser(String username){ 

    TransactionStatus status = transactionManager.getTransaction(txDefRequired) 
    User u = getUser(username); 
    if(u == null) 
     createUser(username); 
    return u; 
    transactionManager.commit(status); // flush the session 

} 

는이 특정 흐름에 그 말을 정확겠습니까, tx.commit()를 호출 방법 내에서 이러한에게 resolveUser()은 세션 (flush-mode = auto)을 플러시하고 인위적 기본 키가 생성되어 할당 된 새 영구 엔터티를 반환하여 나중에 동일한 트랜잭션에서 사용할 수 있도록합니다.

답변

1

아니오. 확약은 항상 작업 단위 (UOW)를 종료하고 갱신 사항을 데이터베이스로 푸시합니다. 반면에 플러시는 db에 변경 사항을 커밋하지 않습니다 (모든 사용자에게 표시되도록 커밋하는 것처럼). 기술적으로 플러시 된 변경 사항을 롤백 할 수 있습니다. 가능한 복제본은 https://stackoverflow.com/a/14626510/2231632입니다.

인공 기본 키를 사용하여 원하는 것을 Session.flush로 사용할 수 있습니다. 그러나 동일한 txn에서 해당 키를 사용하려면 txn을 사용하지 마십시오.

+1

'flush'에 대한 설명이 잘못되었습니다. 지속성 공급자는 읽기 커밋 된 sematics를 유지하면서 db의 변경 사항을 명시 할 수 있습니다. – kostja

+0

그것을 지적 해 주셔서 감사합니다. 나는 조금 더 분명 했어야했다. db에 변경 사항을 적용한다고 말했을 때 나는 다른 사람들이 볼 수있는 변경 사항을 실제로 생각하고있었습니다. 지금 편집되었습니다. – prabugp

+0

쿨 :) +1 .... – kostja

관련 문제