HttpServlet 类解析

来源:互联网 发布:2017淘宝双11实时 编辑:程序博客网 时间:2024/05/20 17:24

HttpServlet 对象开始

当一个HttpServlet 对象(子类) 被执行,也就是被访问的时候,HttpServlet 做了什么?

public void service(ServletRequest req, ServletResponse res)        throws ServletException, IOException {        HttpServletRequest  request;        HttpServletResponse response;        try {            request = (HttpServletRequest) req;            response = (HttpServletResponse) res;        } catch (ClassCastException e) {            throw new ServletException("non-HTTP request or response");        }        service(request, response);    }

这个方法是主要的一个开始,它是被ApplicationFilterChain 调用,而这个方法做的非常简单的处理,是个java 程序员应该都能看懂,这个方法把过来的ServletRequest 对象和ServletResponse 对象进行了强转,强转之后调用了另一个同名的函数。

另一个service 函数

这个函数是对浏览器对客户端方法的类型,进行不同了调用。

 protected void service(HttpServletRequest req, HttpServletResponse resp)        throws ServletException, IOException {        String method = req.getMethod();        if (method.equals(METHOD_GET)) {            long lastModified = getLastModified(req);            if (lastModified == -1) {                doGet(req, resp);            } else {                long ifModifiedSince;                try {                    ifModifiedSince = req.getDateHeader(HEADER_IFMODSINCE);                } catch (IllegalArgumentException iae) {                    ifModifiedSince = -1;                }                if (ifModifiedSince < (lastModified / 1000 * 1000)) {                    maybeSetLastModified(resp, lastModified);                    doGet(req, resp);                } else {                    resp.setStatus(HttpServletResponse.SC_NOT_MODIFIED);                }            }        } else if (method.equals(METHOD_HEAD)) {            long lastModified = getLastModified(req);            maybeSetLastModified(resp, lastModified);            doHead(req, resp);        } else if (method.equals(METHOD_POST)) {            doPost(req, resp);        } else if (method.equals(METHOD_PUT)) {            doPut(req, resp);        } else if (method.equals(METHOD_DELETE)) {            doDelete(req, resp);        } else if (method.equals(METHOD_OPTIONS)) {            doOptions(req,resp);        } else if (method.equals(METHOD_TRACE)) {            doTrace(req,resp);        } else {            String errMsg = lStrings.getString("http.method_not_implemented");            Object[] errArgs = new Object[1];            errArgs[0] = method;            errMsg = MessageFormat.format(errMsg, errArgs);            resp.sendError(HttpServletResponse.SC_NOT_IMPLEMENTED, errMsg);        }    }

这个方法处理访问只有两点。

处理的两点

第一点

也是程序员最能理解的一点,就是处理不同访问方式调用不同方法。
都有哪些访问的方法呢?现在最常用的有两种,分别是GET 和POST。

以下是HttpServlet 的所有访问方式类型。

    private static final String METHOD_DELETE = "DELETE";    private static final String METHOD_HEAD = "HEAD";    private static final String METHOD_GET = "GET";    private static final String METHOD_OPTIONS = "OPTIONS";    private static final String METHOD_POST = "POST";    private static final String METHOD_PUT = "PUT";    private static final String METHOD_TRACE = "TRACE";

除了GET 和 HEAD 这两种访问方式,其他的处理都是非常简单暴力

 else if (method.equals(METHOD_POST)) {            doPost(req, resp);        } else if (method.equals(METHOD_PUT)) {            doPut(req, resp);        } else if (method.equals(METHOD_DELETE)) {            doDelete(req, resp);        } else if (method.equals(METHOD_OPTIONS)) {            doOptions(req,resp);        } else if (method.equals(METHOD_TRACE)) {            doTrace(req,resp);        }

而GET 和 HEAD 类型的访问都做了什么处理?

第二点

第二点,相信大多java 程序员(包括我)都不知道,聪明的小伙伴们都看到了GET 和 HEAD 的处理方式不是那么的简单暴力,那么它俩都做了神马?

GET

在调用doGet 执行之前,HttpServlet 都做了神马?

if (method.equals(METHOD_GET)) {            long lastModified = getLastModified(req);            if (lastModified == -1) {                doGet(req, resp);            } else {                long ifModifiedSince;                try {                    ifModifiedSince = req.getDateHeader(HEADER_IFMODSINCE);                } catch (IllegalArgumentException iae) {                    ifModifiedSince = -1;                }                if (ifModifiedSince < (lastModified / 1000 * 1000)) {                    maybeSetLastModified(resp, lastModified);                    doGet(req, resp);                } else {                    resp.setStatus(HttpServletResponse.SC_NOT_MODIFIED);                }            }        } 

doGet 调用之前做了什么?

else if (method.equals(METHOD_HEAD)) {            long lastModified = getLastModified(req);            maybeSetLastModified(resp, lastModified);            doHead(req, resp);        } 

在调用doHead 函数之前会获取HttpServletRequest 的修改时间,然后设置最后最后修改时间。

0 0