Servlet

作者: 刚子来简书啦 | 来源:发表于2020-09-30 13:42 被阅读0次

Servlet规范为JavaWeb应用制定了对象模型,在这个对象模型中,不仅Servlet是对象,而且容器为它提供的各种功能也都是Java对象。

  • 请求对象(ServletRequest和HttpServletRequest):Servlet从该对象中获取来自客户端的请求信息。
  • 响应对象(ServletResponse和HttpServletResponse):Servlet通过该对象来生成响应结果。
  • Servlet配置对象(ServletConfig):当容器初始化一个Servlet对象时,会向Servlet提供一个ServerConfig对象,Servlet通过该对象来获取初始化参数信息以及ServletContext对象。
  • Servlet上下文(ServletContext):Servlet通过该对象来访问容器为当前Web应用提供的各种资源。
public class DispatcherServlet extends HttpServlet {
    @Override
    public void service(ServletRequest req, ServletResponse res) throws ServletException, IOException {
        String name = req.getParameter("name");
        req.setAttribute("NAME", name);

        ServletContext context = getServletContext();
        RequestDispatcher dispatcher = context.getRequestDispatcher("/index.jsp");
        dispatcher.forward(req, res);
    }
}

Servlet API 的核心是javax.servlet.Servlet接口,所有的Servlet类都必须实现这一接口。在Servlet接口中定义了5个方法,其中有3个方法都由Servlet容器来调用,容器会在Servlet的生命周期的不同阶段调用特定的方法。

  • init(ServletConfig config) 方法:负责初始化Servlet对象。容器在创建好Servlet对象后,就会调用该方法。
  • service(ServletRequest req, ServletResponse res) 方法:负责响应客户的请求,为客户提供相应的服务。当容器接收到客户端要求访问特定Servlet对象的请求时,就会调用该Servlet对象的service()方法。
  • destroy() 方法:负责释放Servlet对象占用的资源。当Servlet对象结束生命周期时,容器会调用此方法。

JavaWeb应用的生命周期由Servlet容器来控制,而Servlet作为JavaWeb应用的最核心的组件,其生命周期也由Servlet容器来控制。Servlet的生命周期可以分为3个阶段:初始化阶段、运行时阶段和销毁阶段,分别会调用Servlet的init、service和destroy方法。

Servlet接口还定义了两个返回Servlet的相关信息的方法。

  • getServletConfig():返回一个ServletConfig对象,在该对象中包含了Servlet的初始化参数信息。
  • getServletInfo():返回一个字符串,在该字符串中包含了Servlet的创建者、版本和版权等信息。
public interface Servlet {
    void init(ServletConfig config) throws ServletException;

    ServletConfig getServletConfig();

    void service(ServletRequest request, ServletResponse response) throws ServletException, IOException;

    String getServletInfo();

    void destroy();
}

Servlet容器在启动一个Web应用时,会为它创建唯一的ServletContext对象。当Servlet容器终止一个Web应用时,就会销毁它的ServletContext对象。由此可见,ServletContext对象与Web应用具有同样的生命周期。由于ServletContext对象可以被Web应用中的所有组件共享,因此可以利用ServletContext对象来存取Web应用范围内的共享数据。

在ServletContext接口中常用的用于存取共享数据的方法包括:

  • setAttribute(String name, Object object):向Web应用范围内存入共享数据。
  • getAttribute(String name):根据参数给定的属性名,从Web应用范围内删除匹配的共享数据。
  • removeAttribute(String name):根据参数给定的属性名,返回Web应用范围内匹配的共享数据。

在Servlet API中由一个ServletContextListener接口,它能够监听ServletContext对象的生命周期,实际上就是监听Web应用的生命周期。在Servlet容器启动或终止Web应用时,会触发ServletContextEvent事件,该事件由ServletContextListener来处理。在ServletContextListener接口中定义了处理ServletContextEvent事件的两个方法:

  • contextInitialized(ServletContextEvent sce):当Servlet容器启动Web应用时调用该方法。在调用完该方法之后,容器再对Filter初始化,并且对那些在Web引用启动时就需要被初始化的Servlet进行初始化。
  • contextDestroyed(ServletContextEvent sce):当Servlet容器终止Web应用时调用该方法。在调用该方法之前,容器会先销毁所有的Servlet和Filter过滤器。
public interface ServletContextListener extends EventListener {
    void contextInitialized(ServletContextEvent event);

    void contextDestroyed(ServletContextEvent event);
}

javax.servlet.RequestDispatcher接口表示请求分发器,它有两个方法:

  • forward()方法:把请求转发给目标组件。
  • include()方法:包含目标组件的相应结果。
public interface RequestDispatcher {
    void forward(ServletRequest request, ServletResponse response) throws ServletException, IOException;

    void include(ServletRequest request, ServletResponse response) throws ServletException, IOException;
}

Servlet容器为了保证能同时响应多个客户的要求访问同一个Servlet的HTTP请求,通常会为每个请求分配一个工作线程,这些工作线程并发执行同一个Servlet对象的service()方法。因此,在Servlet中需要注意局部变量和实例变量的作用范围;需要使用实例变量的地方,注意通过锁机制来处理潜在并发问题。

JSP

JSP是Java Server Page的缩写,它是Servlet的扩展,其作用是简化网站创建过程和维护动态网站。

JSP指令(在 “<%@” 和 “%>” 内)用来设置和整个JSP网页相关的属性,如网页的编码方式和脚本语言等。

<%@ 指令名 属性="值" %>
# page 和 include 两个指令
<%@ page 属性1="值1" 属性2="值2" %>
<%@ include file="被包含组件的绝对URL或相对URL" %>
<%@ taglib prefix="标签库别名" uri="标签库uri" %>
  • page指令可以指定所使用的编程语言、与JSP对应的Servlet所实现的接口、所扩展的类及导入的软件包等。
  • include指令用来包含其他文件的内容,被包含的文件可以是JSP文件或HTML文件。
  • tablib指令用来定义一个标签库以及其自定义标签的前缀。

除了include指令,还可以使用include标签来包含其他文件:

<jsp:include page="被包含组件的绝对URL或相对URL"  />

JSP声明(在 “<%!” 和 “%>” 内)用于声明与JSP对应的Servlet类的成员变量和方法。每个声明变量只在当前JSP文件中有效。

<%! declaration;[declaration;]... %>

在JSP文件中,可以在 “<%” 和 “%>” 标记间直接嵌入任何有效的Java程序代码,这种嵌入的程序片段称为Scriptlet。如果在page指令中没有指定method属性,那么这些程序片段默认为与JSP对应的Servlet类的service()方法中的代码块。

Java表达式的标记为 “<%=” 和 “%>”。如果在JSP文件的模板文件中使用该标记,那么它能把表达式的值输出到网页上。表达式中的int和float类型的值都自动转换成字符串再进行输出。

JSP可以不做任何变量声明,就直接通过固定的引用变量来引用一些隐含对象。

隐含对象的引用变量 隐含对象的类型
request javax.servlet.HttpServletRequest
response javax.servlet.HttpServletResponse
pageContext javax.servlet.jsp.PageContext
application javax.servlet.ServletContext
out javax.servlet.jsp.JspWriter
config javax.servlet.ServletConfig
page java.lang.Object(相当于Java中的this关键字)
session javax.servlet.http.HttpSession
exception java.lang.Exception

JSP和Servlet一样,也能进行请求转发,转发的目标组件可以是HTML文件、JSP文件或者Servlet。

<jsp:forward page="转发的目标组件的绝对URL或相对URL" />

HttpSession

在Web开发领域,会话机制是用于跟踪客户状态的普遍解决方案。会话指的是在一段时间内,单个客户与Web应用的一连串相关的交互过程。在一个会话中,客户可能会多次请求访问Web应用的同一个网页,也有可能请求访问同一个Web应用中的多个网页。

会话并不是由HTTP协议制定的,而是服务端通过Cookie存储一个Session ID来实现的。使用JSP、PHP或ASP开发的Web应用都可以运用会话机制。

Servlet规范制定了基于Java的会话的具体运作机制。在 Servlet API 中定义了代表会话的 javax.servlet.http.HttpSession 接口,Servlet容器必须实现这一接口。当一个会话开始时,Servlet容器将创建一个HttpSession对象,在该对象中可以存放表示客户状态的信息。Servlet容器为每个HttpSession对象分配一个唯一标识符,称为 Session ID。

方法 描述
getId() 返回 Session ID
invalidate 销毁当前的会话,Servlet容器会释放HttpSession对象占用的资源
setAttribute(String name, Object value) 将一对name/value属性保存在HttpSession中
getAttribute(String name) 根据name参数返回保存在HttpSession对象中的属性值
getAttributeNames() 以数组的方式返回HttpSession对象中所有的属性名
removeAttribute(String name) 从HttpSession对象中删除name参数的指定属性
isNew() 判断是否是新创建的会话
setMaxInactiveInterval(int interval) 设定一个会话可以处于不活动状态的最长时间,以秒为单位。如果超过这个时间,Servlet容器会自动销毁会话。如果设置为负数,表示不限制会话处于不活动状态的时间,即会话永远不会过期
getMaxInactiveInterval() 读取当前会话可以处于不活动状态的最长时间
getSevletContext() 返回会话所属的Web应用的ServletContext对象

JSP默认情况下是支持会话的,也可以通过语句来显式地声明支持或不支持会话

<%@ page session="true" %>
<%@ page session="false" %>

Servlet容器在某些情况下会把创建的HttpSession对象从内存中转移到永久性存储设备(如文件系统或数据库)中,在需要访问HttpSession信息时再把它们加载到内存中。会话的持久化有两个好处:

  • 节约内存空间。当有一万个连接时,就会创建一万个HttpSession对象,如果一直放在内存中,将是极大的消耗。因此可以把处于不活动状态的HttpSession对象转移到文件系统或数据库中,这样可以提供对内存资源的利用率。
  • 确保在服务器重启或单个Web应用重启后,能恢复重启前的会话。比如在购物过程中,购物车信息对象保存在HttpSession,这样当服务器突发故障后,也能恢复之前的购物车状态,提高用户体验。

在Servlet API中定义了4个用于监听会话中的各种事件的监听器接口。

  1. HttpSessionListener 接口
  2. HttpSessionAttributeListener 接口
  3. HttpSessionBindingListener 接口
  4. HttpSessionActivationListener 接口

过滤器

过滤器能够对Servlet容器传给Web组件的ServletRequest对象和ServletResponse对象进行检查和修改。过滤器本身并不生成ServletRequest对象和ServletResponse对象,它只为Web组件提供如下过滤功能:

  • 过滤器能够在Web组件被调用之前检查ServletRequest对象,修改请求头和请求正文的内容,或者对请求进行预处理操作。
  • 过滤器能够在Web组件被调用之后检查ServletResponse对象,修改响应头和响应正文。

过滤器负责过滤的Web组件可以是Servlet、JSP或HTML文件。所有自定义的过滤器类都必须实现 javax.servlet.Filter 接口。

public interface Filter {
    void init(FilterConfig config) throws ServletException;

    void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException;

    void destroy();
}

相关文章

  • servlet 笔记

    servlet servlet 声明周期 Servlet 的线程安全 Servlet 获取配置信息 Servlet...

  • Servlet

    Servlet介绍 Servlet开发步骤 创建Servlet 配置Servlet 配置Servlet中设置初始化...

  • 深入理解Servlet技术

    1. 什么是servlet servlet Servlet是javax.servlet.Servlet包中定义的一...

  • Servlet与Jsp(1)

    Servlet 实现原理Servlet接口使Servlet容器能将Servlet类载入内存,并在Servlet实例...

  • web.xml不同版本之间头信息的区别

    一、Servlet 2.3 二、Servlet 2.4 三、Servlet 2.5 四、Servlet 3.0 五...

  • Servlet入门

    Servlet简介 Servlet(Servlet Applet)是Java Servlet的简称,称为小服务程序...

  • Servlet 实例

    Servlet 实例 Servlet 是服务 HTTP 请求并实现 javax.servlet.Servlet 接...

  • Java Servlet API

    Servlet 支持的版本 Servlet 3.0 新特性详解 Servlet 3.0 新特性概述Servlet ...

  • 简单认识Servlet

    Servlet与JSP的关系 初识Servlet Servlet层级关系 顶层Servlet接口 GenericS...

  • 2019-10-14 SpringMVC与Servlet接口 S

    SpringMVC与Servlet接口 Servlet接口规范 Servlet 接口 定义servlet接口规范i...

网友评论

      本文标题:Servlet

      本文链接:https://www.haomeiwen.com/subject/lstjmhtx.html