Workerロールインスタンス間のコミュニケーション手段

2010年3月17日 | By TatsuakiSakai | Filed in: Micosoft Azure.

もはや説明の必要は無いかも知れませんが、Windows Azureのコンピュートサービスで実行されるアプリケーションにはWebロールとWorkerロールが存在し、それぞれのインスタンスが独立した仮想マシン内で実行されています。

場合によっては、独立したインスタンス間でコミュニケーションを図りたいこともあります。
特にWorkerロール間ではTCPによるコミュニケーションが可能になっていますので、これを活用してWorkerロールインスタンスの間で情報を同期するなどの実装が可能になります。

たとえば、Webロールのセッション情報をWorkerロールで管理し、セッション状態を各Workerロールインスタンス間でシェアするといったような使い方が可能です。

これにより、ストレージへの書き込みが発生しないため、高速にセッション情報へアクセスすることが可能です。

もちろん、WebロールもTCPを用いてWorkerロールを呼び出すという前提があります。
Windows AzureにはWorkerロール間のコミュニケーションをサポートするためのTCPポートが提供されています。
その名もInternalEndpointといいます。

InternalEndpointを利用するには、まずWorkerロールのプロパティページで「Endpoints」タグを開き、エンドポイントを追加します。

この時に「Type」を「Internal」にすることでInternalEndpointの利用が可能になります。

この設定を保存すると、ServiceDefinition.csdefに以下のような記述が追加されます。

<Endpoints>
    <InternalEndpoint name=”InnerCommunicationprotocol=”tcp />
</Endpoints>

そして、設定の適用は以下のように記述します。

NetTcpBinding binding = new NetTcpBinding(SecurityMode.None);
RoleInstanceEndpoint innerEndPoint =
    RoleEnvironment.CurrentRoleInstance.InstanceEndpoints[“InnerCommunication“];
this.serviceHost = new ServiceHost(typeof(InnerCommunication));
this.serviceHost.AddServiceEndpoint(
        typeof(IInnerCommunication),
        binding,
        String.Format(“net.tcp://{0}/InnerCommunication“, innerEndPoint.IPEndpoint));
serviceHost.Open();

実際に、登録されたエンドポイントは他のインスタンスから以下のコードで参照することが可能です。

var current = RoleEnvironment.CurrentRoleInstance;
var endPoints = current.Role.Instances.Where(instance => instance != current)
          .Select(instance => instance.InstanceEndpoints[“InnerCommunication“]);

このコードを見てお分かりになるかと思いますが、RoleEnvironmentにCurrentRoleInstanceという静的プロパティがあります。これは同種ロールのインスタンスのコレクションとして存在しています。

このコレクションに対し、クエリを実行することでエンドポイントを発見することが可能です。
あとは、endPointsに対してforeachループで各エンドポイントを取り出すことで、各エンドポイントのロケーションを取得することができます。

追記:
サンプルコードを添付しておきます。
このサンプルは、Visual Studio 2010 RCおよびWindows Azure Tools for Visual Studio 2010 Ver 1.1を利用して開発しています。以下のリンクからダウンロードしてください。

InnerCommunication


Tags:

Comments are closed here.