同時実行
同時実行のサンプルでは、ServiceBehaviorAttribute を ConcurrencyMode 列挙体と共に使用する方法を示します。この列挙体は、サービスのインスタンスがメッセージを順番に処理するか、または同時に処理するかを制御します。このサンプルは、ICalculator
サービス コントラクトを実装する「入門サンプル」に基づいています。このサンプルでは、ICalculator
から継承される新しいコントラクト ICalculatorConcurrency
を定義します。これによって、サービスの同時実行の状態を検査するための 2 つの操作が追加されます。同時実行設定を変更してから、クライアントを実行して動作の変更を確認します。
この例では、クライアントはコンソール アプリケーション (.exe) であり、サービスはインターネット インフォメーション サービス (IIS) によってホストされます。
注 : |
---|
このサンプルのセットアップ手順とビルド手順については、このトピックの最後を参照してください。 |
選択可能な同時実行モードは次の 3 つです。
Single: 各サービス インスタンスは、一度に 1 つのメッセージを処理します。これが既定の同時実行モードです。
Multiple: 各サービス インスタンスは、同時に複数のメッセージを処理します。この同時実行モードを使用するには、サービスの実装がスレッドセーフである必要があります。
Reentrant: 各サービス インスタンスは、一度に 1 つのメッセージを処理しますが、再入可能呼び出しを受け入れます。サービスがこの呼び出しを受け入れるのは、コール アウトするときだけです。再入は「ConcurrencyMode 再入」サンプルで説明されています。
同時実行の使用は、インスタンス化モードに関連します。PerCall インスタンス化では、各メッセージが新しいサービス インスタンスによって処理されるため、同時実行は関係しません。Single インスタンス化では、Single と Multiple のいずれかの同時実行が関係します。これは 1 つのインスタンスがメッセージを順番に処理するか、同時に処理するかによって決まります。PerSession インスタンス化では、どの同時実行モードも関係する可能性があります。
サービス クラスは、[ServiceBehavior(ConcurrencyMode=<setting>)]
属性を使用して同時実行動作を指定します。次のサンプル コードを参照してください。行のコメント化を変更して、Single および Multiple の同時実行モードをそれぞれ試してみてください。同時実行モードを変更したら、サービスを再ビルドする必要があります。
// Single allows a single message to be processed sequentially by each service instance.
//[ServiceBehavior(ConcurrencyMode = ConcurrencyMode.Single, InstanceContextMode = InstanceContextMode.Single)]
// Multiple allows concurrent processing of multiple messages by a service instance.
// The service implementation should be thread-safe. This can be used to increase throughput.
[ServiceBehavior(ConcurrencyMode=ConcurrencyMode.Multiple, InstanceContextMode = InstanceContextMode.Single)]
// Uses Thread.Sleep to vary the execution time of each operation.
public class CalculatorService : ICalculatorConcurrency
{
int operationCount;
public double Add(double n1, double n2)
{
operationCount++;
System.Threading.Thread.Sleep(180);
return n1 + n2;
}
public double Subtract(double n1, double n2)
{
operationCount++;
System.Threading.Thread.Sleep(100);
return n1 - n2;
}
public double Multiply(double n1, double n2)
{
operationCount++;
System.Threading.Thread.Sleep(150);
return n1 * n2;
}
public double Divide(double n1, double n2)
{
operationCount++;
System.Threading.Thread.Sleep(120);
return n1 / n2;
}
public string GetConcurrencyMode()
{
// Return the ConcurrencyMode of the service.
ServiceHost host = (ServiceHost)OperationContext.Current.Host;
ServiceBehaviorAttribute behavior = host.Description.Behaviors.Find<ServiceBehaviorAttribute>();
return behavior.ConcurrencyMode.ToString();
}
public int GetOperationCount()
{
// Return the number of operations.
return operationCount;
}
}
サンプルの既定の設定では、Single インスタンス化と Multiple 同時実行が使用されます。クライアント コードは、非同期プロキシを使用するように変更されています。これにより、クライアントはサービスを呼び出した後に、応答を待たずに次の呼び出しを行うことができます。サービスの同時実行モードの動作の違いを観察してください。
このサンプルを実行すると、操作要求および応答がクライアントのコンソール ウィンドウに表示されます。実行中のサービスの同時実行モードが表示され、各操作が呼び出され、その後で操作数が表示されます。同時実行モードが Multiple の場合、結果が返される順序は呼び出された順序とは異なります。サービスは複数のメッセージを同時に実行するからです。同時実行モードを Single に変更すると、結果は呼び出された順序どおりに返されます。サービスは各メッセージを順次処理するからです。クライアントをシャットダウンするには、クライアント ウィンドウで Enter キーを押します。
サンプルをセットアップ、ビルド、および実行するには
「Windows Communication Foundation サンプルの 1 回限りのセットアップの手順」が実行済みであることを確認します。
Svcutil.exe を使用してプロキシ クライアントを生成する場合は、/async オプションを指定します。
ソリューションの C# 版または Visual Basic .NET 版をビルドするには、「Windows Communication Foundation サンプルのビルド」の手順に従います。
単一コンピューター構成か複数コンピューター構成かに応じて、「Running the Windows Communication Foundation Samples」の手順に従います。
注 : |
---|
サンプルは、既にコンピューターにインストールされている場合があります。続行する前に、次の (既定の) ディレクトリを確認してください。
<InstallDrive>:\WF_WCF_Samples
このディレクトリが存在しない場合は、「.NET Framework 4 向けの Windows Communication Foundation (WCF) および Windows Workflow Foundation (WF) のサンプル」にアクセスして、Windows Communication Foundation (WCF) および WF のサンプルをすべてダウンロードしてください。このサンプルは、次のディレクトリに格納されます。
<InstallDrive>:\WF_WCF_Samples\WCF\Basic\Services\Behaviors\Concurrency
|