8

VisualStudio2010とMSSQLServer 2005を使用しています。WCFを初めて使用し、小さなタスク管理アプリケーションを開発しながら学習しようとしています。

現在、2つのコンソールアプリケーション(WCFサービス)を含むソリューションがあります。クライアントは、コードをテストするためにWCFサービスに接続しています。

WCFサービスは、LINQtoSQLを使用してデータベースに接続します。WCFサービスの背後にあるデータベースに何かを挿入するOperationContractを実装しましたが、これは機能します。WCFサービスからクライアントにGUIDを返すOperationContractを実装しましたが、これも機能します。

WCFサービスからリストのリストを取得しようとすると、次のエラーで失敗します。

  • 「localhost:8000 / TaskerTest / Service / OperationsへのHTTP応答の受信中にエラーが発生しました。これは、サービスエンドポイントのバインディングがHTTPプロトコルを使用していないことが原因である可能性があります。これは、HTTPリクエストコンテキストがサーバーによって中止されていることが原因である可能性もあります。

  • InnerException:基になる接続が閉じられました:受信時に予期しないエラーが発生しました。

私の契約(最初の2つの作業。GetListsが問題です):

[ServiceContract(Namespace = "http://Tasker_Server")]
public interface IOperations {
    [OperationContract]
    string CreateList(string listName, string text);
    [OperationContract]
    string UpdateList(int idList, string listName, string text);
    [OperationContract]
    List<ToDoList> GetLists();
}

実装:

    public List<ToDoList> GetLists() {
        Guid token = OperationContext.Current.IncomingMessageHeaders.GetHeader<Guid>("token", "ns");
        int? userID = CheckCache(token);

        if (userID != null) {
            List<ToDoList> lst = DBAccess.GetListsByUserId(userID.Value);
            return lst;
        }
        else
            return null;
    }

DBアクセスコード:

     public static List<ToDoList> GetListsByUserId(int idCredential) {
        TaskerModelDataContext tmdc = new TaskerModelDataContext();
        List<ToDoList> lists = tmdc.ToDoLists.Where(entry => entry.id_Credential == idCredential).ToList<ToDoList>();
        return lists;

    }

そして、クライアントコード(WCFサービスはクライアントプロジェクトへのサービス参照として追加されます):

        TaskerService.LoginClient test2 = new LoginClient();
        string username = "usr1", password = "psw1";
        test2.ClientCredentials.UserName.UserName = username;
        test2.ClientCredentials.UserName.Password = password;

        Guid result = Guid.Empty;
        try {
            result = test2.CheckCredentials(username, password);
            Console.WriteLine("Login OK!");
        }
        catch (Exception e) {
            Console.WriteLine(e.Message);
        }

        TaskerService.OperationsClient client = new OperationsClient();
        using(OperationContextScope contextScope = new OperationContextScope(client.InnerChannel)) {

            Guid testToken = result; Console.WriteLine(testToken.ToString());
            MessageHeader<Guid> mhg = new MessageHeader<Guid>(testToken);
            MessageHeader untyped = mhg.GetUntypedHeader("token", "ns");
            OperationContext.Current.OutgoingMessageHeaders.Add(untyped);

            client.GetLists();
        }
        client.Close();

クライアントは、上記の例外で失敗します:client.GetLists();

読者の必要に応じて、追加の詳細を提供できます。

アップデート

でトレースをオンにしました

  <system.diagnostics>
    <trace autoflush="true" />
    <sources>
      <source name="System.ServiceModel"
              switchValue="Information, ActivityTracing"
              propagateActivity="true">
        <listeners>
          <add name="sdt"
              type="System.Diagnostics.XmlWriterTraceListener"
              initializeData= "SdrConfigExample.e2e" />
        </listeners>
      </source>
    </sources>
  </system.diagnostics>

次に、生成されたログでMicrosoft Service Trace Viewerを実行したところ、次のエラーが発生しました。

パラメータをシリアル化しようとしたときにエラーが発生しました。InnerExceptionメッセージは「タイプ」「System.DelegateSerializationHolder+DelegateEntry」でデータコントラクト名は「DelegateSerializationHolder.DelegateEntry:http://schemas.datacontract.org/2004/07/System」でした。

dbmlファイルの「ToDoList」クラスに[DataContract]を追加しましたが、例外は発生しません。クライアントで正しい数の結果が得られますが、各クラスの内容は空のようです。

4

3 に答える 3

2

データベース クラスは、dbml ファイル (LINQ to SQL) を使用して自動生成されました。

「TaskerModel.designer.cs」(自動生成ファイル) の ToDoList クラスに [DataContract()] 属性を追加した後、例外は発生しなくなりましたが、クライアントで取得したクラスにはデフォルト値しかありませんでした。メンバーごとに。

次に、[DataMember()] 属性を ToDoList クラスのすべてのメンバーに追加し、追加しました

[ServiceKnownType(typeof(ToDoList))]

    [ServiceContract(Namespace = "http://Tasker_Server")]
    public interface IOperations {
        [OperationContract]
        string CreateList(string listName, string text);
        [OperationContract]
        string UpdateList(int idList, string listName, string text);
        [OperationContract]
        List<ToDoList> GetLists();
}

そして今、それは機能します。もっと簡単な方法があるかどうかはわかりませんが、現在は機能しています。誰かがこれを行うためのより良い方法を知っていれば、コメントをいただければ幸いです。

于 2012-05-27T13:25:42.390 に答える
0

WCF restfull サービスを呼び出すときに同じエラーが発生しました。問題は、私が応答として返したデータ型が原因のようです。

JSON を返しましたが、応答オブジェクトにはデータ型が DateTime の変数が含まれていました。DateTime を文字列に置き換えたところ、問題は解決し、適切な応答が返されました。おそらく、同じ問題に遭遇した人を助けるでしょう。

交換:

[DataMember]
public DateTime dateFrom {get;set;}

これとともに

[DataMember]
public string dateFrom {get;set;}
于 2014-03-17T12:56:32.327 に答える