要求コンテキスト

RequestContext は、トレース ID などのアプリケーション メタデータが要求と共に送信できるようにする Orleans の機能です。 アプリケーション メタデータはクライアントで追加でき、Orleans の要求と共に受信グレインに送信されます。 この機能は、Orleans 名前空間のパブリック静的クラス RequestContext によって実装されます。 このクラスでは、次の 2 つの簡単なメソッドが公開されています。

void Set(string key, object value)

上の API は、要求コンテキストに値を格納するために使われます。 値には、任意のシリアル化可能な型を指定できます。

Object Get(string key)

上の API は、現在の要求コンテキストから値を取得するために使われます。

RequestContext 用のバッキング ストレージは非同期ローカルです。 呼び出し元 (クライアント側か Orleans 内かに関係なく) が要求を送信すると、呼び出し元の RequestContext の内容が要求の Orleans メッセージに加えられます。要求を受信したグレインのコードは、ローカルの RequestContext からそのメタデータにアクセスできます。 グレインのコードで RequestContext が変更されない場合、要求されているすべてのグレインが同じメタデータを受け取ります。

ユーザーが StartNew または ContinueWith を使って将来の計算をスケジュールすると、アプリケーション メタデータも保持されます。どちらの場合も、継続は、計算がスケジュールされた時点でスケジュール コードが持っていたのと同じメタデータを使って実行されます (つまり、システムは現在のメタデータのコピーを作成してそれを継続に渡すので、StartNew または ContinueWith の呼び出し後の変更は継続によって認識されません)。

重要

アプリケーション メタデータは、応答と共に返送されません。つまり、ContinueWith 継続内で、あるいは Task.Wait() または GetValue の呼び出しの後で、応答受信の結果として実行されるコードは、元の要求によって設定された現在のコンテキスト内で引き続き実行されます。

たとえば、クライアント内でトレース ID を新しい Guid に設定するには、単に以下を呼び出します。

RequestContext.Set("TraceId", Guid.NewGuid());

グレインのコード (またはスケジューラ スレッド上の Orleans 内で実行される他のコード) 内では、たとえばログを書き込むときに、元のクライアント要求のトレース ID を使用できます。

Logger.Info("Currently processing external request {0}", RequestContext.Get("TraceId"));

任意のシリアル化可能オブジェクトをアプリケーション メタデータとして送信できますが、大きいオブジェクトや複雑なオブジェクトを送信すると、メッセージのシリアル化時間に顕著なオーバーヘッドが加わる可能性があることに注意してください。 このため、単純型 (文字列、GUID、または数値型) を使うことをお勧めします。