6

Google App Engine の ndb は、_post_put_hook(self, future)次のように文書化された を提供します。

put() の後に実行されるフック

このフックをよりよく理解するために、いつ引数selfの結果と異なるのか疑問に思っています。future

モデル フックのドキュメントには、次の情報が記載されています。

非同期 API でポストフックを使用する場合、フックは、check_result()、get_result() を呼び出すか、(タスクレット内で) 非同期メソッドの future を生成することによってトリガーされます。Post フックは、RPC が成功したかどうかをチェックしません。フックは失敗に関係なく実行されます。

すべての post-hook には、呼び出し署名の最後に Future 引数があります。この Future オブジェクトは、アクションの結果を保持します。この Future で get_result() を呼び出して、結果を取得できます。フックが呼び出されるまでに Future が完了しているため、 get_result() がブロックされないことを確認できます。

ただし、次のようにput非同期で呼び出すと:

from google.appengine.ext import ndb

class MyModel(ndb.Model):
   xyz = ndb.StringProperty()

   def _post_put_hook(self, future):
      print "self.xyz: {}, future.xyz: {}".format(
             self.xyz, future.get_result().get().xyz))

m = MyModel()
f = m.put_async()
f.wait()

m.xyz = 'abc'
f = m.put_async()
f.wait()

出力:

self.xyz: None, future.xyz: None
self.xyz: abc, future.xyz: abc

self「put_async」のコンテキストでは、が変更前のモデルであり、futureが現在保存されているモデルであると合理的に期待できると思います。futureそれ以外の場合、putコンテキストでどのような目的があるかは明確ではありません。

のコンテキストでselfとが異なるのはいつですか? ここの目的は何ですか?futureputfuture

4

1 に答える 1

12

答えは説明にあると思います:

Post フックは、RPC が成功したかどうかをチェックしません。フックは失敗に関係なく実行されます。

future には、put(). この知識を使用して、フックを使用して put が失敗したときに処理できます。たとえば_post_put_hook、モデルのプロパティに基づいて関連付けられた SUM 集計モデルをインクリメントする責任がある場合、関連付けられた SUM 集計モデルをputインクリメントする前に、成功したかどうかを確認できます。RPC が失敗しない限り、selfandの値が変わることはないと思います。future.get_result().get()

このリクエストの後、が実行されるput前に、別のリクエストがモデルを更新した可能性は常にあります。この場合、別の値が返される可能性があります。_post_put_hookfuture.get_result().get(use_cache=False)

于 2013-04-01T13:17:26.437 に答える