您的位置:首页 > 编程语言 > Java开发

JavaEE 学习整理笔记: Servlet 介绍

2015-11-10 11:16 489 查看

Servlet

=============

Servlet是一种托管于Servlet容器的Web组件,可以动态生成内容。Web客户端使用请求/响应模式与Servlet交互。

Servlet容器负责Servlet的声明周期,接受请求与发送响应,并执行这一过程中所需要的编码/解码。

响应处理的过程是由Servlet完成的,Servlet容器只是负责发送Servlet处理后的响应。

WebServlet

Servlet 类是使用@WebServlet注解并继承javax.servlet.http.HttpServlet类的POJO类。例如:代码段一

@WebServlet(urlPatterns={"/demo", "/example"},
initParams={ @webInitParam(name="servlet", value="Demo") } )
public class FirstServlet extends javax.servlet.http.HttpServlet {

protect void doGET(HttpServletRequest request, HttpServletResponse response){
// do something...
}

// doPost...
// doDelete...
// ...
}


HttpServlet接口为每个Http请求:GET、POST、PUT、DELETE、HEAD、OPTIONS和TRACE的处理,都提供了一个do***的方法。通常情况下,我们只需要关心GET和POST的请求处理。如果项目采用RESTful风格的话,可能会额外的关注别的处理方法。

- HttpServletRequest 捕获Web客户端的请求,并可以从中取得请求相关的信息以及客户端的信息。

- HttpServletResponse 向Web客户端返回请求处理响应,开发人员负责填充HttpServletResponse,然后Servlet容器将捕获HTTP头信息或消息体信息发送给客户端。

定制Servlet的默认行为

如代码段一中所见的,我们可以使用@WebInitParam注解来为一个Servlet指定初始化参数。同时,我们也可以通过覆盖javax.servlet.Servlet接口中的生命周期各阶段调用方法init、service和destroy等来定制Servlet的默认行为。例如:通常情况下,我们会将一个数据库连接的初始化代码放置在init方法中,然后将释放代码放置在destroy方法中。

web.xml文件

注解是Servlet2.5版本后引入的新特性,在此之前我们都是使用web.xml文件对Servlet进行配置的,当然在Servlet3.0中也是支持web.xml配置的,并且如果我们在web.xml中配置了Servlet的话,该配置将会覆盖Servlet上的注解,也即是: web.xml中配置的Servlet的值优先级高于Servlet类文件中的注解值 。web.xml配置文件示例:

<!-- Servlet 配置-->
<servlet>
<!-- 指定Servlet的名字,主要是为了之后再配置文件中配置URL映射时使用-->
<servlet-name>demo</servlet-name>
<!-- Servlet 的类全类限定名-->
<servlet-class>com.wenchain.servlet.DemoServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>demo</servlet-name>
<!-- Servlet 负责处理的映射地址-->
<url-pattern>/demo</url-pattern>
</servlet-mapping>
<!-- 一个Servlet可以匹配多个URL映射地址-->
<servlet-mapping>
<servlet-name>demo</servlet-name>
<url-pattern>/example</url-pattern>
</servlet-mapping>


在注解方式配置Servlet产生之后,web.xml就不再是必须要存在的配置文件了,但是,在某些情况下web.xml文件依然是必须要的。例如: 指定Servlet的顺序就只能在web.xml文件中配置完成

如果我们在web.xml文件中配置了metadata-complete元素并将其值设置为true,那么类中定义的注解将会被忽略。例如:

<web-app metadata-complete="true">
// ...
</web-app>


Servlet的存在形式

通常情况下,Servlet被打包在.war文件中。多个Servlet可以被打包在一起,并且共享一个Servlet上下文(Servlet Context)。Servlet上下文类ServletContext中提供了关于Servlet运行环境的详细信息,用于与容器通信。

关于ServletContext的初步认识

如何获取ServletContext

我们可以从HttpServletRequest中获得ServletContext实例:

protect void doGet(HttpServletRequest request, HttpServletResponse response){
ServletContext sc = request.getServletContext();
}


使用场景:

场景一:

我们在某些Web应用中,我们可能需要对用户进行跟踪,以方便记录用户的一些操作数据,例如购物网站。这个时我们通常使用Cookie+Session结合使用的方案。Servlet发送一个名为JSESSIONID的HTTP Cookie到客户端。为了防止该cookie被暴露给客户端脚本代码,进而导致服务器需要承担可能出现的恶意脚本攻击,这时我们需要将该cookie设置为HttpOnly的。为了实现这一方案,我们需要对Cookie进行配置,可能的代码

SessionCookieConfig scconfig = request.getServletContext().getSesssionCookieConfig();
scconfig.setHttpOnly(true);


关于session与cookie的详细讲解,在另外一篇博文中有详细介绍

场景二:

通常情况下,我们对于一个请求的处理过程,涉及到的Servlet往往不止一个。例如:Servlet A 处理完一个请求后还需要将该请求发送给另外一个Servlet B进行进一步的处理。这个时候就需要使用请求转发(forward)。我们使用RequestDispatcher来将请求转发到不同的资源(Servlet)中。

获取RequestDispatcher实例的方法有两种: HttpServletRequest.getRequestDispatcher方法和ServletContext.getRequestDispatcher方法 。这两种获取方式分别对应不同的应用场景。

@WebServlet("/example")
public class ExamlpeServlet extends HttpServlet{
protect void doGet(HttpServletRequest request, HttpServletResponse response){
// 这里demo指代的Servlet部署在与 ExampleServlet 相同的上下文中
request.getRequestDispatcher("demo").forward(request, response);
}
}


如果需要转发到不同上下文的Servlet中,就需要使用ServletContext.getContext方法获得不同的上下文的ServletContext实例,进一步从中获取RequestDispatcher实例来转发请求到对应的上下文中 。

更多的ServletContext使用及介绍在另外一篇学习笔记中进行记录。之后将转为博文上传。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: