android soapfault error
Asked Answered
C

2

1

I am a begginer in android,here I have activity that use web service:

SoapObject request = new SoapObject(NAMESPACE, METHOD_NAME);        
    GetBoundData val = new GetBoundData() {
    };
    PropertyInfo pi = new PropertyInfo();
    pi.setName("GetBoundData");
    pi.setValue(val);
    pi.setType(GetBoundData.class);
    request.addProperty(pi);

    SoapSerializationEnvelope envelope = new SoapSerializationEnvelope(SoapEnvelope.VER11);
    envelope.setOutputSoapObject(request);
    Marshal floatMarshal = new MarshalFloat();

    envelope.addMapping(NAMESPACE, GetBoundData.class.getSimpleName(), GetBoundData.class);
    floatMarshal.register(envelope);
    HttpTransportSE androidHttpTransport = new HttpTransportSE(URL);
    androidHttpTransport.debug =true;
    TextView t = (TextView)this.findViewById(R.id.resultbox);

    HttpTransportSE androidHttpTransport = new HttpTransportSE(URL);
    try {

        androidHttpTransport.call(SOAP_ACTION, envelope);
        System.out.println("aht requestDump is :"+androidHttpTransport.requestDump);
        System.out.println("aht responseDump is :"+androidHttpTransport.responseDump);
    } catch (Exception e) {
        e.printStackTrace(); 
    }
    try {

        Object result = (Object) envelope.bodyIn;
        String s = result.toString();
        t.setText(s);
    } catch (ClassCastException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
        t.setText("1");
    }

and in GetBoundData class :

public abstract class GetBoundData implements KvmSerializable {

String Bound = "((-0.00021792948245596397, -0.0002648681402206421), (0.00021792948246868618, 0.0002648681402206421))";
String Zoom ="21";
public Object getProperty(int arg0) {
switch (arg0){
    case 0:
        return Bound;
    case 1:
        return Zoom;
    default:
        return null;
        }
}

public int getPropertyCount() {
    return 2;//because you have 2 parameters
}

public void getPropertyInfo(int arg0, Hashtable arg1, PropertyInfo arg2) {
switch(arg0)
{

    case 0:
        arg2.type = PropertyInfo.STRING_CLASS;
        arg2.name = "Bound";
        break;
    case 1:
        arg2.type = PropertyInfo.STRING_CLASS;
        arg2.name = "Zoom";
        break;
    default:break;
}

}
public void setval(String bound, String zoom) {
            Bound =  bound;
            Zoom =  zoom;           

    }
public void setProperty(int arg0, Object arg1) {
switch(arg0)
{
    case 0:
        Bound =  (String)arg1;
        break;
    case 1:
        Zoom =  (String)arg1;           
        break;
    default:
        break;
}

} }

and this is webservice xml

<wsdl:types>
 <s:schema elementFormDefault="qualified" targetNamespace="http://tempuri.org/">
  <s:element name="GetBoundData">
   <s:complexType>
    <s:sequence>
      <s:element minOccurs="0" maxOccurs="1" name="Bound" type="s:string"/>
      <s:element minOccurs="0" maxOccurs="1" name="Zoom" type="s:string"/>
    </s:sequence>
   </s:complexType>
  </s:element>
  <s:element name="GetBoundDataResponse">
   <s:complexType>
     <s:sequence>
       <s:element minOccurs="0" maxOccurs="1" name="GetBoundDataResult"       type="tns:ArrayOfAnyType"/>
     </s:sequence>
   </s:complexType>
  </s:element>
  <s:complexType name="ArrayOfAnyType">
    <s:sequence>
      <s:element minOccurs="0" maxOccurs="unbounded" name="anyType" nillable="true"/>
    </s:sequence>
  </s:complexType>
 </s:schema>
</wsdl:types>

here webservice sample:

request:

<?xml version="1.0" encoding="utf-8"?>
<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>
 <GetBoundData xmlns="http://tempuri.org/">
   <Bound>string</Bound>
   <Zoom>string</Zoom>
 </GetBoundData>
</soap:Body>
</soap:Envelope>

response:

<?xml version="1.0" encoding="utf-8"?>
<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>
  <GetBoundDataResponse xmlns="http://tempuri.org/">
    <GetBoundDataResult>
      <anyType />
      <anyType />
    </GetBoundDataResult>
  </GetBoundDataResponse>
 </soap:Body>
</soap:Envelope>

but show this :

SoapFault - faultcode: 'soap:Server'
faultstring: 'Server was unable to process request. ---> Object reference not set to an
instance of an object.' faultactor: 'null' detail: org.kxml2.kdom.Node@44efb360

I used soapobject with getresponse() but error occurred

Cicily answered 23/1, 2012 at 8:3 Comment(2)
Please log the exceptions using Log.e(..) and post the LogCat dumpKaleykaleyard
I add this :catch(Exception exception){ Log.e("TAG","Received an exception",exception); } ,but it dose not catch any exceptionCicily
S
2

Thats because you have complex type (ie Objects) and you are just adding "Simple type" property.
check my answer here, i explained in details what needs to be done.
You will also have to create local classes that match the complex type, these local classes should implement kvmserializable, for example:

<s:element name="GetBoundData">
 <s:complexType>
  <s:sequence>
  <s:element minOccurs="0" maxOccurs="1" name="Bound" type="s:string"/>
  <s:element minOccurs="0" maxOccurs="1" name="Zoom" type="s:string"/>
 </s:sequence>
</s:complexType>

means on the web service, there exists a class called "GetBoundData". So since using ksoap2 you are building manually the soap envelope, you will have to create such a class in your app , implementing kvmserializable ( which is a ksoap2 serialization interface):

public class GetBoundData implements KvmSerializable {

    String Bound; 
    String Zoom;

    @Override
    public Object getProperty(int arg0) {
    switch (arg0){
        case 0:
            return Bound;
        case 1:
            return Zoom;
        default:
            return null;
            }
    }

    @Override
    public int getPropertyCount() {
        return 2;//because you have 2 parameters
    }

    @Override
    public void getPropertyInfo(int arg0, Hashtable arg1, PropertyInfo arg2) {
    switch(arg0)
    {

        case 0:
            arg2.type = PropertyInfo.STRING_CLASS;
            arg2.name = "Bound";
            break;
        case 1:
            arg2.type = PropertyInfo.STRING_CLASS;
            arg2.name = "Zoom";
            break;
        default:break;
    }

    }

    @Override
    public void setProperty(int arg0, Object arg1) {
    switch(arg0)
    {
        case 0:
            Bound =  (String)arg1;
            break;
        case 1:
            Zoom =  (String)arg1;           
            break;
        default:
            break;
    }
}

This is how you build locally a match for the Classes (object,ie complex type) on the server). Then you have to add the necessary properties, build the envelope, add Mapping and Marshalling and send the request. These Steps are all explained in the link i mentioned above.

UPDATE I'll explain to you what these are:

<wsdl:message name="GetBoundDataSoapIn"> 
<wsdl:part name="parameters" element="tns:GetBoundData"/> 
</wsdl:message> 

When is it wsdl:message it means it is a function required on the web service. it has , which means it requires a parameter of type GetBoundData which is not a primitive type, in fact it is a complex type (object).
So here are the steps:
1- you have to write a local representation , ie class, of the complex type GetBoundData ( i already wrote it above)
2- In your application you have to create (its up to u where) a function that will call the function related to "GetBoundDataSoapIn" on the web service. So its a good idead to create a function whose name is significat ie something like:

 public GetBoundData getBoundData()
 {
  try
    {
        SoapObject sobj = new SoapObject(YOUR_NAMESPACE,THE_METHOD_NAME);


        //------------------------------------------------------------------------------
        //  GetBoundData :adding property
        //          <wsdl:message name="GetBoundDataSoapIn"> 
        //          <wsdl:part name="parameters" element="tns:GetBoundData"/> 
        //          </wsdl:message> 
        //  GetBoundData has two params:
        //      <s:element minOccurs="0" maxOccurs="1" name="Bound" type="s:string"/>
        //      <s:element minOccurs="0" maxOccurs="1" name="Zoom" type="s:string"/>
        //
        //--------------------------------------------------------------------------

        //--------------
        //  GetBoundData
        //--------------
        PropertyInfo pi = new PropertyInfo();
        pi.setName("GetBoundData");
        pi.setValue(Whatever_value_your_supposed_to_put);// these values are "Bound" And "Zoom" , they're supposed to be gotten in your app somewhere
        pi.setType(GetBoundData.class);
        sobj.addProperty(pi);

        //------------------------------
        //  START BUILDING SOAP ENVELOPE
        //------------------------------
        SoapSerializationEnvelope soapEnvelope = new SoapSerializationEnvelope(SoapEnvelope.VER11);
        soapEnvelope.setOutputSoapObject(sobj);


        //---------------------------------------------------------------------------------------
        //      MAPPINGS:   
        //---------------------------------------------------------------------------------------

        soapEnvelope.addMapping(YOUR_NAMESPACE, GetBoundData.class.getSimpleName(), GetBoundData.class);

        //---------------------------------------------------------------------------------------
        //      MARSHALLING: 
        //---------------------------------------------------------------------------------------

        Marshal floatMarshal = new MarshalFloat();
        floatMarshal.register(soapEnvelope);


        AndroidHttpTransport aht = new AndroidHttpTransport(YOUR_URL); 


        aht.debug = true;

        try 
        {

            aht.call(YOUR_ACTION, soapEnvelope);

            //Importat Outputs to check how the request/Response looks like.. Check Logcat to find these outputs
            System.out.println("aht requestDump is :"+aht.requestDump);
            System.out.println("aht responseDump is :"+aht.responseDump);


            return soapEnvelope.getResponse();

        } 
        catch (Exception e) 
        {

            e.printStackTrace();
            return "Exception: " + e.getMessage()+"  message IS :" +e.getMessage()+"  localizedmessage is :"+e.getLocalizedMessage();
        }
    }
    catch(Exception ex)
    {
        ex.printStackTrace();
        return "Exception: " + ex.getMessage();
    }
    }
}

So check logCat to see the shape of request and response, and you'll see if you have to get the response and parse it to use it, i am not sure what your response will be, but in my case it was a multidimensional array, so i had to parse it using java functionalities.
as for:

<wsdl:message name="GetBoundDataSoapOut"> 
<wsdl:part name="parameters" element="tns:GetBoundDataResponse"/> 
</wsdl:message> 

this just tells you the web service sends back a response.

Silversmith answered 28/1, 2012 at 2:43 Comment(12)
thank you for your answer but I did not understand what I should write in GetBoundData() functionCicily
You don't "have to" , i meant its a constructor in case you need to initialize some stuff in it. If you don't , then just forget about it.. only function with the "@Override" tags are a MustSilversmith
I re-edit the post and removed the constructor code. If you have any other questions let me knowSilversmith
I really thank you for reply,But could you please tell my how I should add property to soapobject in my case,I have two part GetBoundData and GetBoundDataresult?<wsdl:message name="GetBoundDataSoapIn"> <wsdl:part name="parameters" element="tns:GetBoundData"/> </wsdl:message> <wsdl:message name="GetBoundDataSoapOut"> <wsdl:part name="parameters" element="tns:GetBoundDataResponse"/> </wsdl:message>Cicily
I do that,but still the same soapfault occurred,please check my updated question,thank you for giving this matter your attentionCicily
Bound and staticZoom string are staticCicily
@Cicily can u copy/paste the request/response output you get from :System.out.println("aht requestDump is :"+androidHttpTransport.requestDump); System.out.println("aht responseDump is :"+androidHttpTransport.responseDump);Silversmith
@Cicily the error you are getting is most probably from a wrong value you are passing, are you sure String Bound should be in this format? Is there a non mobile version of your app which is calling the same web service? if yes, try sending your request from there, and check it with soapUI (sourceforge.net/projects/soapui) and see what format the inputs are expected to be.Silversmith
i get this:aht requestDump is :<v:Envelope xmlns:i="w3.org/2001/XMLSchema-instance" xmlns:d="w3.org/2001/XMLSchema" xmlns:c="schemas.xmlsoap.org/soap/encoding" xmlns:v="schemas.xmlsoap.org/soap/envelope/"><v:Header /><v:Body><n0:GetBoundData id="o0" c:root="1" xmlns:n0="tempuri.org/"><GetBoundData i:type="d:anyType"><Bound i:type="d:string">((-0.00021792948245596397, -0.0002648681402206421), (0.00021792948246868618, 0.0002648681402206421))</Bound><Zoom i:type="d:string">21</Zoom></GetBoundData></n0:GetBoundData></v:Body></v:Envelope>Cicily
aht responseDump is :<?xml version="1.0" encoding="utf-8"?><soap:Envelope xmlns:soap="schemas.xmlsoap.org/soap/envelope" xmlns:xsi="w3.org/2001/XMLSchema-instance" xmlns:xsd="w3.org/2001/… was unable to process request. ---&gt; Object reference not set to an instance of an object.</faultstring><detail /></soap:Fault></soap:Body></soap:Envelope>Cicily
@Cicily Ok so the request is now accurate, so the code you are appending is good. The problem is then on the server side, since request soap envelope is accurate. You can try to copy this soap request into soapUI and try it and see what happens. if you get same error, then you should check with the server admin to see what is the problem.Silversmith
@shadesco Could please read my question on WFS and ksoap2-android?Greenwood
B
0


Check you NameSpace ,Method Name . From my experience we get this error when proper connection is not made with webservice

Buyer answered 23/1, 2012 at 8:18 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.