1

これは、サーバー側の私の ABC です。

<endpoint address="msmq.formatname:DIRECT=OS:.\private$\imhmsgs" 
          binding="msmqIntegrationBinding" 
          bindingConfiguration="IncomingMessageHandlerBinding" 
         contract="TMC.Services.Contracts.Messages.IInboundMessageHandlerService">

.Open()サービスをホストするために を実行するとすぐに、例外が発生します。

インターフェイス XYZ.Services.Contracts.Messages.Interfaces.IMyMessage をシリアル化できません。

私の IMyMessage インターフェイス:

[ServiceContract]
[ServiceKnownType(typeof(IMyMessage))]
[ServiceKnownType(typeof(ConcreteMessage))]
public interface IInboundMessageHandlerService
{
    [OperationContract(IsOneWay = true, Action = "*")]
    void ProcessIncomingMessage(MsmqMessage<IMyMessage> incomingMessage); 
}

そのインターフェースの実装者:

[ServiceBehavior(ConcurrencyMode = ConcurrencyMode.Multiple, 
                 ReleaseServiceInstanceOnTransactionComplete = false)]
public class InboundMessageHandlerService : IInboundMessageHandlerService
{
    [OperationBehavior(TransactionScopeRequired = true, TransactionAutoComplete = true)]
    public void ProcessIncomingMessage(MsmqMessage<IMyMessage> incomingMessage)
    {
    }
 }

クライアントによって作成される型は基本的に具象クラスであり、基本クラスとインターフェイス (IMyMessage) から派生し、これを MSMQ に配置します。

いくつかのテストの後、サービスの既知のタイプ属性を削除し、代わりに「文字列」と言うと、ホストを開くように見えますが、エラーが発生します (メッセージ タイプが期待どおりではないため)。

どこが間違っているのですか?

さらにテストすると、具象型のみを指定すると機能することがわかります。

これは私が期待していたものではありません。サービスが既知のインターフェイスとそのインターフェイスを持つクラスを取得できるようにするにはどうすればよいですか? アイデアは、クライアント (同じコントラクトとクラスを使用) がメッセージを "IMyMessage" として送信し、WCF サービスがそれを "IMyMessage" として取得し、先に進んでメッセージ/オブジェクトのタイプを見つけることです。

どのように?

4

1 に答える 1

3

コントラクトはインターフェースですが、コントラクト内の定義は具象クラスでなければなりません。

あなたの場合、物事のリストを送信したいように見えます。それらは異なる可能性がありますが、それらはすべて同じインターフェースをサポートしています。

問題は、WCFがネットワーク経由で送信されたものを逆シリアル化する場合、具体的なタイプで逆シリアル化する必要があることです。定義にインターフェースがあり、その定義を実装する20の異なるタイプがある場合、それをどう処理するかはわかりません。

できることは、インターフェースを実装する基本型を用意することです。すべてのクラスは基本型を継承し、連絡先で基本型を使用します。

于 2012-05-08T21:00:54.700 に答える