0

Data Services v3 の検出エンドポイント (TCP と UDP の両方) を公開し、クライアントからサービスを検出できるようにして、別のアプリケーションでそれらを検出できるようにしたいと考えています。検出の主なポイントは、クライアントでサービス エンドポイント アドレスを取得することです。

Microsoft がWCF Discoveryに提供したサンプルを適応させようとしましたが、これまでのところ目標を達成できませんでした。サーバー側でカスタムData Service Host Factoryを作成しました。

public class CustomDataServiceHostFactory : System.Data.Services.DataServiceHostFactory
{
    protected override System.ServiceModel.ServiceHost CreateServiceHost(Type serviceType, Uri[] baseAddresses)
    {
        var serviceHost = base.CreateServiceHost(serviceType, baseAddresses);

        EndpointDiscoveryBehavior endpointDiscoveryBehavior = new EndpointDiscoveryBehavior();

        // Create XML metadata to add to the service endpoint
        XElement endpointMetadata = new XElement(
            "Root",
            new XElement("Information", "This endpoint is Data Service v3!"),
            new XElement("Time", System.DateTime.Now.ToString("MM/dd/yyyy HH:mm")));

        // Add the XML metadata to the endpoint discovery behavior.
        endpointDiscoveryBehavior.Extensions.Add(endpointMetadata);

        //may be this is not the safest way to set the behaviour
        foreach (var endpoint in serviceHost.Description.Endpoints)
        {
            endpoint.Behaviors.Add(endpointDiscoveryBehavior);
        }

        // Make the service discoverable over UDP multicast
        serviceHost.Description.Behaviors.Add(new ServiceDiscoveryBehavior());
        serviceHost.AddServiceEndpoint(new UdpDiscoveryEndpoint());

        return serviceHost;
    }
}

クライアント側では、次のコードを試しました。

DiscoveryClient discoveryClient = new DiscoveryClient(new UdpDiscoveryEndpoint());

// Find service endpoints    
// ServiceReference.DataModel is the generated class for the Data Service client proxy       
FindCriteria findCriteria = new FindCriteria(typeof(ServiceReference.DataModel));
findCriteria.Duration = TimeSpan.FromSeconds(30);

FindResponse findResponse = discoveryClient.Find(findCriteria);

// Check to see if endpoints were found & print the XML metadata in them.
if (findResponse.Endpoints.Count > 0)
{
    foreach (XElement xElement in findResponse.Endpoints[0].Extensions)
    {
        Console.WriteLine("Printing Metadata from ServiceEndpoint:");
        Console.WriteLine("Endpoint Information: " + xElement.Element("Information").Value);
        Console.WriteLine("Endpoint Started at Time: " + xElement.Element("Time").Value);
        Console.WriteLine();
    }
}

残念ながら、これは機能しません。InvalidOperationExceptionを取得します:

DataModel のコントラクト タイプを取得しようとしましたが、そのタイプは ServiceContract ではなく、ServiceContract を継承していません。

正しい方向に向かっているのであれば、発見のためのサービス コントラクトのタイプを表現する方法が必要です。残念ながら、通常の WCF Discovery のように機能するかどうかはわかりません...

あなたのアイデアを共有してください。または、より良い解決策を共有してください。

4

1 に答える 1

1

例外メッセージは十分に明確だと思います。サービス ディスカバリの場合、データ モデルのタイプを使用しようとしますが、WCF サービス実装のタイプを使用する必要があります。これは別のことです。

基本的に、DataServicesV3 サービス アダプターはデータ モデルを使用し、独自のサービス コントラクトを使用して WCF サービスとして公開します。DataServiceV3 型宣言を見てください。いくつかのインターフェイスを実装していることがわかります。名前を覚えていません。このインターフェイス宣言には、[ServiceContract] および [ServiceOperation] 属性があります。これは、DataServiceV3 のすべての先祖に対するサービス契約です。彼らは同じ契約を使用します。ここで、まだ解決できていない別の問題があります。同じコントラクトを共有している場合に、WS-Discovery を DataServices と連携させるにはどうすればよいかということです。このように掘ったほうがいいです。

于 2013-06-13T14:13:44.963 に答える