Android开发中很多时候要用到webservice,这样可以方便的访问网络资源,这里提供几个网站:
阿里巴巴的FastJson介绍:http://code.alibabatech.com/wiki/display/FastJSON/Home
适合手机的WebService的SDK:Ksoap2:https://code.google.com/archive/p/ksoap2-android/wikis/HowToUse.wiki
获取WebService:http://www.webxml.com.cn/zh_cn/web_services.aspx
这里测试使用天气接口:http://www.webxml.com.cn/WebServices/WeatherWebService.asmx
一、使用Ksoap2:
工具类:WebServiceUtils.java(这个工具类以后就可以直接拿来使用了)
package com.mfc.UrlUtils;
import java.io.IOException;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import org.ksoap2.SoapEnvelope;
import org.ksoap2.serialization.SoapObject;
import org.ksoap2.serialization.SoapSerializationEnvelope;
import org.ksoap2.transport.HttpTransportSE;
import org.xmlpull.v1.XmlPullParserException;
import android.os.Handler;
import android.os.Message;
/*
* 访问WebService的工具类
* 2017年8月10日13:05:29
* */
public class WebServiceUtils {
//webservice路径
public static final String WEB_SERVICE_URL = "http://www.webxml.com.cn/WebServices/WeatherWebService.asmx";
//命名空间
//这个命名空间:找到webservice的网页,点击WSDL就会看到xml,里面有一个
//<wsdl:definitions targetNamespace="http://WebXml.com.cn/">
//就是这个命名空间
private static final String NAMESPACE = "http://WebXml.com.cn/";
//含有三个线程的线程池
private static final ExecutorService executorService = Executors.newFixedThreadPool(3);
/**
*
* @param url
* WebService服务器地址
* @param methodName
* WebService的调用方法名
* @param properties
* WebService的参数
* @param webServiceCallBack
* 回调接口
*/
public static void callWebSerVice(String url, final String methodName,
HashMap<String, String> properties,
final WebServiceCallBack webServiceCallBack) {
// 创建HttpTransportSE对象,传递WebService服务器地址
final HttpTransportSE httpTransportSE = new HttpTransportSE(url);
// 创建SoapObject对象
SoapObject soapObject = new SoapObject(NAMESPACE, methodName);
//soapObject添加参数,这里通过传过来一个HashMap来设置参数
if(properties != null){
Iterator<Map.Entry<String, String>> it = properties.entrySet().iterator();
while(it.hasNext()){
Map.Entry<String, String> entry = it.next();
soapObject.addProperty(entry.getKey(),entry.getValue());
}
}
//实例化SoapSerializationEnvelope,传入WebService的SOAP协议的版本号
final SoapSerializationEnvelope soapEnvelope = new SoapSerializationEnvelope(SoapEnvelope.VER11);
//设置是否调用的是.Net开发的WebService
soapEnvelope.setOutputSoapObject(soapObject);
soapEnvelope.dotNet = true;
httpTransportSE.debug = true;
//用于子线程与主线程通信的Handler
final Handler handler = new Handler(){
@Override
public void handleMessage(Message msg) {
super.handleMessage(msg);
//将返回值回调到callBack的参数中
webServiceCallBack.callBack((SoapObject)msg.obj);
}
};
//开启线程访问WebService
executorService.submit(new Runnable() {
@Override
public void run() {
SoapObject resultSoapObject = null;
try {
httpTransportSE.call(NAMESPACE+methodName, soapEnvelope);
if(soapEnvelope.getResponse() != null){
//获取服务器响应返回的SoapObject
resultSoapObject = (SoapObject) soapEnvelope.bodyIn;
}
} catch (IOException e) {
e.printStackTrace();
} catch (XmlPullParserException e) {
e.printStackTrace();
} finally {
//将获取的消息利用handler发送到主线程
handler.sendMessage(handler.obtainMessage(0, resultSoapObject));
}
}
});
}
public interface WebServiceCallBack {
public void callBack(SoapObject result);
}
}
获取省份的activity:
package com.example.administrator.webserviceandhttpurl;
import android.app.ProgressDialog;
import android.content.Intent;
import android.support.v7.app.AppCompatActivity;
import android.widget.AdapterView.OnItemClickListener;
import android.os.Bundle;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.ListView;
import android.widget.Toast;
import com.mfc.UrlUtils.WebServiceUtils;
import org.ksoap2.serialization.SoapObject;
import java.util.ArrayList;
import java.util.List;
public class KsoapProvinceActivity extends AppCompatActivity {
private List<String> provinceList = new ArrayList<String>();
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.provinceandcity);
init();
}
private void init(){
final ListView listView = (ListView) findViewById(R.id.provinceAndCity);
//显示进度条
final ProgressDialog dialog;
dialog = ProgressDialog.show(KsoapProvinceActivity.this, "提示", "加载中,请稍后...");
//通过工具类调用WebService接口
WebServiceUtils.callWebSerVice(WebServiceUtils.WEB_SERVICE_URL, "getSupportProvince", null, new WebServiceUtils.WebServiceCallBack() {
//WebService接口返回的数据回调到这个方法中
@Override
public void callBack(SoapObject result) {
//关闭进度条
dialog.dismiss();
if(result != null){
provinceList = parseSoapObject(result);
ArrayAdapter<String> adapter = new ArrayAdapter<String>(KsoapProvinceActivity.this, android.R.layout.simple_list_item_1,provinceList);
listView.setAdapter(adapter);
}else{
Toast.makeText(KsoapProvinceActivity.this, "获取WebService数据错误", Toast.LENGTH_SHORT).show();
}
}
});
listView.setOnItemClickListener(new OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
Intent intent = new Intent(KsoapProvinceActivity.this, KsoapCityActivity.class);
intent.putExtra("province", provinceList.get(position));
startActivity(intent);
}
});
}
//解析SoapObject对象
private List<String> parseSoapObject(SoapObject result){
List<String> list = new ArrayList<String>();
//返回的属性中有getSupportProvinceResult,返回的值可能还是一个SoapObject对象,那就再调用一次这个方法,总能得到想要的值
SoapObject provinceSoapObject = (SoapObject) result.getProperty("getSupportProvinceResult");
if(provinceSoapObject == null){
return null;
}
for(int i=0;i<provinceSoapObject.getPropertyCount();i++){
list.add(provinceSoapObject.getProperty(i).toString());
}
return list;
}
}
获取城市的Activity:
package com.example.administrator.webserviceandhttpurl;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import org.ksoap2.serialization.SoapObject;
import android.app.ProgressDialog;
import android.content.Intent;
import android.view.View;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.ArrayAdapter;
import android.widget.ListView;
import android.widget.Toast;
import com.mfc.UrlUtils.WebServiceUtils;
public class KsoapCityActivity extends AppCompatActivity {
private List<String> cityStringList = new ArrayList<String>();
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.provinceandcity);
init();
}
private void init() {
final ListView listView = (ListView) findViewById(R.id.provinceAndCity);
// 显示进度条
final ProgressDialog dialog;
dialog = ProgressDialog.show(KsoapCityActivity.this, "提示", "加载中,请稍后...");
// 添加参数
HashMap<String, String> properties = new HashMap<String, String>();
properties
.put("byProvinceName", getIntent().getStringExtra("province"));
// 通过工具类调用WebService接口
WebServiceUtils.callWebSerVice(WebServiceUtils.WEB_SERVICE_URL,
"getSupportCity", properties, new WebServiceUtils.WebServiceCallBack() {
// WebService接口返回的数据回调到这个方法中
@Override
public void callBack(SoapObject result) {
// 关闭进度条
dialog.dismiss();
if (result != null) {
cityStringList = parseSoapObject(result);
ArrayAdapter<String> adapter = new ArrayAdapter<String>(
KsoapCityActivity.this,
android.R.layout.simple_list_item_1,
cityStringList);
listView.setAdapter(adapter);
} else {
Toast.makeText(KsoapCityActivity.this,
"获取WebService数据错误", Toast.LENGTH_SHORT)
.show();
}
}
});
listView.setOnItemClickListener(new OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> arg0, View arg1,
int arg2, long arg3) {
Intent intent = new Intent(KsoapCityActivity.this, KsoapWeatherActivity.class);
intent.putExtra("city", cityStringList.get(arg2));
startActivity(intent);
}
});
}
// 解析SoapObject对象
private List<String> parseSoapObject(SoapObject result) {
List<String> list = new ArrayList<String>();
SoapObject provinceSoapObject = (SoapObject) result
.getProperty("getSupportCityResult");
for (int i = 0; i < provinceSoapObject.getPropertyCount(); i++) {
String cityString = provinceSoapObject.getProperty(i).toString();
list.add(cityString.substring(0, cityString.indexOf("(")).trim());
}
return list;
}
}
显示省份和城市用的是一个xml:provinceandcity.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent">
<ListView
android:id="@+id/provinceAndCity"
android:layout_width="match_parent"
android:layout_height="wrap_content"></ListView>
</LinearLayout>
获取天气信息的Activity:
package com.example.administrator.webserviceandhttpurl;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import java.util.HashMap;
import org.ksoap2.serialization.SoapObject;
import android.app.ProgressDialog;
import android.widget.TextView;
import android.widget.Toast;
import com.mfc.UrlUtils.WebServiceUtils;
public class KsoapWeatherActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.weather);
init();
}
private void init() {
final TextView mTextWeather = (TextView) findViewById(R.id.weather);
// 显示进度条
final ProgressDialog dialog;
dialog = ProgressDialog.show(KsoapWeatherActivity.this, "提示", "加载中,请稍后...");
HashMap<String, String> properties = new HashMap<String, String>();
properties.put("theCityName", getIntent().getStringExtra("city"));
WebServiceUtils.callWebSerVice(WebServiceUtils.WEB_SERVICE_URL,
"getWeatherbyCityName", properties, new WebServiceUtils.WebServiceCallBack() {
@Override
public void callBack(SoapObject result) {
dialog.dismiss();
if (result != null) {
SoapObject detail = (SoapObject) result
.getProperty("getWeatherbyCityNameResult");
StringBuilder sb = new StringBuilder();
for (int i = 0; i < detail.getPropertyCount(); i++) {
sb.append(detail.getProperty(i)).append("\r\n");
}
mTextWeather.setText(sb.toString());
} else {
Toast.makeText(KsoapWeatherActivity.this,
"获取WebService数据错误", Toast.LENGTH_SHORT)
.show();
}
}
});
}
}
显示天气的xml:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent" >
<ScrollView
android:layout_width="fill_parent"
android:layout_height="fill_parent" >
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent" >
<TextView
android:id="@+id/weather"
android:textColor="#336598"
android:textSize="16sp"
android:layout_width="match_parent"
android:layout_height="match_parent" />
</LinearLayout>
</ScrollView>
</RelativeLayout>
效果图(这里不知道为什么显示不出来天气,还望有人指点):
二、使用HttpUrlConnection:
工具类:
package com.mfc.UrlUtils;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;
/**
* Created by Administrator on 2017/8/10.
*/
public class HttpURLConnectionUtils {
public static String getRemoteInfo(String targetUrl){
String jsonString="";
try {
URL url=new URL(targetUrl);
HttpURLConnection connection=(HttpURLConnection) url.openConnection();
connection.setConnectTimeout(3000);
connection.setRequestMethod("GET");
connection.setDoInput(true);
int code=connection.getResponseCode();
if(code==200){
InputStream inputStream=connection.getInputStream();
ByteArrayOutputStream outputStream=new ByteArrayOutputStream();
int len=0;
byte[] data=new byte[1024];
while ((len=inputStream.read(data))!=-1) {
outputStream.write(data, 0, len);
}
jsonString=new String(outputStream.toByteArray());
}
} catch (IOException e) {
e.printStackTrace();
}
return jsonString;
}
}
Activity:
package com.example.administrator.webserviceandhttpurl;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
import android.support.v7.app.AppCompatActivity;
import android.widget.ListView;
import android.widget.TextView;
import android.widget.Toast;
import com.mfc.UrlUtils.HttpURLConnectionUtils;
/*
* 以查询湖北省的所有城市名称为例
* */
public class HttpURLConnectionActivity extends AppCompatActivity {
private String allCityString;
private TextView allcity;
Handler handler = new Handler(){
@Override
public void handleMessage(Message msg) {
switch (msg.what){
case 000:
allcity.setText(filterHtml(allCityString));
break;
}
}
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.allcity);
allcity = (TextView) findViewById(R.id.allcity);
init();
}
private void init(){
final String path="http://www.webxml.com.cn/WebServices/WeatherWebService.asmx/getWeatherbyCityName?theCityName=随州";
new Thread(new Runnable() {
@Override
public void run() {
allCityString = HttpURLConnectionUtils.getRemoteInfo(path);
handler.sendEmptyMessage(000);
}
}).start();
}
/**
* 使用正则表达式过滤HTML标记
*
* @param source 待过滤内容
* @return
*/
private String filterHtml(String source) {
if(null == source){
return "";
}
return source.replaceAll("</?[^>]+>","").trim();
}
}
显示界面xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent">
<ScrollView
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView
android:id="@+id/allcity"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</ScrollView>
</LinearLayout>
效果图:
资源下载:http://download.youkuaiyun.com/download/fancheng614/9928559
找了比较多类似的博客,发现这一篇讲的挺好的:http://blog.youkuaiyun.com/lyq8479/article/details/6428288