一、GET和POST的对比:
在漫长的时间当中,其他的方法逐渐的退出了历史舞台,最常用的只剩下GET和POST方法。而之前已经讲过了通过GET方法获取数据,今天来学习一下如何分别通过GET和POST获取数据。
举个例子:get类似于明信片,只有请求头,没有请求体。而post类似于一封信,信封上的内容为请求头;信里面的内容为请求体(请求头和请求体是分开的)。
含义如下:
- GET:通过请求URI得到资源。一般用于获取/查询资源信息。
- POST:用于向服务器提交新的内容。一般用于更新资源信息。
主要区别如下:
- GET方法主要用于从服务器取回数据,POST用于向服务器提交数据
- get类似于明信片,只有请求头,没有请求体;post类似于一封信,信封上的内容为请求头;信里面的内容为请求体
- 使用GET方法啊向服务器i教的数据量较小,通常不超过2K,使用POST向服务器提交的数据量通常没有限制(明信片不能多写,而写信可以写好多内容咧)
- GET请求是将所要提交的数据附在URL之后,而POST请求是将提交的数据放置在请求体当中
老罗在将到get和post请求的时候, 是这样说的:
- 1、GET是从服务器上获取数据,POST是向服务器传送数据。
- 2、在客户端, GET方式在通过URL提交数据,数据在URL中可以看到;POST方式,数据放置在HTML HEADER内提交
- 3、对于GET方式,服务器端用Request.QueryString获取变量的值,对于POST方式,服务器端用Request.Form获取提交的数据。
- 4、GET方式提交的数据最多只能有1024字节,而POST则没有此限制
- 5、安全性问题。正如在(2)中提到,使用 GET 的时候,参数会显示在地址栏上,而 POST 不会。所以,如果这些数据是中文数据而且是非敏感数据,那么使用 GET ;如果用户输入的数据不是中文字符而且包含敏感数据,那么还是使用 POST为好
啰嗦了这么多,对这段来个总结吧。
【总结】
get/post请求的区别:
- get请求方式:显式请求方式,请求参数会在URL上显示,相对快,安全性较低,请求数据的大小一般不超过1kb。
- post请求方式:隐式请求方式,请求参数将会在http请求的实体内容中进行传输,相对慢,安全性较高 ,请求数据的大小没有限制
注:GET请求方式和POST请求区别在于请求参数在传递的过程中方式不同。
二、URL的定义和组成:
URL:Uniform Resource Locator 统一资源定位符
URL的组成部分:以http://www.mbalib.com/china/index.htm为例
- http://:代表超文本传输协议
- www:代表一个万维网服务器
- mbalib.com/:服务器的域名,或服务器名称
- China/:子目录,类似于我们的文件夹
- Index.htm:是文件夹中的一个文件
- /china/index.htm统称为URL路径
三、使用tomcat软件在本地搭建服务器:
有了这个服务器,就相当于在本地的计算机有了一个网站,然后我们可以通过浏览器来访问这个网站。
tomcat软甲是apache旗下的一个开源项目。软件下载链接:http://tomcat.apache.org/
下载之后,将压缩包解压:
注意目录名不能有中文和空格。
软件运行之前要保证环境变量已经配置:
上图中,变量名为JAVA_HOME,变量值为:JDK安装的绝对路径。
回到tomcat的bin目录中, 双击startup.bat:
之后弹出如下界面:
这个时候,本地的服务器就已经搭建起来了。
首先查看自己电脑的ip地址,我的计算机的ip地址为:192.168.1.112。
在浏览器中输入http://192.168.1.112:8080/。如果弹出如下界面,表示tomcat安装成功并且启动起来了:
上方图片中,显示我的Tomcat的版本为:8.0.14。它的版本号是跟着JDK的版本走的,所以,建议JDK的版本为1.8。
我们现在在浏览器上测试一下它吧:
首先在D:\apache-tomcat-8.0.14\webapps\ROOT目录中新建一个jsp文件:
jsp文件中填入如下内容:
<%
String name = request.getParameter("name");
String pwd = request.getParameter("password");
out.print("name:" + name + ",password:" + pwd); //在浏览器上显示输入地址中的用户名与密码
%>
现在我们随便起一个用户名和密码的账号,比如用户名smyhvae,密码为smyh,然后在浏览器中输入如下内容:
http://192.168.1.112:8080/test.jsp?name=smyhvae&password=smyh
输入这个链接之后,回车,出现如下界面:
上图中表示,我们向服务器发送这样一个请求,链接中,问号前面的内容代表请求的路径,问号后面是我们要传送的参数(键是固定不变的,值是用户自己填写的),然后服务器返还给我们这样的数据。
四、使用GET方法向服务器发送数据:
我们在博客“Android系列之网络(一)”中其实就已经通过GET方法向服务器获取数据了,只不过那篇文章中是访问百度首页,然后获取百度首页的数据。现在我们要通过同样的GET方法,只不过是换成了获取本地服务器搭建的网站数据。
只需要稍微修改一下那篇文章中的代码(代码结构一样,只是换了另外一个链接)。完整版代码如下:
activity_main.xml:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:context=".MainActivity" >
<EditText
android:id="@+id/nameText"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="username" />
<EditText
android:id="@+id/pwdText"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="password" />
<Button
android:id="@+id/button1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="submit" />
</LinearLayout>
MainActivity.java的代码如下:
1 package com.example.m04_http02;
2
3 import java.io.BufferedReader;
4 import java.io.InputStreamReader;
5 import java.util.ArrayList;
6 import org.apache.http.HttpEntity;
7 import org.apache.http.HttpResponse;
8 import org.apache.http.NameValuePair;
9 import org.apache.http.client.HttpClient;
10 import org.apache.http.client.entity.UrlEncodedFormEntity;
11 import org.apache.http.client.methods.HttpGet;
12 import org.apache.http.client.methods.HttpPost;
13 import org.apache.http.impl.client.DefaultHttpClient;
14 import org.apache.http.message.BasicNameValuePair;
15
16 import android.app.Activity;
17 import android.os.Bundle;
18 import android.util.Log;
19 import android.view.View;
20 import android.view.View.OnClickListener;
21 import android.widget.Button;
22 import android.widget.EditText;
23
24 public class MainActivity extends Activity {
25
26 private EditText nameText;
27 private EditText pwdText;
28 private Button button;
29
30 @Override
31 protected void onCreate(Bundle savedInstanceState) {
32 super.onCreate(savedInstanceState);
33 setContentView(R.layout.activity_main);
34 nameText = (EditText) findViewById(R.id.nameText);
35 pwdText = (EditText) findViewById(R.id.pwdText);
36 button = (Button) findViewById(R.id.button1);
37
38 button.setOnClickListener(new OnClickListener() {
39
40 @Override
41 public void onClick(View v) {
42 // TODO Auto-generated method stub
43 // 用户输入用户名密码, 然后通过Get方法发送给本地服务器
44 String name = nameText.getText().toString();
45 String pwd = pwdText.getText().toString();
46
47 // 运行线程,使用GET方法向本地服务器发送数据
48 GetThread getThread = new GetThread(name, pwd);
49 getThread.start();
50 }
51 });
52 }
53
54 //子线程:通过GET方法向服务器发送用户名、密码的信息
55 class GetThread extends Thread {
56
57 String name;
58 String pwd;
59
60 public GetThread(String name, String pwd) {
61 this.name = name;
62 this.pwd = pwd;
63 }
64
65 @Override
66 public void run() {
67 //用HttpClient发送请求,分为五步
68 //第一步:创建HttpClient对象
69 HttpClient httpClient = new DefaultHttpClient();
70 //注意,下面这一行中,我之前把链接中的"test"误写成了"text",导致调BUG调了半天没弄出来,真是浪费时间啊
71 String url = "http://192.168.1.112:8080/test.jsp?name=" + name+ "&password=" + pwd;
72 //第二步:创建代表请求的对象,参数是访问的服务器地址
73 HttpGet httpGet = new HttpGet(url);
74 try {
75 //第三步:执行请求,获取服务器发还的相应对象
76 HttpResponse response = httpClient.execute(httpGet);
77 //第四步:检查相应的状态是否正常:检查状态码的值是200表示正常
78 if (response.getStatusLine().getStatusCode() == 200) {
79 //第五步:从相应对象当中取出数据,放到entity当中
80 HttpEntity entity = response.getEntity();
81 BufferedReader reader = new BufferedReader(
82 new InputStreamReader(entity.getContent()));
83 String result = reader.readLine();
84 Log.d("HTTP", "GET:" + result);
85 }
86 } catch (Exception e) {
87 e.printStackTrace();
88 }
89
90 }
91 }
92 }
上方代码中,第73行就是我们所放入的url链接。运行程序后,输入用户名密码,可以看到在后台打印出了我们所输入的用户名和密码:
五、使用POST方法向服务器发送数据:
上一段中,我们是通过GET方法向服务器发送数据,现在通过POST方法向服务器发送数据。布局文件的代码不变,就不写了。MainActivity.java的代码如下:
1 package com.example.m04_http02;
2
3 import java.io.BufferedReader;
4 import java.io.InputStreamReader;
5 import java.util.ArrayList;
6
7 import org.apache.http.HttpEntity;
8 import org.apache.http.HttpResponse;
9 import org.apache.http.NameValuePair;
10 import org.apache.http.client.HttpClient;
11 import org.apache.http.client.entity.UrlEncodedFormEntity;
12 import org.apache.http.client.methods.HttpGet;
13 import org.apache.http.client.methods.HttpPost;
14 import org.apache.http.impl.client.DefaultHttpClient;
15 import org.apache.http.message.BasicNameValuePair;
16
17 import android.app.Activity;
18 import android.os.Bundle;
19 import android.util.Log;
20 import android.view.View;
21 import android.view.View.OnClickListener;
22 import android.widget.Button;
23 import android.widget.EditText;
24
25 public class MainActivity extends Activity {
26
27 private EditText nameText;
28 private EditText pwdText;
29 private Button button;
30
31 @Override
32 protected void onCreate(Bundle savedInstanceState) {
33 super.onCreate(savedInstanceState);
34 setContentView(R.layout.activity_main);
35 nameText = (EditText) findViewById(R.id.nameText);
36 pwdText = (EditText) findViewById(R.id.pwdText);
37 button = (Button) findViewById(R.id.button1);
38
39 button.setOnClickListener(new OnClickListener() {
40
41 @Override
42 public void onClick(View v) {
43 // TODO Auto-generated method stub
44 // 用户输入用户名密码, 然后通过Get方法发送给本地服务器
45 String name = nameText.getText().toString();
46 String pwd = pwdText.getText().toString();
47
48 // 使用GET方法向本地服务器发送数据
49 //GetThread getThread = new GetThread(name, pwd);
50 //getThread.start();
51
52 //使用POST方法向服务器发送数据
53 PostThread postThread = new PostThread(name, pwd);
54 postThread.start();
55 }
56 });
57 }
58
59
60 //子线程:通过GET方法向服务器发送用户名、密码的信息
61 class GetThread extends Thread {
62
63 String name;
64 String pwd;
65
66 public GetThread(String name, String pwd) {
67 this.name = name;
68 this.pwd = pwd;
69 }
70
71 @Override
72 public void run() {
73 //用HttpClient发送请求,分为五步
74 //第一步:创建HttpClient对象
75 HttpClient httpClient = new DefaultHttpClient();
76 //注意,下面这一行中,我之前把链接中的"test"误写成了"text",导致调BUG调了半天没弄出来,真是浪费时间啊
77 String url = "http://192.168.1.112:8080/test.jsp?name=" + name+ "&password=" + pwd;
78 //第二步:创建代表请求的对象,参数是访问的服务器地址
79 HttpGet httpGet = new HttpGet(url);
80 try {
81 //第三步:执行请求,获取服务器发还的相应对象
82 HttpResponse response = httpClient.execute(httpGet);
83 //第四步:检查相应的状态是否正常:检查状态码的值是200表示正常
84 if (response.getStatusLine().getStatusCode() == 200) {
85 //第五步:从相应对象当中取出数据,放到entity当中
86 HttpEntity entity = response.getEntity();
87 BufferedReader reader = new BufferedReader(
88 new InputStreamReader(entity.getContent()));
89 String result = reader.readLine();
90 Log.d("HTTP", "GET:" + result);
91 }
92 } catch (Exception e) {
93 e.printStackTrace();
94 }
95
96 }
97 }
98
99 //子线程:使用POST方法向服务器发送用户名、密码等数据
100 class PostThread extends Thread {
101
102 String name;
103 String pwd;
104
105 public PostThread(String name, String pwd) {
106 this.name = name;
107 this.pwd = pwd;
108 }
109
110 @Override
111 public void run() {
112 HttpClient httpClient = new DefaultHttpClient();
113 String url = "http://192.168.1.112:8080/test.jsp";
114 //第二步:生成使用POST方法的请求对象
115 HttpPost httpPost = new HttpPost(url);
116 //NameValuePair对象代表了一个需要发往服务器的键值对
117 NameValuePair pair1 = new BasicNameValuePair("name", name);
118 NameValuePair pair2 = new BasicNameValuePair("password", pwd);
119 //将准备好的键值对对象放置在一个List当中
120 ArrayList<NameValuePair> pairs = new ArrayList<NameValuePair>();
121 pairs.add(pair1);
122 pairs.add(pair2);
123 try {
124 //创建代表请求体的对象(注意,是请求体)
125 HttpEntity requestEntity = new UrlEncodedFormEntity(pairs);
126 //将请求体放置在请求对象当中
127 httpPost.setEntity(requestEntity);
128 //执行请求对象
129 try {
130 //第三步:执行请求对象,获取服务器发还的相应对象
131 HttpResponse response = httpClient.execute(httpPost);
132 //第四步:检查相应的状态是否正常:检查状态码的值是200表示正常
133 if (response.getStatusLine().getStatusCode() == 200) {
134 //第五步:从相应对象当中取出数据,放到entity当中
135 HttpEntity entity = response.getEntity();
136 BufferedReader reader = new BufferedReader(
137 new InputStreamReader(entity.getContent()));
138 String result = reader.readLine();
139 Log.d("HTTP", "POST:" + result);
140 }
141 } catch (Exception e) {
142 e.printStackTrace();
143 }
144 } catch (Exception e) {
145 e.printStackTrace();
146 }
147 }
148 }
149
150
151 }
上方代码中,我们新开一个子线程,使用POST方法向服务器发送用户名、密码等数据。我们之前已经知道,使用GET方法发送HTTP请求有五大步骤,而如今换成POST方法时,需要在第二步和第三步之间加入一些步骤(即上方加粗部分的代码:116-127行),多的步骤其实是往请求对象中加入请求体。现在来详细解释一下这部分代码:
我们通过NameValuePair集合来存放待提交的参数,并将这个参数集合传入到一个UrlEncodedFormEntity当中(这个类的对象就代表了一个请求体,即键值对),然后将请求体放置在请求对象httpPost当中。
程序运行后,输入用户名和密码,点击按钮,在后台打印出了之前输入的用户名密码:
现在我们总结一下POST提交数据的步骤:
- 1. 构造请求对象;
- 2. 将需要传递给服务器端的数据放置在键值对对象当中;
- 3. 将准备好的键值对放置在List当中;
- 4. 生成代表请求体的对象;
- 5. 将存有请求键值对的List对象放置在请求题对象当中;
- 6. 将请求体对象放置到请求对象当中;
- 7. 发送请求对象
- 后面的步骤(即处理请求对象)和GET方法是一致的。