从零开始学习Servlet(3):客户端请求和Servlet响应

这篇博客介绍了Servlet中客户端如何发起请求,包括请求头的获取方式。接着讲解了Servlet服务器对客户端请求的响应过程,涉及状态行、响应报头和文档的构成。还提供了一个设置自动刷新Header的Demo,并解释了设置响应码的方法。
摘要由CSDN通过智能技术生成

Servlet 客户端请求

客户端请求后台数据,部分数据作为HTTP请求头的一部分,不能直接读取:
头信息 描述

头信息描述
Accept这个头信息指定浏览器或其他客户端可以处理的 MIME 类型。值 image/png 或 image/jpeg 是最常见的两种可能值。
Accept-Charset这个头信息指定浏览器可以用来显示信息的字符集。例如 ISO-8859-1。
Accept-Encoding这个头信息指定浏览器知道如何处理的编码类型。值 gzip 或 compress 是最常见的两种可能值。
Accept-Language这个头信息指定客户端的首选语言,在这种情况下,Servlet 会产生多种语言的结果。例如,en、en-us、ru 等。
Authorization这个头信息用于客户端在访问受密码保护的网页时识别自己的身份。
Connection这个头信息指示客户端是否可以处理持久 HTTP 连接。持久连接允许客户端或其他浏览器通过单个请求来检索多个文件。值 Keep-Alive 意味着使用了持续连接。
Content-Length这个头信息只适用于 POST 请求,并给出 POST 数据的大小(以字节为单位)。
Cookie这个头信息把之前发送到浏览器的 cookies 返回到服务器。
Host这个头信息指定原始的 URL 中的主机和端口。
If-Modified-Since这个头信息表示只有当页面在指定的日期后已更改时,客户端想要的页面。如果没有新的结果可以使用,服务器会发送一个 304 代码,表示 Not Modified 头信息。
If-Unmodified-Since这个头信息是 If-Modified-Since 的对立面,它指定只有当文档早于指定日期时,操作才会成功。
Referer这个头信息指示所指向的 Web 页的 URL。例如,如果您在网页 1,点击一个链接到网页 2,当浏览器请求网页 2 时,网页 1 的 URL 就会包含在 Referer 头信息中。
User-Agent这个头信息识别发出请求的浏览器或其他客户端,并可以向不同类型的浏览器返回不同的内容。

以上信息,在Servlet中可以通过调用HttpServletRequest对象的下列方法获取:

返回类型方法名称描述
Cookie[]getCookies()返回一个数组,包含客户端发送该请求的所有的 Cookie 对象。
EnumerationgetAttributeNames()返回一个枚举,包含提供给该请求可用的属性名称。
EnumerationgetHeaderNames()返回一个枚举,包含在该请求中包含的所有的头名。
EnumerationgetParameterNames()返回一个 String 对象的枚举,包含在该请求中包含的参数的名称。
HttpSessiongetSession()返回与该请求关联的当前 session 会话,或者如果请求没有 session 会话,则创建一个。
HttpSessiongetSession(boolean create)返回与该请求关联的当前 HttpSession,或者如果没有当前会话,且创建是真的,则返回一个新的 session 会话。
LocalegetLocale()基于 Accept-Language 头,返回客户端接受内容的首选的区域设置。
ObjectgetAttribute(String name)以对象形式返回已命名属性的值,如果没有给定名称的属性存在,则返回 null。
ServletInputStreamgetInputStream()使用 ServletInputStream,以二进制数据形式检索请求的主体。
StringgetAuthType()返回用于保护 Servlet 的身份验证方案的名称,例如,”BASIC” 或 “SSL”,如果JSP没有受到保护则返回 null。
StringgetCharacterEncoding()返回请求主体中使用的字符编码的名称。
StringgetContentType()返回请求主体的 MIME 类型,如果不知道类型则返回 null。
StringgetContextPath()返回指示请求上下文的请求 URI 部分。
StringgetHeader(String name)以字符串形式返回指定的请求头的值。
StringgetMethod()返回请求的 HTTP 方法的名称,例如,GET、POST 或 PUT。
StringgetParameter(String name)以字符串形式返回请求参数的值,或者如果参数不存在则返回 null。
StringgetPathInfo()当请求发出时,返回与客户端发送的 URL 相关的任何额外的路径信息。
StringgetProtocol()返回请求协议的名称和版本。
StringgetQueryString()返回包含在路径后的请求 URL 中的查询字符串。
StringgetRemoteAddr()返回发送请求的客户端的互联网协议(IP)地址。
StringgetRemoteHost()返回发送请求的客户端的完全限定名称。
StringgetRemoteUser()如果用户已通过身份验证,则返回发出请求的登录用户,或者如果用户未通过身份验证,则返回 null。
StringgetRequestURI()从协议名称直到 HTTP 请求的第一行的查询字符串中,返回该请求的 URL 的一部分。
StringgetRequestedSessionId()返回由客户端指定的 session 会话 ID。
StringgetServletPath()返回调用 JSP 的请求的 URL 的一部分。
String[]getParameterValues(String name)返回一个字符串对象的数组,包含所有给定的请求参数的值,如果参数不存在则返回 null。
booleanisSecure()返回一个布尔值,指示请求是否使用安全通道,如 HTTPS。
intgetContentLength()以字节为单位返回请求主体的长度,并提供输入流,或者如果长度未知则返回 -1。
intgetIntHeader(String name)返回指定的请求头的值为一个 int 值。
intgetServerPort()返回接收到这个请求的端口号。
intgetParameterMap()将参数封装成 Map 类型。

使用getHeaderNames()获取Header中所有参数名的枚举,然后遍历取出Header中的参数。

 @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse response) throws ServletException, IOException {
        //设置响应类型为“text/html;charset=UTF-8"
        String contentType = "text/html;charset=UTF-8";
        response.setContentType(contentType);
        PrintWriter writer = response.getWriter();
        String title = "客户端请求";
        String docType = "<!DOCTYPE html>\n";

        writer.println(docType+
                "<html>\n"
                + "<head><meta charset=\"utf-8\">"
                + "<title>"+title+"</title></head>\n"
                        + "<body bgcolor=\"#f0f0f0\">\n"
                        + "<h1 align=\"center\""+title+"</h1>\n"
                                + "<table width=\"100%\" border=\"1\" align=\"center\">\n"
                                + "<tr bgcolor=\"#949494\">\n"
                                + "<th>Header 名称</th><th>Header 值</th>\n"
                                + "</tr>\n");
        Enumeration headerNames = req.getHeaderNames();
        while (headerNames.hasMoreElements()) {
            String paramName = (String) headerNames.nextElement();
            writer.print("<tr><td>"+paramName+"</td>\n");
            String paramValue = req.getHeader(paramName);
            writer.print("<td>"+paramValue +"</td></tr>");
        }
        writer.println("</table>\n</body></html>");
    }

Servlet 服务器响应客户端请求

Servlet服务器响应一个HTTP请求时通常包含:
- 状态行
- 响应报头
- 空白行
- 文档

格式如下:

HTTP/1.1 200 OK
Content-Type:text/html
Header1:...
Header2:...
...
HeaderN:...
    (Blank Line)
<!Doctype ...>
<html>
<head>Title</head>
<body>
...
</body>
</html>
  • 状态行 包括HTTP版本”HTTP/1.1”、状态码”200”、和与状态码对应的短消息”OK”;
  • 响应报头最常用的字段:
字段名称描述
Allow这个头信息指定服务器支持的请求方法(GET、POST 等)。
Cache-Control这个头信息指定响应文档在何种情况下可以安全地缓存。可能的值有:public、private 或 no-cache 等。
Public表示着文档是可缓存,Private 表示文档是单个用户私用文档,且只能存储在私有(非共享)缓存中,no-cache 表示文档不应被缓存。
Connection这个头信息指示浏览器是否使用持久 HTTP 连接。值 close 指示浏览器不使用持久 HTTP 连接,值 keep-alive 意味着使用持久连接。
Content-Disposition这个头信息可以让您请求浏览器要求用户以给定名称的文件把响应保存到磁盘。
Content-Encoding在传输过程中,这个头信息指定页面的编码方式。
Content-Language这个头信息表示文档编写所使用的语言。例如,en、en-us、ru 等。
Content-Length这个头信息指示响应中的字节数。只有当浏览器使用持久(keep-alive)HTTP 连接时才需要这些信息。
Content-Type这个头信息提供了响应文档的 MIME(Multipurpose Internet Mail Extension)类型。
Expires这个头信息指定内容过期的时间,在这之后内容不再被缓存。
Last-Modified这个头信息指示文档的最后修改时间。然后,客户端可以缓存文件,并在以后的请求中通过 If-Modified-Since 请求头信息提供一个日期。
Location这个头信息应被包含在所有的带有状态码的响应中。在 300s 内,这会通知浏览器文档的地址。浏览器会自动重新连接到这个位置,并获取新的文档。
Refresh这个头信息指定浏览器应该如何尽快请求更新的页面。您可以指定页面刷新的秒数。
Retry-After这个头信息可以与 503(Service Unavailable 服务不可用)响应配合使用,这会告诉客户端多久就可以重复它的请求。
Set-Cookie这个头信息指定一个与页面关联的 cookie。

- 在Servlet中设置这些头信息的方法

返回值方法名描述
StringencodeRedirectURL(String url)为 sendRedirect 方法中使用的指定的 URL 进行编码,或者如果编码不是必需的,则返回 URL 未改变。
StringencodeURL(String url)对包含 session 会话 ID 的指定 URL 进行编码,或者如果编码不是必需的,则返回 URL 未改变。
booleancontainsHeader(String name)返回一个布尔值,指示是否已经设置已命名的响应报头。
booleanisCommitted()返回一个布尔值,指示响应是否已经提交。
voidaddCookie(Cookie cookie)把指定的 cookie 添加到响应。
voidaddDateHeader(String name, long date)添加一个带有给定的名称和日期值的响应报头。
voidaddHeader(String name, String value)添加一个带有给定的名称和值的响应报头。
voidaddIntHeader(String name, int value)添加一个带有给定的名称和整数值的响应报头。
voidflushBuffer()强制任何在缓冲区中的内容被写入到客户端。
voidreset()清除缓冲区中存在的任何数据,包括状态码和头。
voidresetBuffer()清除响应中基础缓冲区的内容,不清除状态码和头。
voidsendError(int sc)使用指定的状态码发送错误响应到客户端,并清除缓冲区。
voidsendError(int sc, String msg)使用指定的状态发送错误响应到客户端。
voidsendRedirect(String location)使用指定的重定向位置 URL 发送临时重定向响应到客户端。
voidsetBufferSize(int size)为响应主体设置首选的缓冲区大小。
voidsetCharacterEncoding(String charset)设置被发送到客户端的响应的字符编码(MIME 字符集)例如,UTF-8。
voidsetContentLength(int len)设置在 HTTP Servlet 响应中的内容主体的长度,该方法设置 HTTP Content-Length 头。
voidsetContentType(String type)如果响应还未被提交,设置被发送到客户端的响应的内容类型。
voidsetDateHeader(String name, long date)设置一个带有给定的名称和日期值的响应报头。
voidsetHeader(String name, String value)设置一个带有给定的名称和值的响应报头。
voidsetIntHeader(String name, int value)设置一个带有给定的名称和整数值的响应报头。
voidsetLocale(Locale loc)如果响应还未被提交,设置响应的区域。
voidsetStatus(int sc)为该响应设置状态码。

Demo 设置自动刷新的Header

@Override
    protected void doGet(HttpServletRequest req, HttpServletResponse response) throws ServletException, IOException {

        //设置自动刷新间隔5s
        response.setIntHeader("Refresh", 5);

        //设置响应内容的类型
        response.setContentType("text/html;charset=utf-8");

        //获得默认时区对应的日历
        Calendar calendar = Calendar.getInstance();
        //将Calendar类型转化为Date类型
        Date date = calendar.getTime();
        //设置日期输出的格式
        String formatStr = "yyyy-MM-dd HH:mm:ss";
        SimpleDateFormat format = new SimpleDateFormat(formatStr);
        //格式化时间
        String fomatTime = format.format(date);

        //获取输出对象
        PrintWriter writer = response.getWriter();

        //设置显示的title
        String title = "Servelt 响应demo 自动刷新Header设置";
        writer.println("<!DOCTYPE html>\n"
                + "<html>\n"
                + "<head><title>"+ title+"</title></head>\n"
                        + "<body bgcolor=\"f0f0f0\">\n"
                        + "<h1 align=\"center\">"+title+"</h1>\n"
                                + "<p>当前的时候是:"+fomatTime+"<p>\n"
                                        + "</body></html>");

    }
响应码
响应码消息描述
100Continue只有请求的一部分已经被服务器接收,但只要它没有被拒绝,客户端应继续该请求。
101Switching Protocols服务器切换协议。
200OK请求成功。
201Created该请求是完整的,并创建一个新的资源。
202Accepted该请求被接受处理,但是该处理是不完整的。
203Non-authoritative Information
204No Content
205Reset Content
206Partial Content
300Multiple Choices链接列表。用户可以选择一个链接,进入到该位置。最多五个地址。
301Moved Permanently所请求的页面已经转移到一个新的 URL。
302Found所请求的页面已经临时转移到一个新的 URL。
303See Other所请求的页面可以在另一个不同的 URL 下被找到。
304Not Modified
305Use Proxy
306Unused在以前的版本中使用该代码。现在已不再使用它,但代码仍被保留。
307Temporary Redirect所请求的页面已经临时转移到一个新的 URL。
400Bad Request服务器不理解请求。
401Unauthorized所请求的页面需要用户名和密码。
402Payment Required您还不能使用该代码。
403Forbidden禁止访问所请求的页面
404Not Found服务器无法找到所请求的页面。.
405Method Not Allowed在请求中指定的方法是不允许的。
406Not Acceptable服务器只生成一个不被客户端接受的响应。
407Proxy Authentication Required在请求送达之前,您必须使用代理服务器的验证。
408Request Timeout请求需要的时间比服务器能够等待的时间长,超时。
409Conflict请求因为冲突无法完成。
410Gone所请求的页面不再可用。
411Length Required“Content-Length” 未定义。服务器无法处理客户端发送的不带 Content-Length 的请求信息。
412Precondition Failed请求中给出的先决条件被服务器评估为 false。
413Request Entity Too Large服务器不接受该请求,因为请求实体过大
414Request-url Too Long服务器不接受该请求,因为 URL 太长。当您转换一个 “post” 请求为一个带有长的查询信息的 “get” 请求时发生。
415Unsupported Media Type服务器不接受该请求,因为媒体类型不被支持。
417Expectation Failed
500Internal Server Error未完成的请求。服务器遇到了一个意外的情况。
501Not Implemented未完成的请求。服务器不支持所需的功能。
502Bad Gateway未完成的请求。服务器从上游服务器收到无效响应。
503Service Unavailable未完成的请求。服务器暂时超载或死机。
504Gateway Timeout网关超时。
505HTTP Version Not Supported服务器不支持”HTTP协议”版本。

设置响应码:

 public void doGet(HttpServletRequest request,
                    HttpServletResponse response)
            throws ServletException, IOException
  {
      // 设置错误代码和原因
      response.sendError(407, "Need authentication!!!" );
  }

本文参考菜鸟教程http://www.runoob.com

  • 0
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值