如何在安卓设备上调用SOAP网络服务

569

我在寻找如何在Android中调用标准的SOAP/WSDL Web服务方面遇到了很多问题。我找到的大部分文档要么非常复杂,要么只是提到了"kSoap2",然后让你手动解析所有内容使用SAX。好吧,这没关系,但是它是2008年的事情,所以我想应该有一些好的库可以用于调用标准Web服务。

这个Web服务基本上只是在NetBeans中创建的一个服务。我想要有IDE支持生成plumbing类。我只需要最简单/最优雅的方式来从基于Android的手机联系WSDL的Web服务。


这是一个非常好的关于在Android中使用SOAP的链接:如何使用SOAP在Android中调用Web服务 - Jainendra
如果之前熟悉MS VS,使用Mono for Android将解决许多与数据服务和Web服务相关的问题,一切都简单而快速地开发。 此外,对于不熟悉C#(代码非常类似于Java)的人来说,所有库都具有相同的方法,一些函数被替换为属性,因此名称几乎相同,之前在Android上使用Java编写的人可以非常轻松地利用他们的经验编写C#代码。 - Eugene Bosikov
请查看以下链接,其中有一个详细的示例,介绍了如何在Android中使用Ksoap2访问Web服务从Android访问Web服务 - Fred Ondieki
我相信使用Xamarin/C#和.Net Core是可能的。请参考https://blogs.msdn.microsoft.com/webdev/2016/05/25/announcing-wcf-connected-service-for-net-core-rc2-and-asp-net-core-rc2/。 - Vahid Amiri
这个由Spring提供的工具看起来很有前途。 - Louis
管理员们又搞出了更多毫无意义的混乱... - undefined
26个回答

5
如果您在Android中调用Web服务时遇到问题,那么您可以使用以下代码来调用Web服务并获取响应。请确保您的Web服务以“数据表格格式”返回响应。如果您正在使用SQL Server数据库,则此代码将对您有所帮助。如果您使用的是MYSQL,则需要更改一个东西,只需从句子obj2 =(SoapObject)obj1.getProperty("NewDataSet"); 中替换单词 NewDataSet DocumentElement 即可。
void callWebService(){ 

private static final String NAMESPACE = "http://tempuri.org/"; // for wsdl it may be package name i.e http://package_name
private static final String URL = "http://localhost/sample/services/MyService?wsdl";
// you can use IP address instead of localhost
private static final String METHOD_NAME = "Function_Name";
private static final String SOAP_ACTION = "urn:" + METHOD_NAME;

    SoapObject request = new SoapObject(NAMESPACE, METHOD_NAME);
    request.addProperty("parm_name", prm_value);// Parameter for Method
    SoapSerializationEnvelope envelope = new SoapSerializationEnvelope(SoapEnvelope.VER11);
    envelope.dotNet = true;// **If your Webservice in .net otherwise remove it**
    envelope.setOutputSoapObject(request);
    HttpTransportSE androidHttpTransport = new HttpTransportSE(URL);

    try {
        androidHttpTransport.call(SOAP_ACTION, envelope);// call the eb service
                                                                                                         // Method
    } catch (Exception e) {
        e.printStackTrace();
    }

    // Next task is to get Response and format that response
    SoapObject obj, obj1, obj2, obj3;
    obj = (SoapObject) envelope.getResponse();
    obj1 = (SoapObject) obj.getProperty("diffgram");
    obj2 = (SoapObject) obj1.getProperty("NewDataSet");

    for (int i = 0; i < obj2.getPropertyCount(); i++) { 
// the method getPropertyCount() and  return the number of rows
            obj3 = (SoapObject) obj2.getProperty(i);
            obj3.getProperty(0).toString();// value of column 1
            obj3.getProperty(1).toString();// value of column 2
            // like that you will get value from each column
        }
    }

如果您在这方面有任何问题,可以给我写信。

4
请下载并将SOAP库文件添加到您的项目中。 文件名: ksoap2-android-assembly-3.4.0-jar-with-dependencies 清除应用程序,然后启动程序。
这是用于SOAP服务调用的代码。
    String SOAP_ACTION = "YOUR_ACTION_NAME";
    String METHOD_NAME = "YOUR_METHOD_NAME";
    String NAMESPACE = "YOUR_NAME_SPACE";
    String URL = "YOUR_URL";
    SoapPrimitive resultString = null;

    try {
        SoapObject Request = new SoapObject(NAMESPACE, METHOD_NAME);
        addPropertyForSOAP(Request);

        SoapSerializationEnvelope soapEnvelope = new SoapSerializationEnvelope(SoapEnvelope.VER11);
        soapEnvelope.dotNet = true;
        soapEnvelope.setOutputSoapObject(Request);

        HttpTransportSE transport = new HttpTransportSE(URL);

        transport.call(SOAP_ACTION, soapEnvelope);
        resultString = (SoapPrimitive) soapEnvelope.getResponse();

        Log.i("SOAP Result", "Result Celsius: " + resultString);
    } catch (Exception ex) {
        Log.e("SOAP Result", "Error: " + ex.getMessage());
    }
    if(resultString != null) {
        return resultString.toString();
    }
    else{
        return "error";
    }

结果可能是JSONObject、JSONArray或String。
为了您更好的参考, https://trinitytuts.com/load-data-from-soap-web-service-in-android-application/ 谢谢。

4
这是一个在安卓设备中使用SOAP web服务的工作示例。
**注意:**在项目中添加ksoap2.jar并在AndroidManifest文件中添加INTERNET权限。
public final String WSDL_TARGET_NAMESPACE = "http://tempuri.org/";
public final String METHOD_NAME = "FahrenheitToCelsius";
public final String PROPERTY_NAME = "Fahrenheit";
public final String SOAP_ACTION = "http://tempuri.org/FahrenheitToCelsius";
public final String SOAP_ADDRESS = "http://www.w3schools.com/webservices/tempconvert.asmx";


private class TestAsynk extends AsyncTask<String, Void, String> {

    @Override
    protected void onPostExecute(String result) {

        super.onPostExecute(result);
        Toast.makeText(getApplicationContext(),
                String.format("%.2f", Float.parseFloat(result)),
                Toast.LENGTH_SHORT).show();
    }

    @Override
    protected String doInBackground(String... params) {
        SoapObject request = new SoapObject(WSDL_TARGET_NAMESPACE,
                METHOD_NAME);
        request.addProperty(PROPERTY_NAME, params[0]);

        SoapSerializationEnvelope envelope = new SoapSerializationEnvelope(
                SoapEnvelope.VER11);
        envelope.dotNet = true;

        envelope.setOutputSoapObject(request);

        HttpTransportSE androidHttpTransport = new HttpTransportSE(
                SOAP_ADDRESS);
        Object response = null;
        try {

            androidHttpTransport.call(SOAP_ACTION, envelope);
            response = envelope.getResponse();
            Log.e("Object response", response.toString());

        } catch (Exception e) {
            e.printStackTrace();
        }
        return response.toString();
    }
}

请帮我解决这个问题:http://stackoverflow.com/questions/41573829/how-to-send-and-receive-soap-data-from-webservice-to-google-app-engine - Edijae Crusar

3
您可以使用特定的标头将SOAP调用作为HTTP POST请求执行。我解决了这个问题,而没有像ksoap2这样的附加库。下面是从SOAP服务获取订单的实时代码。
private static HashMap<String,String> mHeaders = new HashMap<>();

static {
    mHeaders.put("Accept-Encoding","gzip,deflate");
    mHeaders.put("Content-Type", "application/soap+xml");
    mHeaders.put("Host", "35.15.85.55:8080");
    mHeaders.put("Connection", "Keep-Alive");
    mHeaders.put("User-Agent","AndroidApp");
    mHeaders.put("Authorization","Basic Q2xpZW50NTkzMzppMjR3s2U="); // optional
}public final static InputStream receiveCurrentShipments(String stringUrlShipments)
{
    int status=0;
    String xmlstring= "<soap:Envelope xmlns:soap=\"http://www.w3.org/2003/05/soap-envelope\" xmlns:ser=\"http://35.15.85.55:8080/ServiceTransfer\">\n" +
            "   <soap:Header/>\n" +
            "   <soap:Body>\n" +
            "      <ser:GetAllOrdersOfShipment>\n" +
            "         <ser:CodeOfBranch></ser:CodeOfBranch>\n" +
            "      </ser:GetAllOrdersOfShipment>\n" +
            "   </soap:Body>\n" +
            "</soap:Envelope>";
    StringBuffer chaine = new StringBuffer("");

    HttpURLConnection connection = null;
    try {
        URL url = new URL(stringUrlShipments);
        connection = (HttpURLConnection) url.openConnection();
        connection.setRequestProperty("Content-Length", xmlstring.getBytes().length + "");
        connection.setRequestProperty("SOAPAction", "http://35.15.85.55:8080/ServiceTransfer/GetAllOrdersOfShipment");

        for(Map.Entry<String, String> entry : mHeaders.entrySet()) {
            String key = entry.getKey();
            String value = entry.getValue();
            connection.setRequestProperty(key,value);

        }

        connection.setRequestMethod("POST");
        connection.setDoInput(true);

        OutputStream outputStream = connection.getOutputStream();
        outputStream.write(xmlstring.getBytes("UTF-8"));
        outputStream.close();

        connection.connect();
        status = connection.getResponseCode();
    } catch (ProtocolException e) {
        e.printStackTrace();
    } catch (MalformedURLException e) {
        e.printStackTrace();
    } catch (IOException e) {
        e.printStackTrace();
    } finally {

        Log.i("HTTP Client", "HTTP status code : " + status);
    }

    InputStream inputStream = null;
    try {
        inputStream = connection.getInputStream();
    } catch (IOException e) {
        e.printStackTrace();
    }

    return inputStream;
}

请帮忙解决这个问题:如何在Google App Engine中发送和接收来自Web服务的SOAP数据? - Edijae Crusar
有两个问题:1. 这是如何从主活动调用的?2. 作为参数传递的StringUrlShipment的值应该是什么? - Tori
请忽略上面的评论中的问题#1。 - Tori
从主活动中,您应该使用AsyncTask调用此代码。在AsyncTask类中实现doInBackground以启动此代码。 - Lapenkov Vladimir

2

要从Android调用SOAP Web服务,请尝试使用此客户端。

不要忘记在Java构建路径中添加ksoap2-android.jar。

public class WsClient {
    private static final String SOAP_ACTION = "somme";
    private static final String OPERATION_NAME = "somme";
    private static final String WSDL_TARGET_NAMESPACE = "http://example.ws";
    private static final String SOAP_ADDRESS = "http://192.168.1.2:8080/axis2/services/Calculatrice?wsdl";

    public String caclculerSomme() {

        String res = null;
        SoapObject request = new SoapObject(WSDL_TARGET_NAMESPACE,
                OPERATION_NAME);
        request.addProperty("a", "5");
        request.addProperty("b", "2");

        SoapSerializationEnvelope envelope = new SoapSerializationEnvelope(
                SoapEnvelope.VER11);
        envelope.dotNet = true;
        envelope.setOutputSoapObject(request);
        HttpTransportSE httpTransport = new HttpTransportSE(SOAP_ADDRESS);

        try {
            httpTransport.call(SOAP_ACTION, envelope);
            String result = envelope.getResponse().toString();
            res = result;
            System.out.println("############# resull is :" + result);
        } catch (Exception exception) {
            System.out.println("########### ERRER" + exception.getMessage());
        }

        return res;
    }
}

@ Wajdi hh 如何比较来自给定响应结果的响应res:-成功......“responce = 1〜成功”......那么我们如何将该结果与来自服务器端的条件进行比较。 - Amitsharma

1

请添加Soap库(ksoap2-android-assembly-3.2.0-jar-with-dependencies.jar):

public static String Fn_Confirm_CollectMoney_Approval(

        HashMap < String, String > str1,
        HashMap < String, String > str2,
        HashMap < String, String > str3) {

    Object response = null;
    String METHOD_NAME = "CollectMoney";
    String NAMESPACE = "http://xxx/yyy/xxx";
    String URL = "http://www.w3schools.com/webservices/tempconvert.asmx";
    String SOAP_ACTION = "";

    try {

        SoapObject RequestParent = new SoapObject(NAMESPACE, METHOD_NAME);

        SoapObject Request1 = new SoapObject(NAMESPACE, "req");

        PropertyInfo pi = new PropertyInfo();

        Set mapSet1 = (Set) str1.entrySet();

        Iterator mapIterator1 = mapSet1.iterator();

        while (mapIterator1.hasNext()) {

            Map.Entry mapEntry = (Map.Entry) mapIterator1.next();

            String keyValue = (String) mapEntry.getKey();

            String value = (String) mapEntry.getValue();

            pi = new PropertyInfo();

            pi.setNamespace("java:com.xxx");

            pi.setName(keyValue);

            pi.setValue(value);

            Request1.addProperty(pi);
        }

        mapSet1 = (Set) str3.entrySet();

        mapIterator1 = mapSet1.iterator();

        while (mapIterator1.hasNext()) {

            Map.Entry mapEntry = (Map.Entry) mapIterator1.next();

            // getKey Method of HashMap access a key of map
            String keyValue = (String) mapEntry.getKey();

            // getValue method returns corresponding key's value
            String value = (String) mapEntry.getValue();

            pi = new PropertyInfo();

            pi.setNamespace("java:com.xxx");

            pi.setName(keyValue);

            pi.setValue(value);

            Request1.addProperty(pi);
        }

        SoapObject HeaderRequest = new SoapObject(NAMESPACE, "XXX");

        Set mapSet = (Set) str2.entrySet();

        Iterator mapIterator = mapSet.iterator();

        while (mapIterator.hasNext()) {

            Map.Entry mapEntry = (Map.Entry) mapIterator.next();

            // getKey Method of HashMap access a key of map
            String keyValue = (String) mapEntry.getKey();

            // getValue method returns corresponding key's value
            String value = (String) mapEntry.getValue();

            pi = new PropertyInfo();

            pi.setNamespace("java:com.xxx");

            pi.setName(keyValue);

            pi.setValue(value);

            HeaderRequest.addProperty(pi);
        }

        Request1.addSoapObject(HeaderRequest);

        RequestParent.addSoapObject(Request1);

        SoapSerializationEnvelope soapEnvelope = new SoapSerializationEnvelope(
                SoapEnvelope.VER10);

        soapEnvelope.dotNet = false;

        soapEnvelope.setOutputSoapObject(RequestParent);

        HttpTransportSE transport = new HttpTransportSE(URL, 120000);

        transport.debug = true;

        transport.call(SOAP_ACTION, soapEnvelope);

        response = (Object) soapEnvelope.getResponse();

        int cols = ((SoapObject) response).getPropertyCount();

        Object objectResponse = (Object) ((SoapObject) response)
                .getProperty("Resp");

        SoapObject subObject_Resp = (SoapObject) objectResponse;


        modelObject = new ResposeXmlModel();

        String MsgId = subObject_Resp.getProperty("MsgId").toString();


        modelObject.setMsgId(MsgId);

        String OrgId = subObject_Resp.getProperty("OrgId").toString();


        modelObject.setOrgId(OrgId);

        String ResCode = subObject_Resp.getProperty("ResCode").toString();


        modelObject.setResCode(ResCode);

        String ResDesc = subObject_Resp.getProperty("ResDesc").toString();


        modelObject.setResDesc(ResDesc);

        String TimeStamp = subObject_Resp.getProperty("TimeStamp")
                .toString();


        modelObject.setTimestamp(ResDesc);

        return response.toString();

    } catch (Exception ex) {

        ex.printStackTrace();

        return null;
    }

}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接