サービス コントラクト : エラー コントラクト
エラー コントラクトのサンプルでは、エラー情報をサービスからクライアントに通信する方法を示します。サンプルは、「入門サンプル」に基づき、内部例外をエラーに変換するいくつかの追加コードをサービスに追加しています。クライアントは 0 による除算を試行し、サービスを強制的にエラー状態にします。
メモ : |
---|
このサンプルのセットアップ手順とビルド手順については、このトピックの最後を参照してください。 |
電卓コントラクトは、FaultContractAttribute が含まれるように変更されています。次のサンプル コードを参照してください。
[ServiceContract(Namespace="http://Microsoft.ServiceModel.Samples")]
public interface ICalculator
{
[OperationContract]
int Add(int n1, int n2);
[OperationContract]
int Subtract(int n1, int n2);
[OperationContract]
int Multiply(int n1, int n2);
[OperationContract]
[FaultContract(typeof(MathFault))]
int Divide(int n1, int n2);
}
FaultContractAttribute 属性は、Divide
操作が型 MathFault
のエラーを返すことができることを示します。シリアル化可能な任意の型のエラーが発生します。この場合、MathFault
は次のようなデータ コントラクトになります。
[DataContract(Namespace="http://Microsoft.ServiceModel.Samples")]
public class MathFault
{
private string operation;
private string problemType;
[DataMember]
public string Operation
{
get { return operation; }
set { operation = value; }
}
[DataMember]
public string ProblemType
{
get { return problemType; }
set { problemType = value; }
}
}
0 による除算の例外が発生すると、Divide
メソッドは FaultException 例外をスローします。次のサンプル コードを参照してください。この例外により、クライアントにエラーが送信されます。
public int Divide(int n1, int n2)
{
try
{
return n1 / n2;
}
catch (DivideByZeroException)
{
MathFault mf = new MathFault();
mf.operation = "division";
mf.problemType = "divide by zero";
throw new FaultException<MathFault>(mf);
}
}
クライアント コードは、0 による除算を要求することで強制的にエラーを発生させます。このサンプルを実行する場合は、操作要求および応答はクライアントのコンソール ウィンドウに表示されます。0 による除算がエラーとして報告されたことが示されます。クライアントをシャットダウンするには、クライアント ウィンドウで Enter キーを押します。
Add(15,3) = 18
Subtract(145,76) = 69
Multiply(9,81) = 729
FaultException<MathFault>: Math fault while doing division. Problem: divide by zero
Press <ENTER> to terminate client.
クライアントでこれを行うには、適切な FaultException<MathFault>
例外を次のようにキャッチします。
catch (FaultException<MathFault> e)
{
Console.WriteLine("FaultException<MathFault>: Math fault while doing " + e.Detail.operation + ". Problem: " + e.Detail.problemType);
client.Abort();
}
既定では、サービス実装の詳細がサービスのセキュリティの境界から漏えいするのを回避するため、予期しない例外の詳細はクライアントに送信されません。FaultContract
では、コントラクトでエラーを説明し、例外の特定の型がクライアントへの転送に適しているとマークできます。また FaultException<T>
には、エラーをコンシューマに送信するためのランタイム機構が用意されています。
ただし、デバッグ時にはサービス エラーの内部詳細を確認することが役立ちます。前に説明したセキュリティ動作を無効にするには、サーバーで未処理のすべての例外の詳細を、クライアントに送信するエラーに含めるように指定できます。これは、IncludeExceptionDetailInFaults を true に設定することによって行います。次の例に示すように、コードまたは構成のどちらを使用しても設定できます。
<behaviors>
<serviceBehaviors>
<behavior name="CalculatorServiceBehavior">
<serviceMetadata httpGetEnabled="True"/>
<serviceDebug includeExceptionDetailInFaults="True" />
</behavior>
</serviceBehaviors>
</behaviors>
さらに、サービスの behaviorConfiguration 属性を構成ファイルで “CalculatorServiceBehavior” に設定し、動作をサービスに関連付ける必要があります。
こうしたエラーをクライアントでキャッチするには、非ジェネリックの FaultException をキャッチする必要があります。
この動作はデバッグ目的でのみ使用し、製品版では有効にしないでください。
サンプルを設定、ビルド、および実行するには
「Windows Communication Foundation サンプルの 1 回限りのセットアップの手順」が実行済みであることを確認します。
ソリューションの C# 版または Visual Basic .NET 版をビルドするには、「Windows Communication Foundation サンプルのビルド」の手順に従います。
サンプルを単一コンピュータ構成または複数コンピュータ構成で実行するには、「Windows Communication Foundation サンプルの実行」の手順に従います。
Copyright © 2007 by Microsoft Corporation.All rights reserved.