JavaWeb之Servlet:请求 与 响应
1 引入
浏览器和服务器的种类都有很多,要在它们之间通讯,必定要遵循一定的准则,而http协议就是这样的一个"准则"。
Http协议:规定了 浏览器 和 服务器 数据传输的一种格式。
当浏览器想要获取服务器的服务,就会往服务器发送一个请求,这个请求就会使用Http协议规定的格式发送到服务器,而服务器收到这个请求后,也会按照Http协议规定的格式,把服务器的响应发给浏览器。
下面我们看一下这种"格式"的一个实例
请求的格式:
GET /day09/first HTTP/1.1 -- 请求行
Host: localhost:8080 --请求头(多个键值对)
User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:33.0) Gecko/20100101 Firefox/33.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-us,zh-cn;q=0.8,zh;q=0.5,en;q=0.3
Accept-Encoding: gzip, deflate
Connection: keep-alive
--空行
name=eric&password=123456 --实体内容
响应的格式:
HTTP/1.1 200 OK --响应行
Server: Apache-Coyote/1.1 --响应头(多个键值对)
Content-Type: text/html;charset=utf-8
Content-Length: 46
Date: Sat, 22 Nov 2014 01:42:06 GMT
--空行
xxxxxx --实体内容(浏览器主体窗口看到的部分)
现在只要注意格式即可,具体内容我们下面一一讲解
2.Http请求
2.1请求行
GET /day09/first HTTP/1.1
请求行中主要有三个部分 :
1)GET 代表请求的方式。常用的有:GET请求,和 POST请求。
请求方式:GET、POST、HEAD、PUT、CONNECT、TRACE
2)/day09/first 代表请求想要获得的资源的URI
uri : 统一资源标记符。
url:统一资源定位父。
3)HTTP/1.1 代表请求格式的http协议的版本。
http:1.0 : 当前浏览器和服务器建立连接后,一次连接只能发出一次请求。
http:1.1: 当前浏览器和服务器建立连接后,一次连接可以发出多次请求。
那么GET和POST方式为什么事最常用的? 这就要关系到我们的表单。
html表单中只支持的请求的方式只有两个值:GET 和 POST。
下面是表单的一段代码:
<form action="提交的地址" method="GET/POST">
用户名:<input type="text" name="name"/>
密码:<input type="password" name="password"/>
<input type="submit" value="提交"/>
</form>
表单提交后,表单数据就会随请求一起发送到服务器,数据写在了请求里面,但是GET方式 和 POST方式 把数据写在了请求内的不同地方。
Get方式
GET /day09/testGetPost.html?name=eric&password=123456 HTTP/1.1
Host: localhost:8080
User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:33.0) Gecko/20100101 Firefox/33.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-us,zh-cn;q=0.8,zh;q=0.5,en;q=0.3
Accept-Encoding: gzip, deflate
Referer: http://localhost:8080/day09/testGetPost.html
Connection: keep-alive
可以看到,Get方式提交的请求,表单的数据会写在请求行里,并且在请求资源后用 问号 分开。
所以,表单数据会随着显示在浏览器的地址栏,Get方式不适合提交敏感数据,并且数据量不能太大,不能超过1KB.
POST方式
POST /day09/testGetPost.html HTTP/1.1
Host: localhost:8080
User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:33.0) Gecko/20100101 Firefox/33.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-us,zh-cn;q=0.8,zh;q=0.5,en;q=0.3
Accept-Encoding: gzip, deflate
Referer: http://localhost:8080/day09/testGetPost.html
Connection: keep-alive name=eric&password=123456
1)参数放在请求的实体内容中。参数之间以&分割。
2)POST方式可以提交敏感数据
3)POST提交数据大小没有限制。
以上就是 请求行 中的的分析,下面我们来分析请求头。
2.2请求头
Accept: text/html,image/* -- 浏览器告诉服务器支持的数据类型
Accept-Charset: ISO-8859-1 -- 浏览器支持的编码
Accept-Encoding: gzip,compress ---浏览器支持的数据压缩格式
Accept-Language: en-us,zh- --浏览器支持的语言
Host: www.it315.org:80 --浏览器需要访问的主机和端口
If-Modified-Since: Tue, 11 Jul 2000 18:23:51 GMT --浏览器最后更新的缓存时间
Referer: http://www.it315.org/index.jsp --当前请求来自于哪个资源
User-Agent: Mozilla/4.0 (compatible; MSIE 5.5; Windows NT 5.0) --浏览器类型
Cookie:name=eric --浏览器保存的cookie信息
Connection: close/Keep-Alive --浏览器连接的状态。close:关闭。keep-alive:保持连接
Date: Tue, 11 Jul 2000 18:23:51 GMT --请求发出的时间
请求头内包含了很多来自浏览器的信息,我们可以从请求头得到这些信息,这些信息实际上是一些键值对,用这些信息来判断浏览器用户的状态,并且利用这些信息来实现一些功能。
那么我们接收到这些封装好的信息,如何利用代码得到呢?
在java中有这样的一个类,用于得到请求行里面的信息:
HttpServletRequest对象:用于得到请求信息(十分重要),然后处理,得出不同的响应。
核心方法:
请求行:
request.getMethod(); 得到请求方式
request.getRequestURI() / getRequestURL() 得到请求的资源的url
request.getProtocol() 得到协议版本
请求头:
request.getHeader(头名称)
request.getHeaderNames(); 得到所有的头
request.getHeaders(头名称) 得到同名头的值
实体内容:
request.getInputStream(); 得到实体内容的一个输入流
那么如何得到这个对象呢?我们在服务器建一个 servlet ,然后重写一下父类的doGet()方法,doGet方法就是浏览器以Get方式发送请求道服务器时,服务器就会执行doGet()方法里的内容,看下面一段代码:
public class TestServlet extends HttpServlet { public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException { }
}
我们可以看到,doGet()方法的参数中,就有那么一个HttpServletRequest类型的参数,也就是说,在doGet()方法中,我们可以利用这个参数来调用上面说的HttpServletRequest对象的核心方法,来取得请求里的数据!
下面我们利用这些方法获取 请求行 里的信息:
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
String method = request.getMethod();
System.out.println("method is :" + method);
String requestURI = request.getRequestURI();
System.out.println("requestURI is :" + requestURI);
String protocol = request.getProtocol();
System.out.println("protocol is :" + protocol);
}
输出结果:
method is :GET
requestURI is :/MyFirstProject/TestServlet
protocol is :HTTP/1.1
这样就能获取请求行里的信息了!
同理!获取请求头内的键值对的信息,还有实体内容的信息,也可以利用doGet()方法内的HttpServletRequest来完成,此处不一一演示。那么我们下面研究下doGet()方法!
doxxx()方法
上面说过以GET方式提交的请求,Servlet就会调用doGet()方法来处理,十分容易理解的~
所以,如果浏览器以POST方式来提交请求,Servlet就会调用它的doPost()方法来处理了~
对应的,请求方式有这么多种:GET、POST、HEAD、PUT、CONNECT、TRACE
以哪种方式提交的请求,Servlet就会调用doxxx()方法来处理对应的请求了~
获取表单的数据
表单的数据会存储在请求中:
请求行(get方式)
GET /day09/testGetPost.html?name=eric&password=123456 HTTP/1.1
实体内容(post方式)
name=eric&password=123456
细心的读者可能会发现,上面介绍HttpServletRequest的核心方法中,虽然可以获取请求中的数据,但是要清楚得区分出表单内容还是很麻烦,比如说我们想要获得name的值,那么就要写一个程序去判解析字符串,得到name的值。这显得十分麻烦,所以,Servlet中提供了一些简便的方法让我们获取表单数据。
统一的获取请求中表单参数的方法:
request.getParameter(参数名) 获取单个值的参数,比如获得name的值,就这样写:request.getParameter("name");
request.getParameterValues(参数名) 获取多个值的参数,有些表单一个属性有多个值,例如你有多个爱好,那么久调用这个方法获取爱好的多个值。
request.getParameterNames(); 获取所有的参数,这个方法获得表单的所有参数的名字,例如一个表单中有:name,id,hobit,address,phone等。
现实生活中,根据不同的需要,用户提交的表单可能是用Get方式提交的,也可能用POST方式提交的,表单数据根据不同的提交方式存储在请求的不同地方,但是我们得到表单数据后要对数据的处理是一样的,如果在doPost()和doGet()中都写同一个处理方法就显得代码太繁琐了,那么我们如何处理这种情况?
我们可以在doPost()方法中调用doGet()方法,在doGet()判断请求的方式,然后根据两种请求得到数据,然后就对这些数据进行处理。
请求参数的编码问题
1)POST方式
request.setCharacterEncoding(码表);
用于设置获取实体内容参数时查询的码表。建议放在第一 行代码
2)Get方法
2.1 手动解码:(推荐使用)
if("GET".equals(request.getMethod())){ ah = new String(ah.getBytes("iso-8859-1"),"utf-8"); }
2.2 修改服务器的配置文件(依赖服务器,不推荐使用)
找到%tomcat%/conf/server.xml,修改以下配置
<Connector port="8080" protocol="HTTP/1.1" connectionTimeout="20000" redirectPort="8443" URIEncoding="utf-8"/> 加入URIEncoding属性,设置URI后面参数的编码 |
HTTP相应
说完了请求,我们说一下相应,如果你懂了请求里的内容,响应内容就绝对没问题了!
响应浏览器想服务器发出请求,服务器作出响应,我们看以下响应的格式:
HTTP/1.1 200 OK --响应行
Server: Apache-Coyote/1.1 --响应头(多个键值对)
Content-Type: text/html;charset=utf-8
Content-Length: 46
Date: Sat, 22 Nov 2014 01:42:06 GMT
--空行
xxxxxx
响应的格式和请求的格式相似。
响应行
由三部分组成:
Http协议版本 HTTP/1.1
状态码: 服务器告诉浏览器,请求处理的结果。
常用的状态:
200 请求处理完成
302 客户端需要进一步发送请求才能完成过程。通常该状态码与location响应头一起使用。
404 请求的资源没有找到
500 服务器的资源出错。
状态描述: 对状态码的补充
响应头
Location: http://www.it315.org/index.jsp ---重定向的地址。通常和302状态码一起使用。
Server:apache tomcat --服务器的类型
Content-Encoding: gzip -- 服务器发送给浏览器的内容压缩格式
Content-Length: 80 --服务器发送浏览器的数据长度
Content-Language: zh-cn --服务器发送给浏览器的内容语言
Content-Type: text/html; charset=GB2312 --服务器发送给浏览器的内容类型和编码
Last-Modified: Tue, 11 Jul 2000 18:23:51 GMT --服务器资源的最后修改时间
Refresh: 1;url=http://www.it315.org --定时刷新或者隔n秒跳转页面
Content-Disposition: attachment; filename=aaa.zip -- 告诉浏览器以下载方式打开资源
Transfer-Encoding: chunked
Set-Cookie:SS=Q0=5Lb_nQ; path=/search --服务器发送浏览器的cookie信息
Expires: -1 --通知浏览器不使用缓存
Cache-Control: no-cache --通知浏览器不使用缓存
Pragma: no-cache --通知浏览器不使用缓存
Connection: close/Keep-Alive 连接状态
Date: Tue, 11 Jul 2000 18:23:51 GMT 响应的发出时间
最后就是实体内容。 我们可以使用HttpServletResponse对象来操作这些内容,然后发送给浏览器,具体做法其实和HttpServletRequest对象类似。在此不一一讲解。
JavaWeb之Servlet:请求 与 响应的更多相关文章
- 对Servlet请求或响应进行JMockit测试
对Servlet请求及响应进行mock方法, 通过getMockInstance方法对servlet进行打桩,对servlet提供的方法进行mock,替代真正的servlet请求或响应. 参考链接: ...
- Servlet请求和响应
在Java Web中Servlet.请求和响应是最基本的三个对象,在Web容器的管理下,这三者能够完成基本的HTTP请求处理. Servlet的作用是为客户提供服务.servlet的角色是接受一个客户 ...
- 2.Servlet 请求、响应及重定向
PS:以下仅为个人学习笔记,涩及方面略窄 ####################### Request ####################### /** * reque ...
- JavaWeb chapter3 Servlet处理HTTP响应
1. 设置响应状态行 HTTP状态码:1XX,信息性代码: 2XX,客户请求成功: 3XX,用于已经移走的资源文件,指示新的地址: 4XX,由客户端引发的错误: 5XX,由服务器端引发的错误. 2. ...
- servlet servlet请求与响应
request 客户端浏览器发出的请求被封装成一个HttpServletRequest对象.所有的信息包括请求的地址,请求的参数,提交的数据,上传的文件,客户端的Ip地址甚至客户端操作系统都包含在Ht ...
- servlet请求和响应的过程
1.加载 Servlet类被加载到Java虚拟机中,并且实例化.在这个过程中,web容器(例如tomcat)会调用Servlet类的公开无参构造函数,产生一个Servlet类的实例对象.默认情况下Se ...
- HeadFirst Jsp 04 (请求和响应作为servlet)
servlet 的存在就是为了客服服务, servlet的任务是得到一个客户的请求, 再发回一个响应. 由上图可知, web 容器会在启动后就加载所有的servlet类, 并为之创建实例和初始化 注意 ...
- J2EE请求和响应—Servlet
一.什么是Servlet? Servlet是执行Webserver上的一个特殊Java类.其特殊用途是响应client请求并做出处理.使得client与server端进行交互. 二.生命周期 Ser ...
- servlet请求编码与响应编码问题(编码不一致可能会导致乱码)
html中的编码 <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"&g ...
- Java Servlet (1) —— Filter过滤请求与响应
Java Servlet (1) -- Filter过滤请求与响应 版本: Java EE 6 参考来源: Oracle:The Java EE 6 Tutorial: Filtering Reque ...
随机推荐
- C# 扩展
“扩展方法使您能够向现有类型“添加”方法,而无需创建新的派生类型.重新编译或以其他方式修改原始类型.” 这是msdn上说的,也就是你可以对String,Int,DataRow,DataTable等这些 ...
- UITableView 详解 ()
(原本取至D了个L微信公众号) UITableView 详解 一.建立 UITableView DataTable = [[UITableView alloc] initWithFrame:CGRec ...
- DuiLib通用窗口类WindowImplBase封装
.h头文件 class WindowImplBase : public CWindowWnd, public INotifyUI, public IMessageFilterUI, public ID ...
- HDOJ1010(BFS)
//为什么bfs不行呢,想不通 #include<cstdio>#include<cstring>#include<queue>using namespace st ...
- 复杂的sql 一对多查询
SELECT distinct u.Name as UserName, a.OrderId, ( select d.SignCity from T_O ...
- Java 并发编程实战 摘要
第一部分小结 并发技巧清单: 可变状态是至关重要的(It's the mutable state ,stupid). 所有的并发问题结为如何协调对并发状态的访问,可变状态越少,就越容易确保线程安全性. ...
- ERR: Failed to complete setup of assembly (hr = 0x8007000b). Probing terminated.
这个问题, 估计是由于 在 64位系统上运行 C#.net 项目的问题. 试试,将项目 生成属性 中的 平台改成 X86 编译重新发布试试
- 创建parameter id
Custom Parameter-id Creation By Abhijit Daptary, Capgemini India Step1: Creation of parameter ID. P ...
- php实现文件上传的源码
php实现文件上传的源码,更多php技术开发就去php教程网,http://php.662p.com <?php ##author :Androidyue ##sina @androidyue ...
- Mysql授权GRANT ALL PRIVILEGES
1. 改表法. 可能是你的帐号不允许从远程登陆,只能在localhost.这个时候只要在localhost的那台电脑,登入mysql后,更改 "mysql" 数据库里的 " ...