Service Stack Serialization Exception for soap 1.1

2019-05-30 19:04发布

问题:

The Request Message:

<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Body>
  <SendGetAccountNotification xmlns:i="http://www.w3.org/2001/XMLSchema-instance" xmlns="mynamespace">
     <getAccountResponse xmlns:d2p1="mynamespace">
        <d2p1:Account>
           <d2p1:BusOpsDesc>String</d2p1:BusOpsDesc>
           <d2p1:ExternalAccountID>String</d2p1:ExternalAccountID>
        </d2p1:Account>
        <d2p1:ExternalAccountID>String</d2p1:ExternalAccountID>
        <d2p1:Message>String</d2p1:Message>
     </getAccountResponse>
  </SendGetAccountNotification>
</soap:Body>
</soap:Envelope>

Response message / error:

<SendGetAccountNotificationResponse xmlns:i="http://www.w3.org/2001/XMLSchema-instance" xmlns="mynamespace">
   <ResponseStatus>
      <ErrorCode>SerializationException</ErrorCode>
      <Message>Could not deserialize 'application/xml' request using EServices_Response.SendGetAccountNotification'
Error: System.Runtime.Serialization.SerializationException: Error in line 1 position 170. Expecting element 'SendGetAccountNotification' from namespace 'mynamespace'.. Encountered 'Element'  with name 'Envelope', namespace 'http://schemas.xmlsoap.org/soap/envelope/'. 
   at System.Runtime.Serialization.DataContractSerializer.InternalReadObject(XmlReaderDelegator xmlReader, Boolean verifyObjectName, DataContractResolver dataContractResolver)
   at System.Runtime.Serialization.XmlObjectSerializer.ReadObjectHandleExceptions(XmlReaderDelegator reader, Boolean verifyObjectName, DataContractResolver dataContractResolver)
   at ServiceStack.WebHost.Endpoints.Support.EndpointHandlerBase.DeserializeContentType(Type operationType, IHttpRequest httpReq, String contentType)</Message>
      <StackTrace>at ServiceStack.WebHost.Endpoints.Support.EndpointHandlerBase.DeserializeContentType(Type operationType, IHttpRequest httpReq, String contentType)
   at ServiceStack.WebHost.Endpoints.GenericHandler.ProcessRequest(IHttpRequest httpReq, IHttpResponse httpRes, String operationName)</StackTrace>
   </ResponseStatus>
</SendGetAccountNotificationResponse>

The C# Service:

[DataContract(Namespace = "mynamespace")]
public class SendGetAccountResponseService : IService<SendGetAccountNotification>
{
    public object Execute (SendGetAccountNotification request)
    {
        Console.WriteLine ("Reached");
        return null;
    }
}

Question:

Okay so I have been digging around for hours now and I cant find a solution. I inserted that request XML into Soap UI and i got that error response. It looks like it does not like the soap envelope and is trying to serialize the request starting not taking in regard to ignore the Envelope and Serialize the soap body to a model. I have no idea why this is happening, does anyone else know? Do i need to add some attributes in somewhere perhaps? Any help will be appreciated.

Solution:

Look for the green Tick. Solved this by checking my endpoint, it was pointing to the XML endpoint and therefore i was getting that error message. I have improved the service by following the post that solved my problem. Also noticed that I had an older version of service stack so that is now updated and all works like a charm.

回答1:

Below is my (simplified) attempt at your Service. It ignores 'namespace' but there is more information here. I am able to receive a successful response using Soap UI.

SoapUI setup:

Endpoint - http://localhost:1337/soap11

Request Message: (copied from ServiceStack Metadata page)

<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
    <soap:Body>
<SendGetAccountNotification xmlns:i="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://schemas.datacontract.org/2004/07/ServiceStackWinForm">
  <Account>
    <BusOpsDesc>String</BusOpsDesc>
    <ExternalAccountId>12345</ExternalAccountId>
  </Account>
  <ExternalAccountID>String</ExternalAccountID>
  <Message>String</Message>
</SendGetAccountNotification>
    </soap:Body>
</soap:Envelope>

ServiceStack Code:

Account class (part of request):

[DataContract]
public class Account
{
    [DataMember]
    public string BusOpsDesc { get; set; }
    [DataMember]
    public string ExternalAccountId { get; set; }
}

Request class

[DataContract]
[Route("/SendGetAccountNotification")]
public class SendGetAccountNotification
{
    [DataMember]
    public Account Account { get; set; }
    [DataMember]
    public string ExternalAccountID { get; set; }
    [DataMember]
    public string Message { get; set; }
}

Response class with matching naming convention

[DataContract]
public class SendGetAccountNotificationResponse : IHasResponseStatus
{
    [DataMember]
    public String Result { get; set; }
    [DataMember]
    public ResponseStatus ResponseStatus { get; set; }
}

Service

public class SendGetAccountResponseService : Service
{
    public SendGetAccountNotificationResponse Any(SendGetAccountNotification request)
    {
        Console.WriteLine("Reached");
        return new SendGetAccountNotificationResponse() {Result = "Success for Account " + request.Account.ExternalAccountId};
    }
}


回答2:

I had the same kind of issue, I had to modify the request. I can't understant why, but I had to remove the prefix. Try this:

<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Body>
  <SendGetAccountNotification xmlns="http://www.w3.org/2001/XMLSchema-instance" xmlns="mynamespace">
     <getAccountResponse>
        <Account>
           <BusOpsDesc>String</BusOpsDesc>
           <ExternalAccountID>String</ExternalAccountID>
        </Account>
        <ExternalAccountID>String</ExternalAccountID>
        <Message>String</Message>
     </getAccountResponse>
  </SendGetAccountNotification>
</soap:Body>
</soap:Envelope>