データ コントラクト名
クライアントとサービスが同じ型を共有しないことがあります。 このような場合でも、双方のデータ コントラクトが等価であれば、相互にデータを受け渡すことができます。 データ コントラクトの等価性は、データ コントラクトとデータ メンバーの名前に基づいているため、型とメンバーをそれらの名前にマップするための機構が用意されています。 ここでは、データ コントラクトの命名規則に加えて、名前を作成する際の Windows Communication Foundation (WCF) インフラストラクチャの既定の動作についても説明します。
基本的な規則
データ コントラクトの名前付けに関する基本的な規則は次のとおりです。
データ コントラクトの完全修飾名は、名前空間と名前から構成されます。
データ メンバーは名前のみを持ち、名前空間はありません。
データ コントラクトを処理するときに、WCF インフラストラクチャでは、データ コントラクトおよびデータ メンバーの名前空間と名前の両方について大文字と小文字が区別されます。
データ コントラクト名前空間
データ コントラクトの名前空間は、URI (Uniform Resource Identifier) の形式を使用します。 URI は、絶対 URI でも相対 URI のどちらでもかまいません。 既定では、特定の型のデータ コントラクトには、その型の共通言語ランタイム (CLR: Common Language Runtime) 名前空間に基づく名前空間が割り当てられます。
既定では、指定された CLR 名前空間 (Clr.Namespace の形式) は、名前空間 http://schemas.datacontract.org/2004/07/Clr.Namespace
にマップされます。 この既定をオーバーライドするには、ContractNamespaceAttribute 属性をモジュールまたはアセンブリ全体に適用します。 また、型ごとにデータ コントラクト名前空間を制御するには、Namespace の DataContractAttribute プロパティを設定します。
Note
http://schemas.microsoft.com/2003/10/Serialization
名前空間は予約されており、データ コントラクトの名前空間として使用することはできません。
Note
delegate
宣言を含むデータ コントラクト型では、既定の名前空間をオーバーライドすることはできません。
データ コントラクト名
ある型のデータ コントラクトの既定の名前は、その型の名前になります。 この既定をオーバーライドするには、Name の DataContractAttribute プロパティを別の名前に設定します。 ジェネリック型に関する特別な規則については、このトピックで後述される「ジェネリック型のデータ コントラクト名」で説明します。
データ メンバー名
フィールドまたはプロパティのデータ メンバーの既定の名前は、そのフィールドまたはプロパティの名前になります。 この既定をオーバーライドするには、Name の DataMemberAttribute プロパティを別の値に設定します。
例
次の例では、データ コントラクトおよびデータ メンバーの既定の名前付け動作をオーバーライドする方法を示します。
// This overrides the standard namespace mapping for all contracts
// in Contoso.CRM.
[assembly: ContractNamespace("http://schemas.example.com/crm",
ClrNamespace = "Contoso.CRM")]
namespace Contoso.CRM
{
// The namespace is overridden to become:
// http://schemas.example.com/crm.
// But the name is the default "Customer".
[DataContract]
public class Customer
{
// Code not shown.
}
}
namespace Contoso.OrderProc
{
[DataContract]
public class PurchaseOrder
{
// This data member is named "Amount" by default.
[DataMember]
public double Amount;
// The default is overridden to become "Address".
[DataMember(Name = "Address")]
public string Ship_to;
}
// The namespace is the default value:
// http://schemas.datacontract.org/2004/07/Contoso.OrderProc
// The name is "PurchaseOrder" instead of "MyInvoice".
[DataContract(Name = "PurchaseOrder")]
public class MyInvoice
{
// Code not shown.
}
// The contract name is "Payment" instead of "MyPayment"
// and the Namespace is "http://schemas.example.com" instead
// of the default.
[DataContract(Name = "Payment",
Namespace = "http://schemas.example.com")]
public class MyPayment
{
// Code not shown.
}
}
' This overrides the standard namespace mapping for all contracts
' in Contoso.CRM.
<Assembly: ContractNamespace("http://schemas.example.com/crm", _
ClrNamespace:="Contoso.CRM")>
Namespace Contoso.CRM
' The namespace is overridden to become:
' http://schemas.example.com/crm.
' But the name is the default "Customer".
<DataContract()> _
Public Class Customer
' Code not shown.
End Class
End Namespace
Namespace Contoso.OrderProc
<DataContract()> _
Public Class PurchaseOrder
' This data member is named "Amount" by default.
<DataMember()> _
Public Amount As Double
' The default is overridden to become "Address".
<DataMember(Name:="Address")> _
Public Ship_to As String
End Class
' The namespace is the default value:
' http://schemas.datacontract.org/2004/07/Contoso.OrderProc
' The name is "PurchaseOrder" instead of "MyInvoice".
<DataContract(Name:="PurchaseOrder")> _
Public Class MyInvoice
' Code not shown.
End Class
' The contract name is "Payment" instead of "MyPayment"
' and the Namespace is "http://schemas.example.com" instead
' of the default.
<DataContract(Name:="Payment", [Namespace]:="http://schemas.example.com")> _
Public Class MyPayment
' Code not shown.
End Class
End Namespace
ジェネリック型のデータ コントラクト名
ジェネリック型のデータ コントラクト名を決定する場合は、特別な規則があります。 これらの規則は、同じジェネリック型の 2 つのクローズ ジェネリックの間でデータ コントラクト名の競合を回避するのに役立ちます。
既定では、ジェネリック型のデータ コントラクト名は、型の名前の後に文字列 "Of"、ジェネリック パラメーターのデータ コントラクト名、ジェネリック パラメーターのデータ コントラクト名前空間を使用して計算された "ハッシュ" が続きます。 ハッシュとは、1 つのデータを一意に識別するための "フィンガープリント" として機能する、数学関数の結果です。 ジェネリック パラメーターがすべてプリミティブ型の場合は、ハッシュは省略されます。
たとえば、次の例の型を見てください。
[DataContract]
public class Drawing<Shape, Brush>
{
// Code not shown.
}
[DataContract(Namespace = "urn:shapes")]
public class Square
{
// Code not shown.
}
[DataContract(Name = "RedBrush", Namespace = "urn:default")]
public class RegularRedBrush
{
// Code not shown.
}
[DataContract(Name = "RedBrush", Namespace = "urn:special")]
public class SpecialRedBrush
{
// Code not shown.
}
<DataContract()> _
Public Class Drawing(Of Shape, Brush)
<DataContract([Namespace]:="urn:shapes")> _
Public Class Square
' Code not shown.
End Class
<DataContract(Name:="RedBrush", [Namespace]:="urn:default")> _
Public Class RegularRedBrush
' Code not shown.
End Class
<DataContract(Name:="RedBrush", [Namespace]:="urn:special")> _
Public Class SpecialRedBrush
' Code not shown.
End Class
End Class
この例では、Drawing<Square,RegularRedBrush>
型は "DrawingOfSquareRedBrush5HWGAU6h" というデータ コントラクト名を持ちます。ここで "5HWGAU6h" は "urn:shapes" および "urn:default" 名前空間のハッシュになります。 Drawing<Square,SpecialRedBrush>
型は "DrawingOfSquareRedBrushjpB5LgQ_S" というデータ コントラクト名を持ちます。ここで "jpB5LgQ_S" は "urn:shapes" および "urn:special" 名前空間のハッシュになります。 ハッシュを使用しないと 2 つの名前は同一になり、名前の競合が発生することに注意してください。
ジェネリック型のデータ コントラクト名のカスタマイズ
前述のようにジェネリック型用に生成されたデータ コントラクト名を容認できない場合があります。 たとえば、名前の競合が起こらないことが前もってわかっているため、ハッシュを削除するとします。 この場合、DataContractAttribute.Name プロパティを使用して、名前を生成する別の方法を指定できます。 Name
プロパティの中かっこ内に数字を指定して、ジェネリック パラメーターのデータ コントラクト名を参照できます (0 は最初のパラメーターを参照し、1 は 2 番目を参照します。以下同様です)。中かっこ内にシャープ記号 (#) を指定すると、ハッシュを参照できます。 これらの各参照は、複数回使用しても、まったく使用しなくてもかまいません。
たとえば、前の Drawing
ジェネリック型は次の例に示すように宣言できます。
[DataContract(Name = "Drawing_using_{1}_brush_and_{0}_shape")]
public class Drawing<Shape, Brush>
{
// Code not shown.
}
<DataContract(Name:="Drawing_using_{1}_brush_and_{0}_shape")> _
Public Class Drawing(Of Shape, Brush)
' Code not shown.
End Class
この場合、Drawing<Square,RegularRedBrush>
型は、"Drawing_using_RedBrush_brush_and_Square_shape" というデータ コントラクト名になります。 Name プロパティに "{#}" があるため、名前にはハッシュは含まれません。したがって、この型では名前の競合が発生しやすくなります。たとえば、Drawing<Square,SpecialRedBrush>
型は、まったく同じデータ コントラクト名を持ちます。