第一个Servlet

1、什么是Servlet

先看看官方的解释

A servlet is a small Java program that runs within a Web server. Servlets receive and respond to requests from Web clients, usually across HTTP, the HyperText Transfer Protocol.

       也就是,Servlet是运行在WEB服务器上的一段java程序,它的作用是接收WEB客户端的请求并作出响应。
      事实上,Servlet就是JDK中的一个接口。接口是什么?接口就是规范,是统一的标准。而Servlet接口为WEB开发人员制定了一个统一的规范,通常用于扩展WEB服务器的功能。狭义上来说,Servlet指的便是Servlet接口,但从广义上说,Servlet包含Servlet接口及其它的实现类,下面所述皆是指广义上的Servlet。

2、为什么需要Servlet

      一般思考这种问题,我会反其道而行之,即假设在不使用某某某的情况下,要实现某种功能该怎么去做。《HeadFirst Servlets&JSP》中就提出这样一个问题:如何在WEB客户端或者是浏览器上实时地显示当前的时间?
      答:WEB服务器应用只提供静态页面,不擅长处理动态即时页面和数据。要完成上述功能,我们需要一个辅助应用,要求这个应用能与WEB服务器进行通信,并且可以生成非静态的即时页面,至此我们的Servlet应运而生,主要功能在于交互式地浏览和修改数据,用来增强WEB服务器的功能。
      其实CGI程序也可以完成对应的功能,至于为什么不使用CGI程序,可以参考CGI和Servlet的对比

3、Servlet初体验

       现在我们来编写一个简单的Servlet,解决我们提出的问题!首先需要创建一个处理获取当前时间这个请求的Servlet,如下:
这里写图片描述
       但是这样就可以了吗?NO NO NO!就代码来看,PrintDateTimeServlet就是一个简单的java类,继承了HttpSevlet,用来打印当前时间,但是这样的一个类就能完成上述的功能?相信我,这样并不能,它连最基本的main方法都没有。
      那么Servlet是怎么初始化的?答案是Servlet容器,最常见的Servlet容器就是Tomcat。由Servlet容器统一管理Servlet,提供底层的通信支持。所谓通信指的就是客户端和服务端的通信,在Tomcat中,由Socket编程实现。
      Servlet容器帮你完成了这么多功能,但前提是你需要将对应Servlet注册在Servlet容器中,它才能管理对应的Servlet。怎么去注册呢?有两种方法

1) 在web.xml文件中进行配置

这里写图片描述
      可以看到,在注册Servlet时,有两个地方需要配置,一个是<servlet>,另一个是<servlet-Mapping>,这两个一个是配置Servlet,一个是配置其映射信息 。其中<servlet>中的<servlet-name>可以随意指定,但是必须要和<servlet-mapping>中的<servlet-name>保持一致。下面的<servlet-class>是该Servlet类的全路径,即包名+类名(package + class),在上面的例子中,PrintDateTimeServlet是放在src的controller包下的,所以配置的便是controller.PrintDateTimeServlet。在<servlet-mapping>中,<servlet-name>和<servlet>标签中的<servlet-name>保持一致,<url-pattern>用来配置映射的URL路径,表示匹配的动作。
      当客户端发出请求的时候,服务器会根据请求的URL信息,获取该请求的动作,即<url-pattern>属性,根据该属性从<servlet-mapping>中找到对应的<servlet-name>,继而根据<servlet-name>找到对应的Servlet实体类进行请求处理。所以,任意两个不同的Servlet不能具有相同的<url-pattern>,否则会导致请求动作匹配到多个Servlet,Servlet容器不知如何分发,引发 org.apache.catalina.LifecycleException异常。

2) 使用@WebServlet注解

       在Servlet3.0之后的版本,提供了@WebServlet注解,使用该注解也可以完成注册。 比如要注册上述的PrintDateTimeServlet,那么这样来做:
这里写图片描述
在要注册的Servlet上使用@WebServlet注解,其中的urlPatterns属性相当与web.xml中配置的url-pattern属性。以下是@WebServlet注解的实现:
这里写图片描述
其中有几个重要的属性,分别是:

  • name :代表当前Servlet的名称,该名称必须是独一无二的,这个参数会被保存在ServletConfig类中,相当于web.xml中配置的Servlet-name属性。
  • value :该Servlet响应的URL Pattern,注意到该属性是String[]形式的,所以可以配置多个URL Pattern,即一个Servlet可以响应多个URL Pattern。
  • urlPatterns : 作用等同于value。
  • loadOnStartUp : 代表该Servlet初始化的时机,如果该值是正整数或者0,表示在应用启动的时候就会加载这个servlet,该值越小,加载的优先级越高;如果该值是负整数或者没有指定时,表示该servlet在使用之前才会被加载。
  • initParams :表示该Servlet的初始化参数,这些参数配置也会被封装到ServletConfig类中,相当于web.xml中init-param的配置。

上面多次提到ServletConfig类,顾名思义,它是一个配置类,每个Servlet都会关联一个ServletConfig,封装了一些必要的配置信息,如servlet-name,init-param等。下面是ServletConfig类的实现:
这里写图片描述
使用getServletName()方法可以获取在web.xml中所配置的servlet-name属性值或者是在@WebServlet注解中声明的name属性值,同样使用getInitParameter()可以获取在web.xml中所配置的所配置的init-param属性值。

4、调试输出

      代码编写完成之后在服务器上面部署该项目( Servlet的运行环境设置可参考:http://www.runoob.com/servlet/servlet-environment-setup.html),继而在浏览器请求http:127.0.0.1:8080/printTime,就会得到具体的响应结果,如下所示:这里写图片描述

参考资料:
http://xmlns.jcp.org/xml/ns/javaee
https://www.oracle.com/

猜你喜欢

转载自blog.csdn.net/wt_better/article/details/80023814