4

I am trying to consume a Java web service but get an exception System.InvalidCastException: Cannot assign object of type ValueArrayType to an object of type ValueArrayType[]

I am consuming a third party service so cannot change the service and have been informed that they can consume the service ok with php and java.

Value Array type is complex type

 <xsd:complexType name="ValueArrayType">
    <xsd:sequence>
    <xsd:element name="ValueName" type="xsd:string"/>
    <xsd:element name="ValueType" type="xsd:string"/>
    <xsd:element name="ValueValue" type="xsd:string"/>
    </xsd:sequence>
 </xsd:complexType>

It is an element in the response DetailsType that can have several occurrences as it has max = unbound and is wrapped by a sequence attribute.

<xsd:complexType name="DetailsType">
    <xsd:sequence>
         <xsd:element name="Id" type="xsd:int"/>
         <xsd:element name="MobileName" type="xsd:string"/>
         <xsd:element name="ValueArray" type="tns:ValueArrayType" minOccurs="0" maxOccurs="unbounded"/>
   </xsd:sequence>
 </xsd:complexType>

I have tried wsdll.exe and svrcutil.exe to try and generate client code. the ValueArrayType is defined in the generated code as an array.

public ValueArrayType[] ValueArray
{
    get
    {
        return this.valueArrayField;
    }
    set
    {
        this.valueArrayField = value;
    }
}

an example of the data coming back is.

....
<Details xsi:type="tns:DetailsType">
    <Id xsi:type="xsd:int">9999</Id>
    <ValueArray xsi:type="tns:ValueArrayType">
      <ValueName xsi:type="xsd:string">Count</ValueName>
      <ValueType xsi:type="xsd:string">numeric</ValueType>
      <ValueValue xsi:type="xsd:string">11</ValueValue>
    </ValueArray>
    <ValueArray xsi:type="tns:ValueArrayType">
      <ValueName xsi:type="xsd:string">Start</ValueName>
      <ValueType xsi:type="xsd:string">numeric</ValueType>
      <ValueValue xsi:type="xsd:string">31</ValueValue>
    </ValueArray>
    <ValueArray xsi:type="tns:ValueArrayType">
      <ValueName xsi:type="xsd:string">A1</ValueName>
      <ValueType xsi:type="xsd:string">numeric</ValueType>
      <ValueValue xsi:type="xsd:string">23</ValueValue>
    </ValueArray>
    <ValueArray xsi:type="tns:ValueArrayType">
      <ValueName xsi:type="xsd:string">A2</ValueName>
      <ValueType xsi:type="xsd:string">numeric</ValueType>
      <ValueValue xsi:type="xsd:string">0</ValueValue>
    </ValueArray>
    <ValueArray xsi:type="tns:ValueArrayType">
      <ValueName xsi:type="xsd:string">X1</ValueName>
      <ValueType xsi:type="xsd:string">numeric</ValueType>
      <ValueValue xsi:type="xsd:string">0</ValueValue>
    </ValueArray>
    .....

If I change the client code to public ValueArrayType ValueArray instead of an array then the client works but only gets the first ValueArray returned.

Have tried suggestions from http://blogs.msdn.com/b/netcfteam/archive/2007/02/01/why-your-netcf-apps-fail-to-call-some-web-services.aspx.

Update
I have generated a WCF Service with the proxyclass generated from scvutil. When I consume and check the xml with WCFTestCLient.exe.

An Array type is sent back as

<ValueArray>
      <ValueArrayType>
        <ValueName>a</ValueName>
        <ValueType>string</ValueType>
        <ValueValue>1</ValueValue>
      </ValueArrayType>
      <ValueArrayType>
        <ValueName>a</ValueName>
        <ValueType>string</ValueType>
        <ValueValue>2</ValueValue>
      </ValueArrayType>
 </ValueArray> 

I assume either the data being sent does not match the WSDL or there is a bug in the C# scvutil, or System.ServiceModel.

rqmedes
  • 540
  • 2
  • 14
  • Would a manual solution be enough? It should not be too hard to write a XSL transform for the data coming from the server and then serialise the resulting XML into the wanted object... I know it is a lot of boring boiler plate code to write but once done it may prove a more robust solution than to rely on a tool... – Tallmaris Mar 23 '12 at 02:07
  • yeah, that is a solution, but I as we consume many java webservices not something i want to do every time. It seems there is communication layer issue with the way Java does things and the way C# does things – rqmedes Apr 26 '12 at 23:08

3 Answers3

0

The problem is caused by incorrect xsi:type values that mislead WCF deserialization (described here).

The workaround is to use OperationFormatUse.Literal instead of OperationFormatUse.Encoded on all operations.

Community
  • 1
  • 1
Pent Ploompuu
  • 5,364
  • 1
  • 27
  • 47
0

Try to specify your element type inside the generated code

[XmlElement(ElementName = "ValueArray", Type = typeof(ValueArrayType), Namespace = "YourSchemaNamespace")]
        public ValueArrayType[] ValueArray
        {
            get
            {
                return this.valueArrayField;
            }
            set
            {
                this.valueArrayField = value;
            }
        }

More information is available at MSDN

Toan Nguyen
  • 11,263
  • 5
  • 43
  • 59
-2

Can you try something like this ?

JavaServecie js= new JavaService();

js.ValueArrayType arr= js.GetValues(.....

if the class is public.

  • Sorry not following, are you suggesting this at the get/set property for the generated ServiceContract code? I am assuming it is failing when trying to deserialize the xml to the defined types, so an apporpriate ServiceContract attribute on this type and/or getter/setetter code might be the solution. – rqmedes Mar 14 '12 at 05:05
  • If I add a .net webservice and the service has a public reference to a customclass like (employer,product etc) then you can use that class in the client as service.Employer emp = new service.employer(); – Tanveer-Ibn- Haresh Mar 14 '12 at 05:35
  • Sorry I still don't follow as I need to send a request to the WebMethod of the webservice and then consumer the response? How does creating a class of this type help? – rqmedes Mar 14 '12 at 05:43
  • I might have understood you wrong, but I thought the return from your webmethod call would be of the class, that I just talked about. – Tanveer-Ibn- Haresh Mar 14 '12 at 05:50
  • Sorry I cannot understand what you are suggesting – rqmedes Mar 14 '12 at 11:50
  • 2
    @rqmedes Don't worry. Nobody understands. – L.B Mar 16 '12 at 23:56