Android POST方式提交数据
android虽然内置了apache的HttpClient组件来实现客户端向服务器端提交数据,为了便于理解其底层原理,下面例子是通过URL获得Connection,并获得其输出流向服务器发送数据
1.新建一个web项目TestAndroid,我用到了struts2,引入相应的jar包,只需几个核心包就够了,多了容易报错,它们分别是
commons-logging-1.0.4.jar
freemarker-2.3.15.jar
ognl-2.7.3.jar
struts2-core-2.1.8.1.jar
xwork-core-2.1.6.jar
commons-fileupload-1.2.1.jar
2.新建一个action
package com.lamp.action;public class LoginAction{private String id = null;private String name = null;public String getId() {return id;}public void setId(String id) {this.id = id;}public String getName() {return name;}public void setName(String name) {this.name = name;}public String execute() throws Exception {System.out.println(this.id + this.name);return "success";}}
3.在struts.xml中对action进行相应配置
<package name="lamp" extends="struts-default"> <action name="login" name="code"><filter><filter-name>struts2</filter-name><filter-class>org.apache.struts2.dispatcher.FilterDispatcher</filter-class></filter><filter-mapping><filter-name>struts2</filter-name><url-pattern>/*</url-pattern></filter-mapping>
至此web配置完成
5.新建一个android工程,并编写一个工具类实现向服务器端发送数据
package com.lamp.util;import java.io.ByteArrayOutputStream;import java.io.DataOutputStream;import java.io.InputStream;import java.net.HttpURLConnection;import java.net.URL;import java.net.URLEncoder;import java.util.Map;public class NetTool {/** * * @param urlPath 请求路径 * @param params Map中key为请求参数,value为请求参数的值 * @param encoding编码方式 * @return * @throws Exception *///通过post向服务器端发送数据,并获得服务器端输出流public static InputStream getInputStreamByPost(String urlPath,Map<String,String> params,String encoding) throws Exception{StringBuffer sb = new StringBuffer();for(Map.Entry<String,String> entry:params.entrySet()){sb.append(entry.getKey()).append("=").append(URLEncoder.encode(entry.getValue(), encoding));sb.append("&");}String data = sb.deleteCharAt(sb.length()-1).toString();URL url = new URL(urlPath);//打开连接HttpURLConnection conn = (HttpURLConnection)url.openConnection();//设置提交方式conn.setDoOutput(true);conn.setDoInput(true);conn.setRequestMethod("POST");//post方式不能使用缓存conn.setUseCaches(false);conn.setInstanceFollowRedirects(true);//设置连接超时时间conn.setConnectTimeout(6*1000);//配置本次连接的Content-Type,配置为application/x-www-form-urlencodedconn.setRequestProperty("Content-Type", "application/x-www-form-urlencoded");//维持长连接conn.setRequestProperty("Connection", "Keep-Alive");//设置浏览器编码conn.setRequestProperty("Charset", "UTF-8");DataOutputStream dos = new DataOutputStream(conn.getOutputStream());//将请求参数数据向服务器端发送dos.writeBytes(data);dos.flush();dos.close();if(conn.getResponseCode() == 200){//获得服务器端输出流return conn.getInputStream();}return null;}//通过输入流获得字节数组public static byte[] readStream(InputStream is) throws Exception {byte[] buffer = new byte[1024];ByteArrayOutputStream bos = new ByteArrayOutputStream();int len = 0;while((len=is.read(buffer)) != -1){bos.write(buffer, 0, len);} is.close();return bos.toByteArray();}}
6.编写一个测试类
package com.lamp.activity;import java.io.InputStream;import java.util.HashMap;import java.util.Map;import android.test.AndroidTestCase;import android.util.Log;import com.lamp.util.NetTool;public class TestPostData extends AndroidTestCase {private static final String TAG = "TestPostData";public void test() throws Exception {//请求参数键-值对Map<String,String> map = new HashMap<String,String>();map.put("id", "123456");map.put("name", "李四");//服务器请求路径String urlPath = "http://ip地址:8080/TestAndroid/login";InputStream is = NetTool.getInputStreamByPost(urlPath, map, "UTF-8");byte[] data = NetTool.readStream(is);Log.i(TAG, new String(data));}}
记得要在AndroidManifest.xml文件中注册访问网络权限以及单元测试所需的配置
<!-- 注册访问网络权限 --> <uses-permission android:name="android.permission.INTERNET"/>
首先将建立的web项目在应用服务器中部署并运行起来,然后在android工程中运行单元测试我们可以看到在web端得到了客户端发送过来的数据,而且客户端也得到了服务器端发送过来的数据