2017-12-10 99 views
8

पर रोलबैक लेनदेन वहाँ एक इकाई हैस्प्रिंग डाटा:</p> <pre><code>@Entity class A { ... @Version int version; } </code></pre> <p><code>A</code> उदाहरणों अद्यतन आशावादी तरीके से लागू: पुन: प्रयास करें

@Transactional(rollbackFor = {StaleStateException.class}) 
@Retryable(value = {StaleStateException.class}) 
public void updateA() { 
    A a = findA(); 
    B b = new B(); 
    // Update "a" somehow 
    a.update(); 
    // "b" is saved on each retry! 
    save(b); 
} 

के रूप में टिप्पणी में कहा गया है, लगता है कि लेन-देन rollbacked नहीं है जब StaleStateException होता है, इसलिए B इंस्टेंस प्रत्येक पुनः प्रयास पर सहेजा जाता है।

क्या पुनः प्रयास पर रोलबैक लेनदेन करना संभव है?

वांछित व्यवहार यह है कि b केवल सफल a अद्यतन पर सहेजा गया है।

उत्तर

7

मुझे लगता है कि यह @Retryable कॉन्फ़िगरेशन से संबंधित कुछ हो सकता है।

जैसा कि दस्तावेज़ कहता है https://docs.spring.io/spring-batch/trunk/reference/html/retry.html#statelessRetry एक स्टेटलेस रीट्रीएबल एक चक्र से अधिक कुछ नहीं है जो उसी विधि को तब तक कॉल करता रहता है जब तक यह सफल नहीं हो जाता।

समस्या यह है कि हर बार जब यह पहले इंटरसेप्टर को विफल करता है तो वह पुनः प्रयास करने योग्य होता है जो अपवाद को पुनर्स्थापित नहीं करेगा, इसलिए यह कभी भी @Transactional तक नहीं पहुंचता है।

तो क्या होता है कि प्रत्येक पुनः प्रयास डिफ़ॉल्ट लेनदेन प्रचार का पालन करेगा जो संदर्भ में new B() के साथ उसी खुले लेनदेन का पुन: उपयोग करेगा।

आप जांच सकते हैं कि मैं डिबगिंग द्वारा सही सीसा पर हूं या नहीं: यदि आप दूसरी पुनः प्रयास करते हैं और पाते हैं कि A अद्यतन ब्लॉक से पहले ही अपडेट हो चुका है तो मुझे सही होना चाहिए।

आप 2 तरीकों से ठीक कर सकते हैं:

या तो दो ब्लॉक (नेस्टेड लेन-देन के साथ पहली बार पुन: प्रयास)

@Retryable(value = {StaleStateException.class}) 
public void retryableUpdate() { 
    updateA(); 
} 

@Transactional(rollbackFor = {StaleStateException.class}) 
public void updateA() { 
    A a = findA(); 
    B b = new B(); 
    // Update "a" somehow 
    a.update(); 
    // "b" is saved on each retry! 
    save(b); 
} 

ताकि लेनदेन वापस पहले लुढ़का हुआ है विभाजित करते हैं।

या आप दस्तावेज़ों का पालन कर सकते हैं और एक राज्यव्यापी पुनः प्रयास https://docs.spring.io/spring-batch/trunk/reference/html/retry.html#statefulRetry

का उपयोग कर सकते हैं
संबंधित मुद्दे