2013-08-16 89 views
7

私はWCFサービスを持っています。それはUserServiceと呼ばせてください。 UserServiceには、クラスライブラリへの参照があります。それをDoWork.dllとしましょう。 DoWork.dllには、CompanyServiceという別のサービスへのWCFサービスリファレンスがあります。WCFエンドポイント設定エラー: 'contract'属性が無効ですか?

私が最初にUserServiceを呼び出すと、エンドポイントが設定されていないというエラーメッセージが表示されます。ウェブの周りを読んだ後で、CompanyServiceバインディングとクライアント情報を、<system.serviceModel>ノードのUserServiceweb.configに追加する必要があることが判明しました。

ここでは、次のとおりです。

<system.serviceModel> 
    <bindings> 
     <basicHttpBinding> 
     <binding name="BasicHttpBinding_IComapnyService" /> 
     </basicHttpBinding> 
    </bindings> 
    <client> 
     <endpoint name="BasicHttpBinding_ICompanyService" 
      address="http://it-dev.company.local:81/Project/Copmpany/CompanyService.svc" 
      binding="basicHttpBinding" 
      bindingConfiguration="BasicHttpBinding_IComapnyService" 
      contract="CompanyService.ICompanyService" /> 
    </client> 

私が持っている問題はcontract="CompanyService.ICompanyService"は私にエラーを示しています

The 'contract' attribute is invalid - The value 'CompanyService.ICompanyService' is invalid according to its datatype 'clientContractType' - The Enumeration constraint failed.

、私は直接UserService WCFプロジェクトにCompanyServiceの参照を追加した場合、エラーは消える(明らかに)。しかし、私はこれを行う必要はありません。私はICompanyService契約があるネームスペースを完全に修飾しようとしましたが、どちらもうまくいきません。 .suoファイルを削除してプロジェクトを再構築したが、どちらもうまくいきませんでした(Web上の他の場所で提案されています)。また、contract=と入力すると、ドロップダウンリストが表示されますが、CompanyService.ICompanyServiceは見つかりません(私がUserServiceプロジェクトで直接サービスを参照している場合のみ)。

Tools > WCF Service Configuration Editorを使用して設定しようとしましたが、それは役に立ちません。

私はすべてがうまくいくように注意する必要がありますが、intellisenseが私に青い波状の下線とそのエラーメッセージを与えているということは気に入らないのです。私は、がDoWork.dllを参照しているため、CompanyServiceが契約を正しく見ることができないため、web.configに何か別のものが必要であると感じています。

ご意見をいただければ幸いです。前もって感謝します。

+0

私は最近これを見つけ、実際には完全な名前空間を含めて自分の問題に貢献していることを発見しました。この問題を抱えている人には注意してください。 – Ian

答えて

2

あなたはそうです - これを行う必要はありません。

"サービス参照"(ComanyService)でDLL(DoWork.dll)を持つアーキテクチャが悪いです。 DLLがあなたのためにCompanyServiceを呼び出すようにクライアントエンドポイント(コード内)をハードコードしていない限り、DLLを使用する人は誰も知らないサービスのためにクライアントエンドポイントを設定する方法を試してみる必要があります。あなたが走っているのは何ですか。

UserServiceから直接サービス参照を追加すると、これを行う理由は、これを行うと、CompanyServiceメタデータからServiceContractのコピーが取得されることです。これを証明するには、生成されたReference.csファイルを参照して、CompanyServiceを検索し、それにWCFサービスとして識別する[ServiceContract]属性があることがわかります。さらに、メソッドの[OperationContract]属性と、サービスが交換する[DataContracts]属性が表示されます。言い換えれば、これらの「タイプ」はすべてプロジェクトにインポートされ、コンパイル時にWCFはクライアントエンドポイントをインスタンス化する際にこれらのタイプを見つけることができるようになりました。

CompanyServiceがあなたのサービスの1つである場合は、ServiceContract定義(インタフェース)を個別のDLLに抽出することを検討してください。次に、これらのタイプをサービス(CompanyService)およびUserServiceなどのクライアントアプリケーションから「アセンブリ参照」として参照できます。少なくとも、サービス参照を追加する必要はありません。しかし、あなたはまだ技術的に詳細を知らないかもしれないサービスのためにあなたのアプリケーションの....セクションに値を設定しなければなりません。最高のアプローチではありません。

サービスの依存関係をDoWork.dllから外す方が良い方法です。これを行うには、ロジックをUserService実装に移すだけです。

DoWork.dllを独立して保持する必要がある場合は、CompanyServiceに依存するWCFサービスでDoWorkをラップすることを検討してください。次に、UserServiceから、新しいDoWorkサービスへのサービス参照を追加します。これは、SOAのテナントにとってさらに重要であり、サービスを独自に進化させることになります。

+0

情報ありがとうございます。多分私の建築は悪いです。 CompanyServiceはWCFサービスだけです。なぜなら、これは、InstanceContextMode.Singleのサービス動作を持つシングルトンのように動作する必要があるからです。今私のシステムでは、CompanyServiceの1つのサービスメソッドは、DoWork.DLL以外のどこからでも呼び出されるべきではありません。だから私の後続の質問は、私はDoWork.DLLのエンドポイントをハードコードする必要がありますか?私はすべて一緒にComapnyServiceを離れて何とかDoWork.dllに何らかの形でシングルトンの動作を維持していますか?ありがとう。 – BBauer42

+1

いいえ、エンドポイントをハードコードしないでください。 私が最後に提示したオプションは、おそらくあなたのシナリオに最も適した方法です。 DoWork.DLLをラップするサービスがCompanyServiceを呼び出すことができる唯一のサービスであることを保証する方法(セキュリティ設定を介して)があります。だから、このようなもの。 UserService <--> NewWrapperService(dowork)<--> CompanyService –

関連する問題