日本综合一区二区|亚洲中文天堂综合|日韩欧美自拍一区|男女精品天堂一区|欧美自拍第6页亚洲成人精品一区|亚洲黄色天堂一区二区成人|超碰91偷拍第一页|日韩av夜夜嗨中文字幕|久久蜜综合视频官网|精美人妻一区二区三区

RELATEED CONSULTING
相關(guān)咨詢
選擇下列產(chǎn)品馬上在線溝通
服務(wù)時間:8:30-17:00
你可能遇到了下面的問題
關(guān)閉右側(cè)工具欄

新聞中心

這里有您想知道的互聯(lián)網(wǎng)營銷解決方案
創(chuàng)新互聯(lián)Django4.0教程:Django4.0數(shù)據(jù)庫事務(wù)-管理數(shù)據(jù)庫事務(wù)

Django默認(rèn)的事務(wù)行為

Django 默認(rèn)的事務(wù)行為是自動提交。除非事務(wù)正在執(zhí)行,每個查詢將會馬上自動提交到數(shù)據(jù)庫。
Django 自動使用事務(wù)或還原點(diǎn),以確保需多次查詢的 ORM 操作的一致性,特別是 ?delete()? 和 ?update()? 操作。
由于性能原因,Django 的 ?TestCase? 類同樣將每個測試用事務(wù)封裝起來。

創(chuàng)新互聯(lián)主營朝天網(wǎng)站建設(shè)的網(wǎng)絡(luò)公司,主營網(wǎng)站建設(shè)方案,重慶APP開發(fā),朝天h5小程序開發(fā)搭建,朝天網(wǎng)站營銷推廣歡迎朝天等地區(qū)企業(yè)咨詢

將事務(wù)綁定到HTTP請求

在 Web 里,處理事務(wù)比較常用的方式是將每個請求封裝在一個事務(wù)中。 在你想啟用該行為的數(shù)據(jù)庫中,把配置中的參數(shù) ?ATOMIC_REQUESTS ?設(shè)置為 ?True?。
它是這樣工作的:在調(diào)用視圖方法前,Django 先生成一個事務(wù)。如果響應(yīng)能正常生成,Django 會提交該事務(wù)。而如果視圖出現(xiàn)異常,Django 則會回滾該事務(wù)。
你可以在你的視圖代碼中使用還原點(diǎn)執(zhí)行子事務(wù),一般會使用 ?atomic()? 上下文管理器。但是,在視圖結(jié)束時,要么所有的更改都被提交,要么所有的更改都不被提交。

注意:雖然這種簡潔的事務(wù)模型很吸引人,但在流量增加時,也會降低效率。為每個視圖打開一個事務(wù)都會帶來一些開銷。對性能的影響程度取決于應(yīng)用執(zhí)行的查詢語句和數(shù)據(jù)庫處理鎖的能力。

每次請求的事務(wù)和流式響應(yīng)

當(dāng)視圖返回一個 ?StreamingHttpResponse ?時,獲取該響應(yīng)的內(nèi)容總會執(zhí)行代碼,生成內(nèi)容。由于早就返回了該視圖,某些代碼會在事務(wù)外執(zhí)行。
一般來說,不建議在生成流式響應(yīng)時寫入數(shù)據(jù)庫,因為在開始發(fā)送響應(yīng)后,就沒有能有效處理錯誤的方法了。

實際上,此功能只是簡單地用下文介紹的 ?atomic()? 裝飾器裝飾了每個視圖函數(shù)。
注意,只有視圖被限制在事務(wù)中執(zhí)行。中間件在事務(wù)之外運(yùn)行,同理,渲染模板響應(yīng)也是在事務(wù)之外運(yùn)行的。
即便啟用了 ?ATOMIC_REQUESTS?,仍能避免視圖在事務(wù)中運(yùn)行。

non_atomic_requests(using=None)

該裝飾器會為指定視圖取消 ?ATOMIC_REQUESTS ?的影響。

from django.db import transaction

@transaction.non_atomic_requests
def my_view(request):
    do_stuff()

@transaction.non_atomic_requests(using='other')
def my_other_view(request):
    do_stuff_on_the_other_database()

只有在它被應(yīng)用到視圖時才會生效。

顯式控制事務(wù)

Django 提供了一個 API 控制數(shù)據(jù)庫事務(wù)。

atomic(using=None, savepoint=True, durable=False)

原子性是數(shù)據(jù)庫事務(wù)的定義屬性。 ?atomic ?允許創(chuàng)建代碼塊來保證數(shù)據(jù)庫的原子性。如果代碼塊成功創(chuàng)建,這個變動會提交到數(shù)據(jù)庫。如果有異常,變動會回滾。
?atomic ?塊可以嵌套。在這個例子里,當(dāng)內(nèi)部塊成功完成時,如果在稍后外部塊里引發(fā)了異常,則仍可回滾到最初效果。

確保原子塊始終是最外層的原子塊有時很有用,確保在退出塊時提交任何數(shù)據(jù)庫更改而沒有錯誤。 這稱為持久性,可以通過設(shè)置?durable=True?來實現(xiàn)。 如果原子塊嵌套在另一個塊中,則會引發(fā) ?RuntimeError?。

atomic 既可用作裝飾器:

from django.db import transaction

@transaction.atomic
def viewfunc(request):
    # This code executes inside a transaction.
    do_stuff()

并作為上下文管理器:

from django.db import transaction

def viewfunc(request):
    # This code executes in autocommit mode (Django's default).
    do_stuff()

    with transaction.atomic():
        # This code executes inside a transaction.
        do_more_stuff()

在 ?try?/?except ?塊中使用裝飾器 ?atomic ?來允許自然處理完整性錯誤:

from django.db import IntegrityError, transaction

@transaction.atomic
def viewfunc(request):
    create_parent()

    try:
        with transaction.atomic():
            generate_relationships()
    except IntegrityError:
        handle_exception()

    add_children()

在這個例子里,雖然 ?generate_relationships()? 會通過破壞完整性約束導(dǎo)致數(shù)據(jù)庫錯誤,但你可以 ?add_children()? 中執(zhí)行查找,來自 ?create_parent()? 的變化也會在這里,并且綁定到相同的事務(wù)。注意,任何試圖在 ?generate_relationships()? 中執(zhí)行的操作在 ?handle_exception()? 被調(diào)用的時候也會安全的回滾,因此異常處理也會在必要的時候在數(shù)據(jù)庫上操作。

要避免在 atomic 內(nèi)部捕捉異常!

當(dāng)存在 ?atomic ?塊時, Django 查看它是否正常退出或存在異常來決定是提交還是正?;貪L。如果你在 ?atomic ?內(nèi)部捕捉并且處理異常,你可以對 Django 隱藏問題代碼。這會導(dǎo)致一些意外的行為。
這主要是 ?DatabaseError ?和它的子類的一個問題(比如 ?IntegrityError ?)。出現(xiàn)這樣的錯誤之后,事務(wù)會奔潰,并且 Django 將在 ?atomic ?塊的末尾執(zhí)行回滾。如果你打算在回滾發(fā)生的時候運(yùn)行數(shù)據(jù)庫查詢,Django 將引發(fā) ?TransactionManagementError ?錯誤。當(dāng) ORM 相關(guān)的信號處理程序引發(fā)異常時,你也可能遇到這個問題。
捕捉數(shù)據(jù)庫錯誤的正確的方法是像上方所示那樣圍繞 ?atomic ?塊。如有需要,為此目的可以添加額外的 ?atomic ?塊。這個模式有別的優(yōu)勢:如果異常發(fā)生,它會明確界定哪些操作將回滾。
如果捕獲由原始SQL查詢引發(fā)的異常,那么Django的行為是未指定的,并且依賴于數(shù)據(jù)庫。

當(dāng)回滾事務(wù)時,你可能需要手工恢復(fù)模型狀態(tài)。

當(dāng)事務(wù)回滾時,模型字段的值不會被恢復(fù)。除非你手工恢復(fù)初始的字段值,否則這會導(dǎo)致模型狀態(tài)不一致。
例如,給定帶有 ?active ?字段的 ?MyModel ?模型,如果在事務(wù)中更新 ?active ?到 ?True ?失敗,那么這個片段確保最后的 ?if obj.active? 檢查使用正確的值:

from django.db import DatabaseError, transaction

obj = MyModel(active=False)
obj.active = True
try:
    with transaction.atomic():
        obj.save()
except DatabaseError:
    obj.active = False

if obj.active:
    ...

為了保證原子性,?atomic ?禁用了一些API。在 ?atomic ?塊中試圖提交、回滾或改變數(shù)據(jù)庫連接的自動提交狀態(tài)將引發(fā)異常。
?atomic ?帶有 ?using ?參數(shù),這個參數(shù)是數(shù)據(jù)庫名字。如果這個參數(shù)沒有提供,Django 會使用默認(rèn)數(shù)據(jù)庫。
在后臺,Django 的事務(wù)管理代碼:

  • 當(dāng)進(jìn)入最外面的 ?atomic塊時打開事務(wù);
  • 當(dāng)進(jìn)入 ?atomic ?塊內(nèi)部時創(chuàng)建一個保存點(diǎn);
  • 從塊內(nèi)部退出時釋放或回滾保存點(diǎn);
  • 離開塊的最外層時提交或回滾事務(wù)。

你可以通過設(shè)置 ?savepoint ?參數(shù)為 ?False ?來為內(nèi)部塊禁用保存點(diǎn)的創(chuàng)建。如果發(fā)生異常,Django將在退出帶有保存點(diǎn)的第一個父塊(如果有的話)時執(zhí)行回滾,否則退出最外面的塊。外部事物仍保證了原子性。僅當(dāng)保存點(diǎn)開銷明顯時,才應(yīng)使用此選項。它的缺點(diǎn)是破壞了上述錯誤處理。

當(dāng)自動提交關(guān)閉時,可以使用 ?atomic ?。它將只使用保存點(diǎn),即使對于最外面的塊也是如此。

性能考慮因素

打開事務(wù)會對數(shù)據(jù)庫服務(wù)器有性能成本。盡量減少這種開銷,要保持事務(wù)盡可能簡短。如果正在 Django 的請求 / 響應(yīng)周期之外,在長時間運(yùn)行的進(jìn)程中使用 ?atomic()? ,這點(diǎn)尤其重要。


本文名稱:創(chuàng)新互聯(lián)Django4.0教程:Django4.0數(shù)據(jù)庫事務(wù)-管理數(shù)據(jù)庫事務(wù)
標(biāo)題路徑:http://www.dlmjj.cn/article/dpesejp.html