1.GET请求:

   组拼url的路径,把提交的数据拼装url的后面,提交给服务器。

缺点:(1)安全性(Android下提交数据组拼隐藏在代码中,不存在安全问题)  (2)长度有限不能超过4K(http协议限制),IE浏览器限制至1K

优点:代码方便编写

2.我们首先在电脑模拟下GET请求访问服务器的场景

(1)使用Eclipse 新建一个 " 动态web项目 ",如下:

(2)然后编写一个servlet程序(运行在服务端),命名为" LoginServlet ",如下:

代码内容如下:

 package com.himi.web;

 import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse; /**
* Servlet implementation class LoginServlet
*/
@WebServlet("/LoginServlet")
public class LoginServlet extends HttpServlet {
private static final long serialVersionUID = 1L; /**
* @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
*/
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
String qq = request.getParameter("qq");
String password = request.getParameter("password");
System.out.println("qq:"+qq);
System.out.println("password:"+password); //模拟服务器操作,查询数据库,看qq和密码是否正确. response.getOutputStream()获得一个输出流,向浏览器写入数据(提示数据).这里是输出Output,服务器输出到浏览器
if("10086".equals(qq) && "123456".equals(password)) {
response.getOutputStream().write("Login Success".getBytes());
}else {
response.getOutputStream().write("Login Failed".getBytes());
} } }

刚刚我们说过GET请求方法,把提交的数据组拼到url路径上提交到服务器上,所以这里request.getParameter();

(3)接下来编写一个jsp动态页面(区别于html静态页面),首先我们说一下jsp和html区别,如下:

jsp和html区别:

      •HTML页面是静态页面,也就是事先由用户写好放在服务器上,由web服务器向客户端发送;JSP页面是动态页面,有JSP容器执行该页面的Java代码部分然后实时生成的页面.

      •定义上HTML页面是静态页面可以直接运行,JSP页面是动态页它运行时需要转换成servlet。 

      •HTML能直接打开,jsp只能发布到Tomact等服务器上才能打开

      •他们的表头不同,这个是JSP的头“ <%@ page language="java" import="java.util.*" pageEncoding="gbk"%>”在表头中有编码格式和倒入包等。

      •很好区分的在jsp中用<%%>就可以写Java代码了,而html没有<%%>。

编写一个login.jsp代码,在WebContent文件夹下:

login.jsp代码如下:

 <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<%@ page language="java" contentType="text/html; charset=utf-8"
pageEncoding="utf-8"%>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>???????</title>
</head>
<body> <form action="LoginServlet" method="get">
请输入QQ账号: <input type="text" name="qq"> <br/>
请输入QQ密码: <input type="password" name="password"> <br/>
<input type="submit" value="登录">
</form>
</body>
</html>

右击login.jsp文件," 运行方式 "--> " 在服务器上运行 ";运行的结果如下:

(4)打开360浏览器抓包分析http通信的详细过程:

• 打开360浏览器,地址栏输入:http://localhost:8080/web/login.jsp,结果如下:

•随便输入一个QQ账号和QQ密码,输入QQ账号:,输入QQ密码:,如下:

观察下面,我们可以观察到我们输入的QQ账号和QQ密码已经传输到Tomcat服务器上:

详细的抓取数据包如下:

上面提到的Response的数据长度是(字符数),如下Response数据内容:

• 输入正确的QQ账号和QQ密码,如下:

由下面我们知道了我们输入的QQ账号和QQ密码已经传输到Tomcat服务器上面: 

同样抓取的数据包为:

上面提到的Response的数据长度是(字符数),如下Response数据内容:

(5)小结:

•首先我们让编写的Servlet的程序在LoginServlet在Tomcat运行,Tomcat则处于一直监听状态(监听外界Http--GET请求),当我们在login.jsp输入QQ账号和QQ密码时候,点击"登录"之后,浏览器会把QQ账号和QQ密码组拼到url路径上,把这些数据提交给Tomcat服务器;

•此时处于监听状态的Tomcat服务器则根据接收到http的请求数据包中提取到QQ账号和QQ密码,比对正确的QQ账号和QQ密码(现实则是比对数据库的QQ账号和QQ密码);

•根据QQ账号和QQ密码匹配状况,反馈不同的信息,匹配成功返回"Login Success" ,反之匹配失败返回"Login Failed";

•返回的数据包被电脑浏览器获取,然后提取出返回数据,显示在浏览上,这样浏览器上就出现了"Login Success"或"Login Failed";

3.Android下模拟出手机GET请求访问远端服务器场景:

(1)新建一个Android工程,命名为”qq登录",下面首先是MainActivity.java:

 package com.itheima.qqlogin;

 import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL; import android.app.Activity;
import android.os.Bundle;
import android.text.TextUtils;
import android.util.Log;
import android.view.View;
import android.widget.CheckBox;
import android.widget.EditText;
import android.widget.Toast; public class MainActivity extends Activity {
private static final String Tag = "MainActivity";
private EditText et_qq;
private EditText et_pwd;
private CheckBox cb_remember; @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//查询关心的控件
et_qq = (EditText) findViewById(R.id.et_qq);
et_pwd = (EditText) findViewById(R.id.et_pwd);
cb_remember = (CheckBox) findViewById(R.id.cb_remember);
Log.i(Tag,"oncreate 被调用");
//完成数据的回显。
readSavedData();
}
//读取保存的数据
private void readSavedData() {
// getFilesDir() == /data/data/包名/files/ 获取文件的路径 一般系统是不会清理的。 用户手工清理,系统会有提示。
// getCacheDir()== /data/data/包名/cache/ 缓存文件的路径 当系统内存严重不足的时候 系统会自动的清除缓存 用户手工清理系统没有提示
File file = new File(getFilesDir(),"info.txt");
if(file.exists()&&file.length()>0){
try {
//FileInputStream fis = new FileInputStream(file);
FileInputStream fis =this.openFileInput("info.txt");
BufferedReader br = new BufferedReader(new InputStreamReader(fis));
//214342###abcdef
String info = br.readLine();
String qq = info.split("###")[0];
String pwd = info.split("###")[1];
et_qq.setText(qq);
et_pwd.setText(pwd);
fis.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}
/**
* 登陆按钮的点击事件,在点击事件里面获取数据
* @param view
*/
public void login(View view){
final String qq = et_qq.getText().toString().trim();
final String pwd = et_pwd.getText().toString().trim();
if(TextUtils.isEmpty(qq)||TextUtils.isEmpty(pwd)){
Toast.makeText(this, "qq号码或者密码不能为空", 0).show();
return;
}
//判断用户是否勾选记住密码。
if(cb_remember.isChecked()){
//保存密码
Log.i(Tag,"保存密码");
try {
// File file = new File(getFilesDir(),"info.txt");
// FileOutputStream fos = new FileOutputStream(file);
FileOutputStream fos = this.openFileOutput("info.txt", 0);
//214342###abcdef
fos.write((qq+"###"+pwd).getBytes());
fos.close();
Toast.makeText(this, "保存成功", 0).show();
} catch (Exception e) {
e.printStackTrace();
Toast.makeText(this, "保存失败", 0).show();
}
}else{
//无需保存密码
Log.i(Tag,"无需保存密码");
} //登录的操作,网络的请求
new Thread() {
public void run() {
//String path = "http://localhost:8080/web/LoginServlet";这里不能写成localhost
try {
String path = getString(R.string.serverip);
URL url = new URL(path+"?qq="+qq+"&password="+pwd);
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setRequestMethod("GET");
int code = conn.getResponseCode();
if(code == 200) {
InputStream is = conn.getInputStream();
String result = StreamTools.readStream(is);
showToastInAnyThread(result);
}else {
showToastInAnyThread("请求失败");
}
} catch (Exception e) {
e.printStackTrace();
showToastInAnyThread("请求失败");
}
};
}.start(); } /**
* 显示土司 在主线程更新UI
* @param text
*/
public void showToastInAnyThread(final String text) {
runOnUiThread(new Runnable() { @Override
public void run() {
Toast.makeText(MainActivity.this, text, 0).show(); }
});
}
}

其中使用到的工具类StreamTools如下:

 package com.itheima.qqlogin;

 import java.io.ByteArrayOutputStream;
import java.io.InputStream; /**
* 流的工具类
* @author Administrator
*
*/
public class StreamTools {
/**
* 把输入流的内容转换成字符串
* @param is
* @return null解析失败, string读取成功
*/
public static String readStream(InputStream is) throws Exception {
ByteArrayOutputStream baos = new ByteArrayOutputStream();
byte[] buffer = new byte[1024];
int len = 0;
while((len = is.read(buffer)) != -1) {
baos.write(buffer, 0, len);
}
is.close();
String result = baos.toString();
baos.close();
return result; }
}

ByteArrayOutputStream类:是在创建它的实例时,程序内部创建一个byte型别数组的缓冲区

ByteArrayInputStream:的实例向数组中写入或读出byte型数据。

具体用法:

         ByteArrayOutputStream:    可以捕获内存缓冲区的数据,转换成字节数组

         ByteArrayInputStream:     可以将字节数组转化为输入流

(2)布局文件activity_main.xml:

 <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center_horizontal"
android:paddingLeft="10dp"
android:paddingRight="10dp"
android:orientation="vertical" > <ImageView
android:layout_width="200dip"
android:layout_height="200dip"
android:src="@drawable/ic_launcher" /> <EditText
android:id="@+id/et_qq"
android:inputType="text"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="请输入qq号码" /> <EditText
android:id="@+id/et_pwd"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:hint="请输入密码"
android:inputType="textPassword" /> <CheckBox
android:id="@+id/cb_remember"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="记住密码"
/> <Button
android:onClick="login"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="登陆" />
</LinearLayout>

布局效果图如下:

(3) 布署程序到模拟器上,我们进行演示:

当我们输入QQ账号:,QQ密码:,效果如下:

点击登录,出现”Login Failed",如下:

与此同时,我们的Tomcat服务器端也接收到了账号和密码:

(4)当我们输入正确的QQ账号和密码时候:

同时我们看到了Tomcat服务器上面,也收到QQ账号和QQ密码的信息,如下:

(5)小结:

我们点击"登录",程序中提取到QQ账号 和 QQ密码,组拼成url网络访问路径,访问Tomcat服务器;

Tomcat服务器得到账号和密码,会在LoginServlet程序中进行比对,如果匹配成功就返回"Login Success",匹配失败就是返回"Login Failed";

返回的信息数据,手机端程序获取之后,以土司的形式打印出来,提示用户登录的情况。

Android(java)学习笔记152:采用get请求提交数据到服务器(qq登录案例)的更多相关文章

  1. Android(java)学习笔记210:采用post请求提交数据到服务器(qq登录案例)

    1.POST请求:  数据是以流的方式写给服务器 优点:(1)比较安全 (2)长度不限制 缺点:编写代码比较麻烦   2.我们首先在电脑模拟下POST请求访问服务器的场景: 我们修改之前编写的logi ...

  2. Android(java)学习笔记153:采用post请求提交数据到服务器(qq登录案例)

    1.POST请求:  数据是以流的方式写给服务器 优点:(1)比较安全 (2)长度不限制 缺点:编写代码比较麻烦   2.我们首先在电脑模拟下POST请求访问服务器的场景: 我们修改之前编写的logi ...

  3. Android(java)学习笔记212:中文乱码的问题处理(qq登录案例)

    1.我们在之前的笔记中LoginServlet.java中,我们Tomcat服务器回复给客户端的数据是英文的"Login Success","Login Failed&q ...

  4. Android(java)学习笔记155:中文乱码的问题处理(qq登录案例)

    1. 我们在之前的笔记中LoginServlet.java中,我们Tomcat服务器回复给客户端的数据是英文的"Login Success","Login Failed& ...

  5. Android(java)学习笔记209:采用get请求提交数据到服务器(qq登录案例)

    1.GET请求:    组拼url的路径,把提交的数据拼装url的后面,提交给服务器. 缺点:(1)安全性(Android下提交数据组拼隐藏在代码中,不存在安全问题)  (2)长度有限不能超过4K(h ...

  6. Java学习笔记:基本输入、输出数据操作实例分析

    Java学习笔记:基本输入.输出数据操作.分享给大家供大家参考,具体如下: 相关内容: 输出数据: print println printf 输入数据: Scanner 输出数据: JAVA中在屏幕中 ...

  7. Android 采用post方式提交数据到服务器

    接着上篇<Android 采用get方式提交数据到服务器>,本文来实现采用post方式提交数据到服务器 首先对比一下get方式和post方式: 修改布局: <LinearLayout ...

  8. Android 采用get方式提交数据到服务器

    首先搭建模拟web 服务器,新建动态web项目,servlet代码如下: package com.wuyudong.web; import java.io.IOException; import ja ...

  9. Java学习笔记之[ 利用扫描仪Scanner进行数据输入 ]

    /*********数据的输入********//**利用扫描仪Scanner进行数据输入 怎么使用扫描仪Scanner *1.放在类声明之前,引入扫描仪 import java.util.Scann ...

随机推荐

  1. MATLAB求微分

    求微分 diff(函数) , 求的一阶导数;diff(函数, n) , 求的n阶导数(n是具体整数);diff(函数,变量名), 求对的偏导数;diff(函数, 变量名,n) ,求对的n阶偏导数; & ...

  2. 浅谈JavaScript -- 正则表达式

    什么是正则表达式? 正则表达式是由一个字符序列形成的搜索模式.可用于文本搜索和文本替换. 语法:/正则表达式主体/修饰符(可选) var patt=new RegExp(pattern,modifie ...

  3. python字符串和日期相互转换

  4. 2017-10-19 NOIP模拟赛

    Count(哈格朗日插值) 题解: 有个定理,另sum(x)表示小于等于x的数中与x互质的数的和 sum(x)=φ(x)*x/2    最后可知f(x)=x  (f(1)=2)  当然打表能知道. 然 ...

  5. 为什么Python如此慢

    Python当前人气暴涨.它在DevOps,数据科学,Web开发和安全领域均有使用. 但是在速度方面没有赢得美誉. 这里有关于Python比较其他语言如,Java, C#, Go, JavaScrip ...

  6. 3、kubernetes应用快速入门190625

    一.kubernetes应用入门 1.kubectl命令 Basic Commands create Create a resource from a file or from stdin. expo ...

  7. Go入门基础手记

    1. 配置环境变量(临时) export GOPATH=yourpath 2. 跨平台交叉编译 env GOOS=linux GOARCH=amd64 go build 3. test写法 // 首先 ...

  8. linux限制内存和磁盘使用

    一.如何限制用户的磁盘空间 1. 查看系统中所有用户的磁盘空间配额 sudo repquota /dev/vda1 2. 查看某个用户的磁盘空间配额 sudo edquota user_name 要想 ...

  9. 运算符优先级 (JavaScript)

    运算符优先级描述了在计算表达式时执行运算的顺序.先执行具有较高优先级的运算,然后执行较低优先级的运算.例如,先执行相乘,再执行相加. JavaScript 运算符     下表列出了 JavaScri ...

  10. ie 9 position:fixed 无效的两种情况

    第一种情况: 运行发现在Google Chrome,FireFox都可以的,但是在IE9就不行了很是郁闷,因为IE6以上的版本都是支持fixed的属性的:上网上找了好久没找到,因为不知道关键字该怎么搜 ...