android HTTP 通信, XML 解析, 通过 Hander 实现异步消息处理 (1)

来源:互联网 发布:德塔文数据 编辑:程序博客网 时间:2024/04/26 00:17
android HTTP 通信, XML 解析, 通过 Hander 实现异步消息处理 (1)
2010-02-03 10:55

介绍
在 Android 中与服务端做 HTTP 通信,解析 XML,通过 Handler 实现异步消息处理
HTTP 通信 - 与服务端做 HTTP 通信,分别以 GET 方式和 POST 方式做演示
XML 解析 - 可以用两种方式解析 XML,分别是 DOM 方式和 SAX 方式
异步消息处理 - 通过 Handler 实现异步消息处理,以一个自定义的异步下载类来说明 Handler 的用法

1、HTTP 通信和 XML 解析的 Demo
MySAXHandler.java

代码
package com.webabcd.communication;

import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.DefaultHandler;

// 继承 DefaultHandler 以实现指定 XML 的 SAX 解析器
// DOM - W3C 标准,需要把 xml 数据全部加载完成后才能对其做解析,可对树做任意遍历
// SAX - 流式解析,通过事件模型解析 xml,只能顺序解析
public class MySAXHandler extends DefaultHandler {

    private boolean mIsTitleTag = false;
    private boolean mIsSalaryTag = false;
    private boolean mIsBirthTag = false;
    private String mResult = "";
   
    // 打开 xml 文档的回调函数
    @Override
    public void startDocument() throws SAXException {
        // TODO Auto-generated method stub
        super.startDocument();
    }
   
    // 关闭 xml 文档的回调函数
    @Override
    public void endDocument() throws SAXException {
        // TODO Auto-generated method stub
        super.endDocument();
    }
   
    // 一发现元素开始标记就回调此函数
    @Override
    public void startElement(String uri, String localName, String qName,
            Attributes attributes) throws SAXException {
        if (localName == "title")
            mIsTitleTag = true;
        else if (localName == "salary")
            mIsSalaryTag = true;
        else if (localName == "dateOfBirth")
            mIsBirthTag = true;
        else if (localName == "employee")
            mResult += "/nname:" + attributes.getValue("name");   
    }

    // 一发现元素结束标记就回调此函数
    @Override
    public void endElement(String uri, String localName, String qName)
            throws SAXException {
        if (localName == "title")
            mIsTitleTag = false;
        else if (localName == "salary")
            mIsSalaryTag = false;
        else if (localName == "dateOfBirth")
            mIsBirthTag = false;
    }

    // 一发现元素值或属性值就回调此函数
    @Override
    public void characters(char[] ch, int start, int length)
            throws SAXException {
        if (mIsTitleTag)
            mResult += new String(ch, start, length);
        else if (mIsSalaryTag)
            mResult += " salary:" + new String(ch, start, length);
        else if (mIsBirthTag)
            mResult += " dateOfBirth:" + new String(ch, start, length);
    }
   
    public String getResult(){
        return mResult;
    }
}


Main.java

代码
package com.webabcd.communication;

import java.io.BufferedInputStream;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;

import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory;

import org.apache.http.HttpEntity;
import org.apache.http.HttpResponse;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.message.BasicNameValuePair;
import org.apache.http.protocol.HTTP;
import org.apache.http.util.ByteArrayBuffer;
import org.apache.http.util.EncodingUtils;
import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.NodeList;
import org.xml.sax.InputSource;
import org.xml.sax.XMLReader;

import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;

public class Main extends Activity {
   
    private TextView textView;
   
    /** Called when the activity is first created. */
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
       
        textView = (TextView) this.findViewById(R.id.textView);
       
        Button btn1 = (Button) this.findViewById(R.id.btn1);
        btn1.setText("http get demo");
        btn1.setOnClickListener(new Button.OnClickListener() {
            public void onClick(View v) {
                httpGetDemo();
            }
        });
       
        Button btn2 = (Button) this.findViewById(R.id.btn2);
        btn2.setText("http post demo");
        btn2.setOnClickListener(new Button.OnClickListener() {
            public void onClick(View v) {
                httpPostDemo();
            }
        });
       
        Button btn3 = (Button) this.findViewById(R.id.btn3);
        // DOM - Document Object Model
        btn3.setText("DOM 解析 XML");
        btn3.setOnClickListener(new Button.OnClickListener() {
            public void onClick(View v) {
                DOMDemo();
            }
        });
       
        Button btn4 = (Button) this.findViewById(R.id.btn4);
        // SAX - Simple API for XML
        btn4.setText("SAX 解析 XML");
        btn4.setOnClickListener(new Button.OnClickListener() {
            public void onClick(View v) {
                SAXDemo();
            }
        });
    }
   
    // Android 调用 http 协议的 get 方法
    // 本例:以 http 协议的 get 方法获取远程页面响应的内容
    private void httpGetDemo(){
        try {
            // 模拟器测试时,请使用外网地址
            URL url = new URL("http://xxx.xxx.xxx");
            URLConnection con = url.openConnection();
           
            String result = "http status code: " + ((HttpURLConnection)con).getResponseCode() + "/n";
            // HttpURLConnection.HTTP_OK
           
            InputStream is = con.getInputStream();
            BufferedInputStream bis = new BufferedInputStream(is);
            ByteArrayBuffer bab = new ByteArrayBuffer(32);
            int current = 0;
            while ( (current = bis.read()) != -1 ){
                bab.append((byte)current);
            }
            result += EncodingUtils.getString(bab.toByteArray(), HTTP.UTF_8);
           
            bis.close();
            is.close();

            textView.setText(result);
        } catch (Exception e) {
            textView.setText(e.toString());
        }
    }
   
    // Android 调用 http 协议的 post 方法
    // 本例:以 http 协议的 post 方法向远程页面传递参数,并获取其响应的内容
    private void httpPostDemo(){
        try {
            // 模拟器测试时,请使用外网地址
            String url = "http://5billion.com.cn/post.php";
            Map<String, String> data = new HashMap<String, String>();
            data.put("name", "webabcd");
            data.put("salary", "100");
           
            DefaultHttpClient httpClient = new DefaultHttpClient();
            HttpPost httpPost = new HttpPost(url);
            ArrayList<BasicNameValuePair> postData = new ArrayList<BasicNameValuePair>();
            for (Map.Entry<String, String> m : data.entrySet()) {
                postData.add(new BasicNameValuePair(m.getKey(), m.getValue()));
            }

            UrlEncodedFormEntity entity = new UrlEncodedFormEntity(postData, HTTP.UTF_8);
            httpPost.setEntity(entity);
           
            HttpResponse response = httpClient.execute(httpPost);
           
            String result = "http status code: " + response.getStatusLine().getStatusCode() + "/n";
            // HttpURLConnection.HTTP_OK
           
            HttpEntity httpEntity = response.getEntity();
           
            InputStream is = httpEntity.getContent();
            result += convertStreamToString(is);
           
            textView.setText(result);
        } catch (Exception e) {
            textView.setText(e.toString());   
        }
    }
   
    // 以 DOM 方式解析 XML(xml 数据详见 res/raw/employee.xml)
    private void DOMDemo(){
        try    {
            DocumentBuilderFactory docFactory = DocumentBuilderFactory.newInstance();
            DocumentBuilder docBuilder = docFactory.newDocumentBuilder();
            Document doc = docBuilder.parse(this.getResources().openRawResource(R.raw.employee));
            Element rootElement = doc.getDocumentElement();
            NodeList employeeNodeList = rootElement.getElementsByTagName("employee");
           
            textView.setText("DOMDemo" + "/n");
            String title = rootElement.getElementsByTagName("title").item(0).getFirstChild().getNodeValue();
            textView.append(title);
            for (int i=0; i<employeeNodeList.getLength(); i++){
                Element employeeElement = ((Element)employeeNodeList.item(i));
                String name = employeeElement.getAttribute("name");
                String salary = employeeElement.getElementsByTagName("salary").item(0).getFirstChild().getNodeValue();
                String dateOfBirth = employeeElement.getElementsByTagName("dateOfBirth").item(0).getFirstChild().getNodeValue();
                textView.append("/nname: "+name+" salary: "+salary+" dateOfBirth: " + dateOfBirth);
            }
        } catch (Exception e) {
            textView.setText(e.toString());   
        }
    }
   
    // 以 SAX 方式解析 XML(xml 数据详见 res/raw/employee.xml)
    // SAX 解析器的实现详见 MySAXHandler.java
    private void SAXDemo(){
        try    {
            SAXParserFactory saxFactory = SAXParserFactory.newInstance();
            SAXParser parser = saxFactory.newSAXParser();
            XMLReader reader = parser.getXMLReader();
           
            MySAXHandler handler = new MySAXHandler();
            reader.setContentHandler(handler);
            reader.parse(new InputSource(this.getResources().openRawResource(R.raw.employee)));
            String result = handler.getResult();
            textView.setText("SAXDemo" + "/n");
            textView.append(result);
        } catch (Exception e) {
            textView.setText(e.toString());   
        }
    }

    // 辅助方法,用于把流转换为字符串
    private String convertStreamToString(InputStream is) {
        BufferedReader reader = new BufferedReader(new InputStreamReader(is));
        StringBuilder sb = new StringBuilder();  

        String line = null;
        try {
            while ((line = reader.readLine()) != null) {
                sb.append(line + "/n");
            }
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            try {
                is.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }  

        return sb.toString();

原创粉丝点击