title: Deserialize the soap xml response in a .netcore app
body: <p>I have to call a soap service from a C# .net core app and get the results in a class that I can use to do some logic. I did the soap request and the remote call works fine, but now I have to deserialize the xml soap response into a class. Here's an example of the response:</p>
  
  <pre><code>&lt;SOAP-ENV:Envelope SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/" xmlns:tns="http://some_domain/soap/ApplicationServices"&gt;
    &lt;SOAP-ENV:Body&gt;
      &lt;ns1:preparelabelsResponse xmlns:ns1="http://some_domain/soap/ApplicationServices"&gt;
        &lt;return xsi:type="SOAP-ENC:Array" SOAP-ENC:arrayType="tns:PrepareReturn[1]"&gt;
          &lt;item xsi:type="tns:PrepareReturn"&gt;
            &lt;clientref xsi:type="xsd:string"&gt;2015/0418/001&lt;/clientref&gt;
            &lt;pclid xsi:type="xsd:string"&gt;&lt;/pclid&gt;
            &lt;error xsi:type="xsd:string"&gt;Invalid timestamp 20191018105727&lt;/error&gt;
          &lt;/item&gt;
        &lt;/return&gt;
      &lt;/ns1:preparelabelsResponse&gt;
    &lt;/SOAP-ENV:Body&gt;
  &lt;/SOAP-ENV:Envelope&gt;
  </code></pre>
  
  <p>Since I'm using Visual Studio 2017 I tried adding a connected service in my .netcore app using the WCF Web Service Reference Provider and then call the method. The call failed with the message: Wrong XML format, that was probably generated by the server. Doing the same steps in a .net framework app worked fine though, and I got the proper response. So I suspect something is different in the .netcore wcf provider.
  My second approach was to create the soap request manually and then parse the soap response. For constructing the request I have an elegant solution, but for parsing the response I don't. I tried to use  the classes that were generated by the wcf provider, but the xml deserialization didn't work. I then tried to change the attributes to get it right, but didn't help. I added below those classes:</p>
  
  <pre><code>[System.Diagnostics.DebuggerStepThroughAttribute()]
  [System.CodeDom.Compiler.GeneratedCodeAttribute("dotnet-svcutil", "1.0.0.1")]
  [System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Advanced)]
  [System.ServiceModel.MessageContractAttribute(WrapperName="preparelabelsResponse", WrapperNamespace="encoded", IsWrapped=true)]
  public partial class preparelabelsResponse
  {    
      [System.ServiceModel.MessageBodyMemberAttribute(Namespace="", Order=0)]
      public PrepareReturn[] @return;
  
      public preparelabelsResponse()
      {
      }
  
      public preparelabelsResponse(PrepareReturn[] @return)
      {
          this.@return = @return;
      }
  }
  
  /// &lt;remarks/&gt;
  [System.CodeDom.Compiler.GeneratedCodeAttribute("dotnet-svcutil", "1.0.0.1")]
  [System.Diagnostics.DebuggerStepThroughAttribute()]
  [System.Xml.Serialization.SoapTypeAttribute(Namespace="http://some_domain/soap/ApplicationServices")]
  public partial class PrepareReturn
  {     
      private string clientrefField;
  
      private string pclidField;
  
      private string errorField;
  
      /// &lt;remarks/&gt;
      public string clientref
      {
          get
          {
              return this.clientrefField;
          }
          set
          {
              this.clientrefField = value;
          }
      }
  
      /// &lt;remarks/&gt;
      public string pclid
      {
          get
          {
              return this.pclidField;
          }
          set
          {
              this.pclidField = value;
          }
      }
  
      /// &lt;remarks/&gt;
      public string error
      {
          get
          {
              return this.errorField;
          }
          set
          {
              this.errorField = value;
          }
      }
  }
  </code></pre>
  
  <p>And the xml deserialization:</p>
  
  <pre><code>var soapResponse = XDocument.Load(sr);
  XNamespace myns = "http://some_domain/soap/ApplicationServices";
  var xml = soapResponse.Descendants(myns + "preparelabelsResponse").FirstOrDefault().ToString();
  var result = Deserialize&lt;preparelabelsResponse&gt;(xml);
  
  ...
  
  public static T Deserialize&lt;T&gt;(string xmlStr)
  {
      var serializer = new XmlSerializer(typeof(T));
      T result;
      using (TextReader reader = new StringReader(xmlStr))
      {
          result = (T)serializer.Deserialize(reader);
      }
      return result;
  }
  </code></pre>
  
  <p>So what I could do is to strip the xml away of all the namespaces and attributes and deserialize it to a simple class, but that is not an elegant solution for my problem. What I want is to be able to create/decorate my classes in such a way that the deserialization will work without any altering of the actual xml contents.</p>