一、什么是Servlet
Servlet(Server Applet)是Java Servlet的简称,称为小服务程序或服务连接器,用Java编写的服务器端程序,主要功能在于交互式地浏览和修改数据,生成动态Web内容。
狭义的Servlet是指Java语言实现的一个接口,广义的Servlet是指任何实现了这个Servlet接口的类,一般情况下,人们将Servlet理解为后者。Servlet运行于支持Java的应用服务器中。从原理上讲,Servlet可以响应任何类型的请求,但绝大多数情况下Servlet只用来扩展基于HTTP协议的Web服务器。
——百科
简单说就是服务器上一个处理请求的程序,也可以认为是一切服务器端后台开发的起点。
浏览器-服务器的模式有着如下的流程:
用户通过浏览器访问一个地址 -> 浏览器产生http请求发送到服务器 -> 服务器容器程序接收请求并启动一个线程并调用一个Servlet来处理请求。剩下的工作就由Servlet完成。
二、Servlet的功能
Servlet及相应的类都存在于javax.Servlet包和javax.Servlet.http包中。
Servlet包括5个方法:
/** * Servlet容器在初始化Servlet时调用,因此只调用一次 * 其中参数ServletConfig config 来自于Servlet容器 */ public void init(ServletConfig config) throws ServletException;
/** * 获取Servlet的配置信息,用于后续操作 */ public ServletConfig getServletConfig();
/** * 核心方法,每当有请求时,Servlet容器都会调用Servlet的Service方法来进行处理
* 两个参数是由Servlet容器封装的请求和响应对象 */ public void service(ServletRequest req, ServletResponse res) throws ServletException, IOException;
/** * 获取Servlet信息,如作者之类的,没什么用,通用实现时直接返回“” */ public String getServletInfo();
/** * Servlet容器移除Servlet时调用,通常发生在容器关闭时
* 可以用来释放连接或者存储数据到数据库等操作 */ public void destroy();
三、Servlet实现——HttpServlet
Servlet自身只是一个接口,其中使用的各种ServletConfig、ServletRequest等都是接口,如果要直接使用Servlet进行操作需要许多操作。而在javax.Servlet.http包中,给出了Servlet对应的http版本的实现。其中最主要的就是HttpServlet类。
GenericServlet直接实现了Servlet接口,但是并没有添加太多的内容,只实现了一些获取配置信息的方法。而HttpServlet主要实现了Service方法。
/** * 根据http方法的不同,调用不同的方法进行处理 */ protected void service(HttpServletRequest req,HttpServletResponse resp) throws ServletException, IOException { String method = req.getMethod();
//GET方法,做了上次访问内容是否修改的判断 if (method.equals(METHOD_GET)) { long lastModified = getLastModified(req); if (lastModified == -1) { doGet(req, resp); } else { long ifModifiedSince = req.getDateHeader(HEADER_IFMODSINCE); if (ifModifiedSince < (lastModified / 1000 * 1000)) { // If the servlet mod time is later, call doGet() // Round down to the nearest second for a proper compare // A ifModifiedSince of -1 will always be less maybeSetLastModified(resp, lastModified); doGet(req, resp); } else { resp.setStatus(HttpServletResponse.SC_NOT_MODIFIED); } } //HEAD方法 } else if (method.equals(METHOD_HEAD)) { long lastModified = getLastModified(req); maybeSetLastModified(resp, lastModified); doHead(req, resp); //POST方法 } else if (method.equals(METHOD_POST)) { doPost(req, resp); //PUT方法 } else if (method.equals(METHOD_PUT)) { doPut(req, resp); //DELETE方法 } else if (method.equals(METHOD_DELETE)) { doDelete(req, resp); //OPTIONS方法 } else if (method.equals(METHOD_OPTIONS)) { doOptions(req,resp); //TRACE方法 } 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); } }
因此,在开发自己的Servlet时,可以只覆写相应的doxxx方法,无需自己处理service。而HttpServlet中提供的doxxx方法默认实现的是提示错误信息,因此,在覆写时不需使用super.doxxx()方法。
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { String protocol = req.getProtocol(); String msg = lStrings.getString("http.method_get_not_supported"); if (protocol.endsWith("1.1")) { resp.sendError(HttpServletResponse.SC_METHOD_NOT_ALLOWED, msg); } else { resp.sendError(HttpServletResponse.SC_BAD_REQUEST, msg); } }
四、其他设置
除了编写自己的Servlet继承HttpServlet之外,开发时还需要在web.xml中向Servlet容器注册自己写的Servlet。
<servlet> <servlet-name>MyServlet </servlet-name> //这里是servlet 的名字,自己定义的 <servlet-class>Servlet </servlet-class> //这里是servlet的位置。包名.类名 </servlet> <servlet-mapping> <servlet-name>MyServlet </servlet-name> //这里跟 上面的;servlet-name 必须一样 <url-pattern>/abc </url-pattern> //这里 在地址输入访问的时候输入的,自己定义 </servlet-mapping>
Servlet的主体部分就是这些,此外还有配置类,上下文、cookie、session等内容。(待续)