2 सत्र इस तरह दिखने चाहिए:
user = Student.query.with_for_update(of=Student, nowait=True).filter(Student.id == 122).first()
user.type = 1
db.session.commit()
और
user = Student.query.with_for_update(of=Student, nowait=True).filter(Student.id == 122).first()
user.type -= 1
db.session.commit()
FOR UPDATE
. के क्रम में ठीक से काम करने के लिए, सभी शामिल लेनदेन जो पंक्ति को अद्यतन करने का इरादा रखते हैं, उन्हें इसका उपयोग करने की आवश्यकता है।
आपके उदाहरण में, सत्र 2 with_for_update
. का उपयोग नहीं कर रहा है . चूंकि आपने इसे FOR UPDATE
. का उपयोग करने के लिए नहीं कहा था , यह पंक्ति के पुराने मान को पढ़ने के लिए स्वतंत्र है (चूंकि नया मान अभी तक प्रतिबद्ध नहीं किया गया है, और ताले शुद्ध पाठकों को ब्लॉक नहीं करते हैं), फिर उस इन-मेमोरी मान को संशोधित करें, फिर उसे वापस लिखें।
यदि आप FOR UPDATE
. का उपयोग नहीं करना चाहते हैं हर जगह जहां आप इसे बदलने के इरादे से पंक्ति पढ़ते हैं, आप इसके बजाय isolation level serializable
का उपयोग कर सकते हैं हर जगह। हालाँकि यदि आप करते हैं, तो चीजें अवरुद्ध नहीं हो सकती हैं, बल्कि प्रतिबद्ध होने तक सफल होती दिखाई देंगी, फिर क्रमांकन त्रुटियों को फेंक दें जिन्हें पकड़ने और उनसे निपटने की आवश्यकता होगी।
नोट: आपके पूर्व-संपादन उदाहरण को काम करना चाहिए था क्योंकि दोनों सत्रों को with_for_update
. के साथ लेबल किया गया था ।