2016-03-28 3 views
1

Django 1.9アプリケーションでは、特定のリモートAPIへのクエリの結果に基づいてデータベースに変更が加えられるコードセクションが実行されています。たとえば、これはデータベース内のエンティティとして保存したいコミット、ファイル変更、レビューア、プル要求などのデータです。Djangoでのエラー処理でのアトミックブロックの使用

私が呼び出す数少ないAPIの1つが有効なデータの代わりに何らかのエラーを返す可能性が非常に高いです。私は本質的にこのセクションを単一のアトミックなトランザクションにする必要があるので、HTTP requestsから返されたエラーがなければ、すべての変更をデータベースにコミットします。それ以外の場合は、2つのAPIが正しく返されてもデータが失われる可能性がありますが、3番目のAPIは返されません。

Djangoがデータベーストランザクションのためにcommit hooksをサポートしていることがわかりましたが、それがこの状況に当てはまるのか、それをどうやって実装するのかと思っていました。

答えて

4

アトミック操作にしたい場合は、transaction.atomic()にラップしてください。コードのいずれかが例外を発生させると、ブロック全体がロールバックされます。あなたがうまく動作するはずのリモートAPIからの読み取りだけをしている場合。典型的なパターンは次のとおりです。

def my_function(): 
    try: 
     with transaction.atomic(): 
      # Do your work here 
      pass 
    except Exception: 
     # Do some error handling 
     pass 

Djangoはon_commit hookを持っているが、それはここでは実際に適用されていません。その目的は、トランザクションが正常に完了した後にいくつかのコードを実行することです。たとえば、トランザクションが成功した場合は、リモートAPIにログデータを書き込むことができます。

+0

例外の場合、 'transaction.atomic()'は正常に終了しますか?これはエラーハンドリングを中心に設計されているので、エラーがあるときは、例外を「除外」してエラーの記録を作成し、特定のユーザーに報告するなどしなければなりません。あるいは、別の関数'try except'ブロックを実行し、そこからエラー処理を行いますか? – skeletalbassman

+0

@skeletalbassman:確かに、アトムブロックをtry-except節にラップするだけです。答えに例を追加しました。 –

+0

うん、これはトリックです。私はあなたの例を適用し、それが動作することを確認することができます。 – skeletalbassman

関連する問題