title: Android Ksoap2 - complex type(request and response)
body: <p>I am using ksoap2 to call the java webservice in Android. 
  Java Web service method is,</p>
  
  <p>ImageProcessImpl.java</p>
  
  <pre><code>public UserResponse sample(UserRequest userRequest) {
       return ImageProcessDAO.sample(userRequest);
  }
  </code></pre>
  
  <p>ImageProcessDAO.java</p>
  
  <pre><code>public static String sample(UserRequest userRequest) {
       System.out.println(userRequest.getClientName());
       UserResponse UserResponse = new UserResponse();
       userResponse.setMessage("SUCCESS");
       return userResponse;
  }
  </code></pre>
  
  <p>I am calling these webservices from Android as,</p>
  
  <pre><code>try{
          String NAMESPACE = "http://impl.test.com";
          String URL = "http://10.0.2.2:8080/Webservice/services/ImageProcessImpl?wsdl";  
          String SOAP_ACTION = "http://impl.test.com/sample";
          String METHOD_NAME = "sample";
  
          SoapObject request = new SoapObject(NAMESPACE, METHOD_NAME); 
  
          UserRequest userRequest = new UserRequest();            
          userRequest.setClientName("Test");
  
          PropertyInfo pi = new PropertyInfo();
          pi.setName("userRequest");
          pi.setValue(userRequest);
          pi.setType(UserRequest.class);
          request.addProperty(pi);
  
          SoapSerializationEnvelope envelope = new SoapSerializationEnvelope(SoapEnvelope.VER11); 
          envelope.setOutputSoapObject(request);  
          envelope.implicitTypes = true;
          envelope.addMapping(NAMESPACE, "UserResponse", UserResponse.class);
  
          AndroidHttpTransport httpTransport = new AndroidHttpTransport(URL);  
          httpTransport.debug = true;
          httpTransport.call(SOAP_ACTION, envelope);
  
         UserResponse response = (UserResponse) envelope.getResponse(); 
         Log.e(Test.LOG_TAG, response.getMessage());
          }catch (Exception e) {
              Log.e(Test.LOG_TAG, "throws an exception: " + e.getMessage());
          }
  </code></pre>
  
  <p>But I am getting the error in my Logcat is "<strong>throws an exception: Cannot serialize: com.test.common.UserRequest</strong>". How to fix this error? Is this right way to call web service with complex type?</p>
  
  <p>my wsdl file is,</p>
  
  <pre><code>&lt;?xml version="1.0" encoding="UTF-8"?&gt;
  &lt;wsdl:definitions targetNamespace="http://impl.test.com" xmlns:apachesoap="http://xml.apache.org/xml-soap" xmlns:impl="http://impl.test.com" xmlns:intf="http://impl.test.com" xmlns:tns1="http://common.test.com" xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/" xmlns:wsdlsoap="http://schemas.xmlsoap.org/wsdl/soap/" xmlns:xsd="http://www.w3.org/2001/XMLSchema"&gt;
  &lt;!--WSDL created by Apache Axis version: 1.4
  Built on Apr 22, 2006 (06:55:48 PDT)--&gt;
   &lt;wsdl:types&gt;
    &lt;schema elementFormDefault="qualified" targetNamespace="http://impl.test.com" xmlns="http://www.w3.org/2001/XMLSchema"&gt;
     &lt;import namespace="http://common.test.com"/&gt;
     &lt;element name="sample"&gt;
      &lt;complexType&gt;
       &lt;sequence&gt;
        &lt;element name="userRequest" type="tns1:UserRequest"/&gt;
       &lt;/sequence&gt;
      &lt;/complexType&gt;
     &lt;/element&gt;
     &lt;element name="sampleResponse"&gt;
      &lt;complexType&gt;
       &lt;sequence&gt;
        &lt;element name="sampleReturn" type="tns1:UserResponse"/&gt;
       &lt;/sequence&gt;
      &lt;/complexType&gt;
     &lt;/element&gt;
    &lt;/schema&gt;
    &lt;schema elementFormDefault="qualified" targetNamespace="http://common.test.com" xmlns="http://www.w3.org/2001/XMLSchema"&gt;
     &lt;complexType name="UserRequest"&gt;
      &lt;sequence&gt;
       &lt;element name="clientName" nillable="true" type="xsd:string"/&gt;
      &lt;/sequence&gt;
     &lt;/complexType&gt;
     &lt;complexType name="UserResponse"&gt;
      &lt;sequence&gt;
       &lt;element name="message" nillable="true" type="xsd:string"/&gt;
      &lt;/sequence&gt;
     &lt;/complexType&gt;
    &lt;/schema&gt;
   &lt;/wsdl:types&gt;
  
     &lt;wsdl:message name="sampleRequest"&gt;
  
        &lt;wsdl:part element="impl:sample" name="parameters"&gt;
  
        &lt;/wsdl:part&gt;
  
     &lt;/wsdl:message&gt;
  
     &lt;wsdl:message name="sampleResponse"&gt;
  
        &lt;wsdl:part element="impl:sampleResponse" name="parameters"&gt;
  
        &lt;/wsdl:part&gt;
  
     &lt;/wsdl:message&gt;
  
     &lt;wsdl:portType name="ImageProcessImpl"&gt;
  
        &lt;wsdl:operation name="sample"&gt;
  
           &lt;wsdl:input message="impl:sampleRequest" name="sampleRequest"&gt;
  
         &lt;/wsdl:input&gt;
  
           &lt;wsdl:output message="impl:sampleResponse" name="sampleResponse"&gt;
  
         &lt;/wsdl:output&gt;
  
        &lt;/wsdl:operation&gt;
  
     &lt;/wsdl:portType&gt;
  
     &lt;wsdl:binding name="ImageProcessImplSoapBinding" type="impl:ImageProcessImpl"&gt;
  
        &lt;wsdlsoap:binding style="document" transport="http://schemas.xmlsoap.org/soap/http"/&gt;
        &lt;wsdl:operation name="sample"&gt;
  
           &lt;wsdlsoap:operation soapAction=""/&gt;
  
           &lt;wsdl:input name="sampleRequest"&gt;
  
              &lt;wsdlsoap:body use="literal"/&gt;
  
           &lt;/wsdl:input&gt;
  
           &lt;wsdl:output name="sampleResponse"&gt;
  
              &lt;wsdlsoap:body use="literal"/&gt;
  
           &lt;/wsdl:output&gt;
  
        &lt;/wsdl:operation&gt;
  
     &lt;/wsdl:binding&gt;
  
     &lt;wsdl:service name="ImageProcessImplService"&gt;
  
        &lt;wsdl:port binding="impl:ImageProcessImplSoapBinding" name="ImageProcessImpl"&gt;
  
           &lt;wsdlsoap:address location="http://localhost:8080/Webservice/services/ImageProcessImpl"/&gt;
  
        &lt;/wsdl:port&gt;
  
     &lt;/wsdl:service&gt;
  
  &lt;/wsdl:definitions&gt;
  </code></pre>
  
  <p>I used the KvmSerializable. I have added one more array bean variable
  <code>private Client[] clientNameList = null;</code> in UserRequest.java. </p>
  
  <p>When I call the web service it is working fine in the request. But in the response I am getting one string that contains all values. The response string is given below.</p>
  
  <p><code>anyType{clientNameList=anyType{clientNameList=anyType{clientID=1; }; clientNameList=anyType{clientID=2; }; }; message=SUCCESS; }.</code> </p>
  
  <p>How Can I parse this string?</p>
  
  <p>UserResponse.java</p>
  
  <pre><code>public class UserResponse implements KvmSerializable{
  
  public String message = null;
  public Client[] clientNameList = null;
  
  @Override
  public Object getProperty(int index) {
      switch (index){
      case 0:
          return message;
      case 1:
          return clientNameList;
       default:
           return null;
      }
  }
  
  @Override
  public int getPropertyCount() {
      // TODO Auto-generated method stub
      return 2;
  }
  
  @Override
  public void getPropertyInfo(int index, Hashtable arg1, PropertyInfo info) {
      switch(index)
      {
      case 0:
          info.type = PropertyInfo.STRING_CLASS;
          info.name = "message";
          break;
      case 1:
          info.type = PropertyInfo.OBJECT_TYPE;
          info.name = "clientNameList";
          break;
      default:
          break;
      }
  
  }
  
  @Override
  public void setProperty(int index, Object value) {
      switch(index)
      {
      case 0:
          message = value.toString();
          break;
      case 1:
          clientNameList = (Client[]) value;
          break;
      default:
          break;
      }
  
  }   
  }
  </code></pre>
  
  <p>Client.java contains only clientId of Integer type.</p>
  
  <p><strong>Updated code and wsdl</strong> </p>
  
  <p>ImageProcessImpl.java</p>
  
  <pre><code>public UserResponse sample(UserRequest userRequest) {
       return ImageProcessDAO.sample(userRequest);
  }
  </code></pre>
  
  <p>ImageProcessDAO.java</p>
  
  <pre><code>public static String sample(UserRequest userRequest) {
      System.out.println(userRequest.getClientName());
      UserResponse userResponse = new UserResponse();
      userResponse.setMessage(SUCCESS);
      Client[] clients = new Client[2];
      Client client = null;
      for(int i=0;i&lt;2;i++)
      {
          client = new Client();
          client.setClientID(i+1);
          clients[i] = client;
      }
      userResponse.setClientNameList(clients);
      return userResponse;
  }
  </code></pre>
  
  <p>I am calling these webservices from Android as,</p>
  
  <pre><code>try{
          String NAMESPACE = "http://impl.test.com";
          String URL = "http://10.0.2.2:8080/Webservice/services/ImageProcessImpl?wsdl";  
          String SOAP_ACTION = "http://impl.test.com/sample";
          String METHOD_NAME = "sample";
  
          SoapObject request = new SoapObject(NAMESPACE, METHOD_NAME); 
  
          UserRequest userRequest = new UserRequest();            
          userRequest.setClientName("Test");
  
          PropertyInfo pi = new PropertyInfo();
          pi.setName("userRequest");
          pi.setValue(userRequest);
          pi.setType(UserRequest.class);
          request.addProperty(pi);
  
          SoapSerializationEnvelope envelope = new SoapSerializationEnvelope(SoapEnvelope.VER11); 
          envelope.setOutputSoapObject(request);  
          envelope.implicitTypes = true;
          envelope.addMapping(NAMESPACE, "userRequest", UserRequest.class);
          envelope.addMapping(NAMESPACE, "UserResponse", UserResponse.class);
  
          AndroidHttpTransport httpTransport = new AndroidHttpTransport(URL);  
          httpTransport.debug = true;
          httpTransport.call(SOAP_ACTION, envelope);
  
         SoapObject result = (SoapObject) envelope.getResponse();
         userResponse.message = result.getProperty(0).toString();
         Log.e(Test.LOG_TAG, userResponse.message);
          }catch (Exception e) {
              Log.e(Test.LOG_TAG, "throws an exception: " + e.getMessage());
          }
  </code></pre>
  
  <p>my new wsdl file is,</p>
  
  <pre><code>&lt;?xml version="1.0" encoding="UTF-8"?&gt;
  &lt;wsdl:definitions targetNamespace="http://impl.test.com" xmlns:apachesoap="http://xml.apache.org/xml-soap" xmlns:impl="http://impl.test.com" xmlns:intf="http://impl.test.com" xmlns:tns1="http://common.test.com" xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/" xmlns:wsdlsoap="http://schemas.xmlsoap.org/wsdl/soap/" xmlns:xsd="http://www.w3.org/2001/XMLSchema"&gt;
  &lt;!--WSDL created by Apache Axis version: 1.4
  Built on Apr 22, 2006 (06:55:48 PDT)--&gt;
   &lt;wsdl:types&gt;
    &lt;schema elementFormDefault="qualified" targetNamespace="http://impl.test.com" xmlns="http://www.w3.org/2001/XMLSchema"&gt;
     &lt;import namespace="http://common.test.com"/&gt;
     &lt;element name="sample"&gt;
      &lt;complexType&gt;
       &lt;sequence&gt;
        &lt;element name="userRequest" type="tns1:UserRequest"/&gt;
       &lt;/sequence&gt;
      &lt;/complexType&gt;
     &lt;/element&gt;
     &lt;element name="sampleResponse"&gt;
      &lt;complexType&gt;
       &lt;sequence&gt;
        &lt;element name="sampleReturn" type="tns1:UserResponse"/&gt;
       &lt;/sequence&gt;
      &lt;/complexType&gt;
     &lt;/element&gt;
     &lt;complexType name="ArrayOf_tns1_Client"&gt;
      &lt;sequence&gt;
       &lt;element maxOccurs="unbounded" minOccurs="0" name="item" type="tns1:Client"/&gt;
      &lt;/sequence&gt;
     &lt;/complexType&gt;
    &lt;/schema&gt;
    &lt;schema elementFormDefault="qualified" targetNamespace="http://common.test.com" xmlns="http://www.w3.org/2001/XMLSchema"&gt;
     &lt;import namespace="http://impl.test.com"/&gt;
     &lt;complexType name="UserRequest"&gt;
      &lt;sequence&gt;
       &lt;element name="clientName" nillable="true" type="xsd:string"/&gt;
      &lt;/sequence&gt;
     &lt;/complexType&gt;
     &lt;complexType name="Client"&gt;
      &lt;sequence&gt;
       &lt;element name="clientID" type="xsd:int"/&gt;
      &lt;/sequence&gt;
     &lt;/complexType&gt;
     &lt;complexType name="UserResponse"&gt;
      &lt;sequence&gt;
       &lt;element name="clientNameList" nillable="true" type="impl:ArrayOf_tns1_Client"/&gt;
       &lt;element name="message" nillable="true" type="xsd:string"/&gt;
      &lt;/sequence&gt;
     &lt;/complexType&gt;
    &lt;/schema&gt;
   &lt;/wsdl:types&gt;
  
     &lt;wsdl:message name="sampleRequest"&gt;
  
        &lt;wsdl:part element="impl:sample" name="parameters"&gt;
  
        &lt;/wsdl:part&gt;
  
     &lt;/wsdl:message&gt;
  
     &lt;wsdl:message name="sampleResponse"&gt;
  
        &lt;wsdl:part element="impl:sampleResponse" name="parameters"&gt;
  
        &lt;/wsdl:part&gt;
  
     &lt;/wsdl:message&gt;
  
     &lt;wsdl:portType name="ImageProcessImpl"&gt;
  
        &lt;wsdl:operation name="sample"&gt;
  
           &lt;wsdl:input message="impl:sampleRequest" name="sampleRequest"&gt;
  
         &lt;/wsdl:input&gt;
  
           &lt;wsdl:output message="impl:sampleResponse" name="sampleResponse"&gt;
  
         &lt;/wsdl:output&gt;
  
        &lt;/wsdl:operation&gt;
  
     &lt;/wsdl:portType&gt;
  
     &lt;wsdl:binding name="ImageProcessImplSoapBinding" type="impl:ImageProcessImpl"&gt;
  
        &lt;wsdlsoap:binding style="document" transport="http://schemas.xmlsoap.org/soap/http"/&gt;
  
        &lt;wsdl:operation name="sample"&gt;
  
           &lt;wsdlsoap:operation soapAction=""/&gt;
  
           &lt;wsdl:input name="sampleRequest"&gt;
  
              &lt;wsdlsoap:body use="literal"/&gt;
  
           &lt;/wsdl:input&gt;
  
           &lt;wsdl:output name="sampleResponse"&gt;
  
              &lt;wsdlsoap:body use="literal"/&gt;
  
           &lt;/wsdl:output&gt;
  
        &lt;/wsdl:operation&gt;
  
     &lt;/wsdl:binding&gt;
  
     &lt;wsdl:service name="ImageProcessImplService"&gt;
  
        &lt;wsdl:port binding="impl:ImageProcessImplSoapBinding" name="ImageProcessImpl"&gt;
  
           &lt;wsdlsoap:address location="http://localhost:8080/Webservice/services/ImageProcessImpl"/&gt;
  
        &lt;/wsdl:port&gt;
  
     &lt;/wsdl:service&gt;
  
  &lt;/wsdl:definitions&gt;
  </code></pre>