38

私はちょうど WCF の使用方法を学んでおり、(ホスト側とクライアント側の両方で) 小さな HelloWorld プログラムをゼロから作成しようとしています。クライアントがサービスを利用しようとするProtocolException Unhandledたびにエラーが発生しますが、その理由がわかりません。IIS を使用してサービスをホストしています。

設定方法について: クライアント、プロキシ、ホスト、サービス、およびコントラクトを分離するために最善を尽くしています (このビデオとこの記事で説明されているとおり) 。基本的に、私はそれらのそれぞれのソリューション内に異なるプロジェクトを持っています。

ここに私が話していることを示すいくつかの異なるファイルがあります:

サービス

namespace HelloWorld
{
  public class HelloWorldService : IHelloWorldService
  {
    public String GetMessage(String name)
    {
        return "Hello World from " + name + "!";
    }
  }
}

契約

namespace HelloWorld
{
  [ServiceContract]
  public interface IHelloWorldService
  {
      [OperationContract]
      String GetMessage(String name);
  }
}

プロキシー

namespace HelloWorld
{
  public class Proxy : ClientBase<IHelloWorldService>, IHelloWorldService
  {
    #region IHelloWorldService Members

    public String GetMessage(String name)
    {
        return Channel.GetMessage(name);
    }

    #endregion

  }

}

クライアント

namespace Client
{
  public partial class Form1 : Form
  {
    public Form1()
    {
        InitializeComponent();
    }

    private void button1_Click_1(object sender, EventArgs e)
    {
        Proxy proxy = new Proxy();
        MessageBox.Show(proxy.GetMessage(textBox1.Text));
    }
  }

}

クライアントは、テキスト ボックスとボタンを備えた単なるフォームであり、テキスト ボックスの内容をパラメーターとして使用して GetMessage() を実行しようとします。フォームのインスタンスを実際に作成する別のクラスがあります。

Web サイトの web.config は次のとおりです。

Web.config

<?xml version="1.0"?>
<configuration>
  <system.web>
    <compilation debug="true" targetFramework="4.0" />
  </system.web>
  <system.webServer>
    <modules runAllManagedModulesForAllRequests="true"/>
  </system.webServer>
  <system.serviceModel>
    <behaviors>
      <serviceBehaviors>
        <behavior name="MyServiceTypeBehaviors">
          <serviceMetadata httpGetEnabled="true" />
          <serviceDebug includeExceptionDetailInFaults="false" />
        </behavior> 
      </serviceBehaviors>
    </behaviors>
    <services>
      <service name="HelloWorld.HelloWorldService" behaviorConfiguration="MyServiceTypeBehaviors">
        <endpoint address="http://localhost:8002/" binding="basicHttpBinding" contract="HelloWorld.IHelloWorldService"/>
        <endpoint contract="IMetadataExchange" binding="mexHttpBinding" address="mex"/>
      </service>
    </services>
  </system.serviceModel>
</configuration>

そして、これがクライアントと一緒に行く私の app.config です:

app.config

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  <system.serviceModel>
    <client>
      <endpoint address="http://localhost:8002/" binding="basicHttpBinding" contract="HelloWorld.IHelloWorldService" />
    </client>
  </system.serviceModel>

</configuration>

私のsvcファイルは非常に短く、次のとおりです。

HelloWorldService.svc

<%@ServiceHost Service="HelloWorld.HelloWorldService"%>

http://localhost:8002/HelloWorldService.svcブラウザでに移動すると、次のような画面が表示されるため、サービスが実行されていることがわかります

サービスを作成しました。

このサービスをテストするには、クライアントを作成し、それを使用してサービスを呼び出す必要があります。

ここで障害が発生します。サービスは IIS を使用して実行されています。クライアントのインスタンスを起動すると、テキスト ボックスとボタンが表示されたウィンドウが表示されます。文字を入力してボタンを押すと、プログラムがクラッシュし、ProtocolException Unhandled, (405) Method not allowed. Proxy クラスの次の行でエラーが発生します。

return Channel.GetMessage(name);

私はこれを何時間も理解しようとしてきましたが、あまり進歩していません。誰かが少なくとも私を正しい方向に向けることができれば、私は非常に感謝しています.

最後に、svcutil.exe を使用せずに、クライアントとプロキシをゼロから作成したいと考えています。

4

4 に答える 4

2

わかりました、解決策を見つけましたが、なぜそれが機能するのか完全にはわかりません. Web サイトをホストするために Cassini や IIS などを使用している場合、web.config ファイルのエンドポイントでアドレスを指定することは想定されていません。私がしなければならなかったのは、それをに変更するだけでaddress=""、適切に機能し始めました。サーバーがサービスをホストしているポートが app.config ファイルのコードと一致していることを確認してください。

于 2013-08-02T14:02:42.777 に答える