JavaWeb Servlet
Posted Mr.Aaron
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了JavaWeb Servlet相关的知识,希望对你有一定的参考价值。
1. Servlet介绍
1.1. 百度百科
Servlet是在服务器上运行的小程序。这个词是在Java applet的环境中创造的,Java applet是一种当作单独文件跟网页一起发送的小程序,它通常用于在客户端运行,结果得到为用户进行运算或者根据用户互作用定位图形等服务。
服务器上需要一些程序,常常是根据用户输入访问数据库的程序。这些通常是使用公共网关接口(CGI(Common Gateway Interface))应用程序完成的。然而,在服务器上运行Java,这种程序可使用Java编程语言实现。在通信量大的服务器上,Javaservlet的优点在于它们的执行速度更快于CGI程序。各个用户请求被激活成单个程序中的一个线程,而无需创建单独的进程,这意味着服务器端处理请求的系统开销将明显降低。
1.2. 维基百科
Servlet(Server Applet),全称Java Servlet,未有中文译文。是用Java编写的服务器端程序。其主要功能在于交互式地浏览和修改数据,生成动态Web内容。狭义的Servlet是指Java语言实现的一个接口,广义的Servlet是指任何实现了这个Servlet接口的类,一般情况下,人们将Servlet理解为后者。
Servlet运行于支持Java的应用服务器中。从实现上讲,Servlet可以响应任何类型的请求,但绝大多数情况下Servlet只用来扩展基于HTTP协议的Web服务器。
最早支持Servlet标准的是JavaSoft的Java Web Server。此后,一些其它的基于Java的Web服务器开始支持标准的Servlet。
1.3. 什么是Servlet
Servlet是JavaEE三大组件之一,是使用Java语言编写服务器端的程序,主要用来处理Web应用程序中的请求-响应。Servlet并没有main之类的执行方法,当用户访问服务器的时候,Tomcat是通过调用Servlet的某些方法来完成整个处理过程的。Servlet是运行在Tomcat服务器提供的Servlet容器中的,所以Servlet是不用程序指定调用的。
1.4. Tomcat与JavaEE
JavaEE的版本与Tomcat服务器的版本是存在一种对应关系的,在开发Web应用程序的时候,需要注意对应版本关系,不然可能引起Web程序报错。
JavaEE与Tomcat服务器的版本对应关系如下表:
Tomcat服务器版本 |
Servlet\\JSP版本 |
JavaEE版本 |
Java运行环境 |
Tomcat 4.1 |
Servlet 2.3\\JSP 1.2 |
JavaEE 1.3 |
JDK 1.3 |
Tomcat 5.0 |
Servlet 2.4\\JSP 2.0 |
JavaEE 1.4 |
JDK 1.4 |
Tomcat 5.5\\6.0 |
Servlet 2.5\\JSP 2.1 |
JavaEE 5.0 |
JDK 5.0 |
Tomcat 7.0 |
Servlet 3.0\\JSP 2.2 |
JavaEE 6.0 |
JDK 6.0 |
如果使用Tomcat服务器的高版本时,可以向下兼容Servlet\\JSP、JavaEE及Java运行环境的版本。目前我们学习研究Servlet,主要是以2.5版本为主,所以使用的JavaEE版本可以是JavaEE 5.0版本。
在Tomcat服务器与JavaEE中,分别提供了有关Servlet的帮助文档信息。如果在Tomcat服务器中查看Servlet的相关信息在Tomcat服务器的安装目录中,webapps目录中的docs目录中名为servletapi文件夹中查看。如果在JavaEE中查看有关Servlet的相关信息,需要下载对应JavaEE版本的API帮助文档。
需要注意的是,Servlet 3.0版本在Tomcat服务器和JavaEE都提供帮助文档,但Servlet 2.5版本只有在JavaEE提供了帮助文档,Tomcat并没有提供Servlet 2.5版本的帮助文档。
2. 编写一个Servlet
2.1. 通过Eclipse创建Servlet
开发工具Eclipse或MyEclipse本身提供了创建Servlet的功能,下面我们首先利用开发工具来创建一个Servlet,具体步骤如下:
- 首先,我们创建一个Web工程。
- 在Web工程的src目录下,鼠标右键点击“New”选项,选择“Servlet”选项。
- 弹出创建Servlet的界面窗口,具体内容如下:
- 输入Servlet的包名、名称及相关方法后,点击“Next”按钮进行下一步操作。
该界面是配置Servlet在web.xml文件中的相关信息,具体内容如下:
-
- Servlet/JSP Class Name:Servlet的完整路径。
- Servlet/JSP Name:Servlet的名称。
- Servlet/JSP Mapping URL:配置Servlet拦截的路径,客户端通过该路径访问Servlet。
- File Path of web.xml:当前工程的web.xml配置文件保存路径。
- Display Name:显示名称。
- Description:描述名称。
- 配置完毕之后,点击“Finish”按钮,完成Servlet的创建工作。
创建完成之后,当前Web工程的变化是在src目录下多了一个Servlet的Java文件,在WEB-INF目录中的web.xml文件中多了Servlet相关配置信息。
创建的Servlet的Java文件内容:
public class FirstServlet extends HttpServlet { public void init() throws ServletException {} public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { response.setContentType("text/html"); PrintWriter out = response.getWriter(); out.println("<!DOCTYPE HTML >"); out.println("<HTML>"); out.println(" <HEAD><TITLE>A Servlet</TITLE></HEAD>"); out.println(" <BODY>"); out.println (" This is "+ this.getClass()+", using the GET method"); out.println(" </BODY>"); out.println("</HTML>"); out.flush(); out.close(); } public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { response.setContentType("text/html"); PrintWriter out = response.getWriter(); out.println("<!DOCTYPE HTML >"); out.println("<HTML>"); out.println(" <HEAD><TITLE>A Servlet</TITLE></HEAD>"); out.println(" <BODY>"); out.println (" This is "+ this.getClass()+", using the GET method"); out.println(" </BODY>"); out.println("</HTML>"); out.flush(); out.close(); } public void destroy() {} }
Web工程的配置文件web.xml内容:
<?xml version="1.0" encoding="UTF-8"?> <web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"> <display-name></display-name> <servlet> <description>This is the description of my J2EE component</description> <display-name>This is the display name of my J2EE component</display-name> <servlet-name>FirstServlet</servlet-name> <servlet-class>app.java.servlet.FirstServlet</servlet-class> </servlet> <servlet-mapping> <servlet-name>FirstServlet</servlet-name> <url-pattern>/servlet/FirstServlet</url-pattern> </servlet-mapping> <welcome-file-list> <welcome-file>index.jsp</welcome-file> </welcome-file-list> </web-app>
将当前Web应用程序发布到Tomcat服务器,并启动Tomcat服务器运行测试当前创建的Servlet内容。
- 通过Eclipse或MyEclipse将当前Web工程发布到Tomcat服务器,并启动Tomcat服务器。
- 打开浏览器,在地址栏中输入http://localhost:8080/08_servlet/servlet/FirstServlet,访问服务器端的Servlet内容。
2.2. 手动编写一个Servlet
通过Eclipse或MyEclipse创建Servlet虽然简单,但我们并不知道相关代码是什么含义。所以,下面我们需要研究一下生成出来的代码。
首先, 我们来研究一下创建的Servlet文件源代码,会发现如下内容:
- 是继承于HttpServlet类。
- 包含init()、doGet()、doPost()和destroy()方法。
根据上述内容,我们可以手动创建一个Servlet的Java文件,如下面的代码所示:
public class SecondServlet extends HttpServlet { @Override public void init() throws ServletException { System.out.println("这是init()方法..."); } @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { System.out.println("这是doGet()方法..."); } @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { System.out.println("这是doPost()方法..."); } @Override public void destroy() { System.out.println("这是destroy()方法..."); } }
其次,web.xml配置文件增加的内容:
<?xml version="1.0" encoding="UTF-8"?> <web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"> <display-name></display-name> <!-- servlet标签:用于配置Servlet的名称和完整路径. * servlet-name标签:用于为对应的Servlet设置名称. * servlet-class标签:用于设置对应的Servlet的完整路径. --> <servlet> <servlet-name>SecondServlet</servlet-name> <servlet-class>app.java.servlet.SecondServlet</servlet-class> </servlet> <!-- servlet-mapping标签:用于配置Servlet拦截客户端请求路径. * servlet-name标签:用于设置对应使用的Servlet名称. * url-pattern标签:用于设置客户端请求的拦截路径. * 相对路径:/servlet/FirstServlet * 绝对路径:http://localhost:8080/08_servlet/servlet/FirstServlet --> <servlet-mapping> <servlet-name>SecondServlet</servlet-name> <url-pattern>/servlet/SecondServlet</url-pattern> </servlet-mapping> <welcome-file-list> <welcome-file>index.jsp</welcome-file> </welcome-file-list> </web-app>
将当前Web应用程序发布到Tomcat服务器,并启动Tomcat服务器运行测试当前创建的Servlet内容。
- 通过Eclipse或MyEclipse将当前Web工程发布到Tomcat服务器,并启动Tomcat服务器。
- 打开浏览器,在地址栏中输入http://localhost:8080/08_servlet/servlet/SecondServlet,访问服务器端的Servlet内容。
2.3. Servlet的继承链
通过创建Servlet的Java文件中的代码内容,可以发现创建的Servlet是继承于HttpServlet类,查看JavaEE帮助文档中的HttpServlet内容。
Method Summary |
|
protected void |
doGet(HttpServletRequest req, HttpServletResponse resp) |
protected void |
doPost(HttpServletRequest req, HttpServletResponse resp) |
protected void |
service(HttpServletRequest req, HttpServletResponse resp) |
void |
service(ServletRequest req, ServletResponse res) |
通过帮助文档提供的内容,我们可以知道创建Servlet中的doGet和doPost方法是继承于HttpServlet提供的,但还有init和destroy方法没有找到。我们发现HttpServlet是继承于GenericServlet,查看JavaEE帮助文档中的GenericServlet内容。
Method Summary |
|
void |
destroy() |
void |
init() |
abstract void |
service(ServletRequest req, ServletResponse res) |
通过帮助文档提供的内容,我们可以知道init和destroy方法是源于GenericServlet。但是其实GenericServlet都实现了Servlet接口。
Method Summary |
|
void |
destroy() |
getServletConfig() |
|
getServletInfo() |
|
void |
init(ServletConfig config) |
void |
service(ServletRequest req, ServletResponse res) |
所以,init和destroy方法是Servlet接口提供的方法。通过上述的查找,我们已经很清晰的知道了Servlet的继承关系,具体如下图:
2.4. Servlet工作流程
利用Servlet完成的Web应用的实际工作流程是通过Tomcat服务器发布服务,客户端与服务器端之间的交互遵循Http协议完成的。具体工作流程如下:
- 客户端浏览器向服务器端发送请求。
- 服务器端由Tomcat服务器提供的Servlet容器解析接收到的请求。
- 通过Web应用程序的配置文件web.xml,解析到对应执行的Servlet。
- Servlet完成客户端发送的请求逻辑,并完成向客户端发送的响应内容。
- 由Tomcat服务器提供的Servlet容器向客户端浏览器进行响应。
我们也可以通过下面的图来理解Servlet具体的工作流程。
2.5. Servlet注意事项
值得注意的是Servlet内容是属于JavaEE内容,和使用JavaSE内容一样,都是需要引入JAR包的。使用Eclipse或MyEclipse创建Web应用程序的时候,会发现已经导入了JavaEE所需要的JAR包。其中javaee.jar包中包含了使用Servlet的所有内容。
但是,当把Web应用程序发布到Tomcat服务器的时候,发现对应的目录中并没有javaee.jar包。我们知道无论是编译还是运行都是需要这些JAR包的,这说明Tomcat服务器本身提供了Servlet运行所需要的环境。在Tomcat服务器的安装目录中的lib目录中可以找到servlet-api.jar包,该JAR包也提供了Servlet运行所需的环境。
我们如果想要手动编译Servlet的话,需要做以下及步:
- 在Tomcat安装目录中的webapps目录创建Web工程名称及目录结构。
- 在命令行中利用命令编译Servlet文件。
javac -classpath C:\\Tools\\apache-tomcat-7.0.55\\lib\\servlet-api.jar -d . Servlet.java
- 在对应Web工程目录的WEB-INF目录中的web.xml进行配置。
3. 深入掌握Servlet
3.1. Servlet的生命周期
一般情况下,自定义Servlet都是继承HttpServlet。但通过HttpServlet的继承链,我们知道HttpServlet是实现了Servlet接口,下面列表是Servlet接口提供的所有方法。
Method Summary |
|
void |
destroy() |
getServletConfig() |
|
getServletInfo() |
|
void |
init(ServletConfig config) |
void |
service(ServletRequest req, ServletResponse res) |
上述所有方法中,init()、service()和destroy()方法叫做Servlet的生命周期。下面我们分别讨论一下有关生命周期的三个方法:
- init()方法
- 在Servlet实例化之后,Servlet容器会调用init()方法,主要是用来完成处理客户端请求之前的初始化工作。
- init()方法在Servlet的生命周期中只被执行一次。
- service()方法
- Servlet容器调用service()方法来处理客户端发送的请求。在service()方法被调用之前,必须保证init()方法被正确执行。
- service()方法在每次客户端发送请求之后,会被执行一次。
- destroy()方法
- 当Servlet容器检测到当前Servlet实例被移除时,会调用destroy()方法,以便让Servlet实例可以释放所使用的所有资源。
- destroy()方法在Servlet的生命周期中也只被执行一次。
下面我们通过实际操作来讨论关于Servlet的生命周期是怎么样的:
- 首先,创建一个Servlet文件,具体如下。
public class LifeServlet implements Servlet { public LifeServlet(){ System.out.println("这里创建了一个Servlet实例对象..."); } public void init(ServletConfig config) throws ServletException { System.out.println("这是init()方法..."); } public void service(ServletRequest req, ServletResponse res) throws ServletException, IOException { System.out.println("这是service()方法..."); } public void destroy() { System.out.println("这是destroy()方法..."); } public ServletConfig getServletConfig() { return null; } public String getServletInfo() { return null; } }
- 在web.xml文件中,配置有关Servlet信息。
<?xml version="1.0" encoding="UTF-8"?> <web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"> <servlet> <servlet-name>LifeServlet</servlet-name> <servlet-class>com.servlet.LifeServlet</servlet-class> </servlet> <servlet-mapping> <servlet-name>LifeServlet</servlet-name> <url-pattern>/servlet/LifeServlet</url-pattern> </servlet-mapping> </web-app>
- 将Web应用程序发布到Tomcat服务器,并启动Tomcat服务器。
- 启动Tomcat服务器之后,我们可以查看Tomcat服务器启动的日志内容,并没有有关Servlet信息。
十一月 20, 2017 1:22:48 下午 org.apache.catalina.core.AprLifecycleListener init
INFO: Loaded APR based Apache Tomcat Native library 1.2.12.
十一月 20, 2017 1:22:48 下午 org.apache.catalina.core.AprLifecycleListener init
INFO: APR capabilities: IPv6 [true], sendfile [true], accept filters [false], random [true].
十一月 20, 2017 1:22:49 下午 org.apache.coyote.AbstractProtocol init
INFO: Initializing ProtocolHandler ["http-apr-8080"]
十一月 20, 2017 1:22:49 下午 org.apache.coyote.AbstractProtocol init
INFO: Initializing ProtocolHandler ["ajp-apr-8009"]
十一月 20, 2017 1:22:49 下午 org.apache.catalina.startup.Catalina load
INFO: Initialization processed in 1914 ms
十一月 20, 2017 1:22:49 下午 org.apache.catalina.core.StandardService startInternal
INFO: Starting service Catalina
十一月 20, 2017 1:22:49 下午 org.apache.catalina.core.StandardEngine startInternal
INFO: Starting Servlet Engine: Apache Tomcat/7.0.27
十一月 20, 2017 1:22:49 下午 org.apache.catalina.startup.HostConfig deployDirectory
INFO: Deploying web application directory E:\\apache-tomcat-7.0.27\\webapps\\08_servlet
十一月 20, 2017 1:22:50 下午 com.sun.faces.config.ConfigureListener contextInitialized
INFO: 初始化上下文 \'/08_servlet\' 的 Mojarra 2.0.3 (FCS b03)
十一月 20, 2017 1:22:51 下午 com.sun.faces.spi.InjectionProviderFactory createInstance
INFO: JSF1048:有 PostConstruct/PreDestroy 注释。标有这些注释的 ManagedBeans 方法将表示注释已处理。
十一月 20, 2017 1:22:51 下午 org.apache.catalina.startup.HostConfig deployDirectory
INFO: Deploying web application directory E:\\apache-tomcat-7.0.27\\webapps\\docs
十一月 20, 2017 1:22:51 下午 org.apache.catalina.startup.HostConfig deployDirectory
INFO: Deploying web application directory E:\\apache-tomcat-7.0.27\\webapps\\examples
十一月 20, 2017 1:22:51 下午 org.apache.catalina.core.ApplicationContext log
INFO: ContextListener: contextInitialized()
十一月 20, 2017 1:22:51 下午 org.apache.catalina.core.ApplicationContext log
INFO: SessionListener: contextInitialized()
十一月 20, 2017 1:22:51 下午 org.apache.catalina.core.ApplicationContext log
INFO: ContextListener: attributeAdded(\'org.apache.jasper.compiler.TldLocationsCache\', \'org.apache.jasper.compiler.TldLocationsCache@526509bf\')
十一月 20, 2017 1:22:51 下午 org.apache.catalina.startup.HostConfig deployDirectory
INFO: Deploying web application directory E:\\apache-tomcat-7.0.27\\webapps\\host-manager
十一月 20, 2017 1:22:51 下午 org.apache.catalina.startup.HostConfig deployDirectory
INFO: Deploying web application directory E:\\apache-tomcat-7.0.27\\webapps\\manager
十一月 20, 2017 1:22:51 下午 org.apache.catalina.startup.HostConfig deployDirectory
INFO: Deploying web application directory E:\\apache-tomcat-7.0.27\\webapps\\ROOT
十一月 20, 2017 1:22:52 下午 org.apache.coyote.AbstractProtocol start
INFO: Starting ProtocolHandler ["http-apr-8080"]
十一月 20, 2017 1:22:52 下午 org.apache.coyote.AbstractProtocol start
INFO: Starting ProtocolHandler ["ajp-apr-8009"]
十一月 20, 2017 1:22:52 下午 org.apache.catalina.startup.Catalina start
INFO: Server startup in 2333 ms
- 打开浏览器,在地址栏中输入http://localhost:8080/08_servlet/servlet/LifeServlet,并查看控制台信息。
- 重新刷新页面,再次发送请求,调用Servlet内容。
- 停止Tomcat服务器,并查看控制台信息。
通 以上是关于JavaWeb Servlet的主要内容,如果未能解决你的问题,请参考以下文章 JavaWeb实现用户登录注册功能实例代码(基于Servlet+JSP+JavaBean模式)