从android调用java web服务

时间:2013-01-15 17:42:48

标签: java android web-services soap

我正在运行一个简单的项目,点击android中的按钮。从Web服务返回显示的消息,其编码在java中完成。

这是我在eclipse for Android中的程序:

@Override
public void onClick(View v) {
    final String url = "http://10.0.2.2:8050/WebPractice/PracticeWebServices?wsdl";
    final String namespace = "http://PracticeWebServices/";
    final String methodName = "hello";
    final String action = namespace + methodName;

    if(v.getId() == submit_btn.getId()) {
        SoapObject so = new SoapObject(namespace, methodName);
        so.addProperty("name", "Arjun");
        SoapSerializationEnvelope sse = new SoapSerializationEnvelope(SoapEnvelope.VER11);
        sse.setOutputSoapObject(so);
        HttpTransportSE hse = new HttpTransportSE(url);

        try {
            hse.call(action, sse);
            SoapPrimitive primitive = (SoapPrimitive)sse.getResponse();
            Toast.makeText(getApplicationContext(),primitive.toString() , Toast.LENGTH_SHORT);
        } catch(IOException e) {
            e.printStackTrace();
        } catch (XmlPullParserException e) {
            e.printStackTrace();
        }
    }
}

以下是我在Java中的代码:

@WebService(serviceName = "PracticeWebServices")
public class PracticeWebServices {

    @WebMethod(operationName = "hello")
    public String hello(@WebParam(name = "name") String name) {
        return "Hello " + name + " !";
    }
}

我在清单文件中包含了互联网权限....

<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />

现在,当我在Eclipse中提供的模拟器中运行该文件时。点击该按钮后,它会显示一条消息Unfortunately the program has stopped

当我检查logCat时....似乎我在 android.os.NetworkOnMainThreadException

中遇到异常

4 个答案:

答案 0 :(得分:2)

你不应该在主要线程中调用长时间守护进程,如互联网资源,磁盘上的数据,......你应该使用后台任务。否则,您会遇到ANR错误或编译错误。

答案 1 :(得分:2)

这里的问题只是你需要在一个单独的线程上进行Web服务调用(或者你有什么)。所以,很简单,你需要研究如何使用Android进行线程化。不幸的是,这可能有点痛苦,因为您需要在单独的线程上进行服务调用,但是您需要更新主线程上的UI。通常这需要在线程之间传递数据,这涉及处理程序或其他复杂性。幸运的是,Android平台提供了异步任务来处理这个问题,这可以缓解一些复杂性,并可以帮助您避免代码中的混乱。

将网络调用迁移到线程(或Android的异步任务)的有用文档

无痛线程(来自Android Developer docs) 异步任务(来自Android Developer docs) Android线程,处理程序和AsyncTask - 教程 设计响应性(来自Android开发人员文档)

答案 2 :(得分:2)

您应该将长网络抓取操作放在ThreadAsyncTask

我建议您使用AsyncTask

您可以通过创建class

extends AsyncTask来执行此类操作
private class LongNetworkOperation extends AsyncTask<String, Void, String> {

    @Override
    protected String doInBackground(String... params) {

        SoapObject so = new SoapObject(namespace, methodName);
        so.addProperty("name", "Arjun");
        SoapSerializationEnvelope sse = new SoapSerializationEnvelope(SoapEnvelope.VER11);
        sse.setOutputSoapObject(so);
        HttpTransportSE hse = new HttpTransportSE(url);

        try {
            hse.call(action, sse);
            SoapPrimitive primitive = (SoapPrimitive)sse.getResponse();
            Toast.makeText(getApplicationContext(),primitive.toString() , Toast.LENGTH_SHORT);
        } catch(IOException e) {
            e.printStackTrace();
        } catch (XmlPullParserException e) {
            e.printStackTrace();
        }
    }
}

您可以在onClick()这样的

上拨打电话
@Override
public void onClick(View v) {
    if(v.getId()==submit_btn.getId()) {
        new LongNetworkOperation.execute();
    }
}

另外,我建议您在ProgressDialog上显示onPreExecute()并将其隐藏在onPostExecute()中,以便用户了解长时间操作时强烈建议的漫长后台进程< / p>

答案 3 :(得分:1)

您不应该在主线程上运行网络请求,这会导致NetworkOnMainThreadException。请使用自定义AsyncTask查看this solution或使用以下其中一个库: