走进JavaWeb技术世界6:Tomcat5整体架构剖析

本系列文章将整理到我在GitHub上的《Java面试指南》仓库,更多精彩内容请到个人仓库里查看html

https://github.com/h2pl/Java-...

喜欢的话麻烦点下Star哈前端

文章首发于个人我的博客:java

www.how2playlife.com

本文是微信公众号【Java技术江湖】的《走进JavaWeb技术世界》其中一篇,本文部份内容来源于网络,为了把本文主题讲得清晰透彻,也整合了不少我认为不错的技术博客内容,引用其中了一些比较好的博客文章,若有侵权,请联系做者。python

该系列博文会告诉你如何从入门到进阶,从servlet到框架,从ssm再到SpringBoot,一步步地学习JavaWeb基础知识,并上手进行实战,接着了解JavaWeb项目中常常要使用的技术和组件,包括日志组件、Maven、Junit,等等内容,以便让你更完整地了解整个JavaWeb技术体系,造成本身的知识框架。为了更好地总结和检验你的学习成果,本系列文章也会提供每一个知识点对应的面试题以及参考答案。mysql

若是对本系列文章有什么建议,或者是有什么疑问的话,也能够关注公众号【Java技术江湖】联系做者,欢迎你参与本系列博文的创做和修订。android

文末赠送8000G的Java架构师学习资料,须要的朋友能够到文末了解领取方式,资料包括Java基础、进阶、项目和架构师等免费学习资料,更有数据库、分布式、微服务等热门技术学习视频,内容丰富,兼顾原理和实践,另外也将赠送做者原创的Java学习指南、Java程序员面试指南等干货资源)
<!-- more -->git

jsp做为Servlet技术的扩展,常常会有人将jsp和Servlet搞混。本文,将为你们带来servlet和jsp的区别,但愿对你们有所帮助。程序员

servlet和jsp的区别

一、Servlet在Java代码中能够经过HttpServletResponse对象动态输出HTML内容。github

二、JSP是在静态HTML内容中嵌入Java代码,而后Java代码在被动态执行后生成HTML内容。面试

servlet和jsp各自的特色

一、Servlet虽然可以很好地组织业务逻辑代码,可是在Java源文件中,由于是经过字符串拼接的方式生成动态HTML内容,这样就容易致使代码维护困难、可读性差。

二、JSP虽然规避了Servlet在生成HTML内容方面的劣势,可是在HTML中混入大量、复杂的业务逻辑。

经过MVC双剑合璧

JSP和Servlet都有自身的适用环境,那么有没有什么办法可以让它们发挥各自的优点呢?答案是肯有的,MVC模式就可以完美解决这一问题。

MVC模式,是Model-View-Controller的简称,是软件工程中的一种软件架构模式,分为三个基本部分,分别是:模型(Model)、视图(View)和控制器(Controller):

Controller——负责转发请求,对请求进行处理

View——负责界面显示

Model——业务功能编写(例如算法实现)、数据库设计以及数据存取操做实现

在JSP/Servlet开发的软件系统中,这三个部分的描述以下所示:

229cf9ff5b1729eaf408fac56238eeb3_hd

一、Web浏览器发送HTTP请求到服务端,而后被Controller(Servlet)获取并进行处理(例如参数解析、请求转发)

二、Controller(Servlet)调用核心业务逻辑——Model部分,得到结果

三、Controller(Servlet)将逻辑处理结果交给View(JSP),动态输出HTML内容

四、动态生成的HTML内容返回到浏览器显示

MVC模式在Web开发中有很大的优点,它完美规避了JSP与Servlet各自的缺点,让Servlet只负责业务逻辑部分,而不会生成HTML代码;同时JSP中也不会充斥着大量的业务代码,这样能大提升了代码的可读性和可维护性。

JavaWeb基础知识

1、Servlet 是什么?

Java Servlet 是运行在 Web 服务器或应用服务器上的程序,它是做为来自 Web 浏览器或其余 HTTP 客户端的请求和 HTTP 服务器上的数据库或应用程序之间的中间层。

使用 Servlet,您能够收集来自网页表单的用户输入,呈现来自数据库或者其余源的记录,还能够动态建立网页。

Java Servlet 一般状况下与使用 CGI(Common Gateway Interface,公共网关接口)实现的程序能够达到殊途同归的效果。可是相比于 CGI,Servlet 有如下几点优点:

  • 一、性能明显更好。
  • 二、Servlet 在 Web 服务器的地址空间内执行。这样它就没有必要再建立一个单独的进程来处理每一个客户端请求。
  • 三、Servlet 是独立于平台的,由于它们是用 Java 编写的。
  • 四、服务器上的 Java 安全管理器执行了一系列限制,以保护服务器计算机上的资源。所以,Servlet 是可信的。
  • 五、Java 类库的所有功能对 Servlet 来讲都是可用的。它能够经过 sockets 和 RMI 机制与 applets、数据库或其余软件进行交互。

2、Servlet的生命周期

Servlet 生命周期可被定义为从建立直到毁灭的整个过程。如下是 Servlet 遵循的过程:

  • 一、Servlet 经过调用 init () 方法进行初始化。
  • 二、Servlet 调用 service() 方法来处理客户端的请求。
  • 三、Servlet 经过调用 destroy() 方法终止(结束)。
  • 四、最后,Servlet 是由 JVM 的垃圾回收器进行垃圾回收的。

init() 方法

init 方法被设计成只调用一次。它在第一次建立 Servlet 时被调用,在后续每次用户请求时再也不调用。所以,它是用于一次性初始化,就像 Applet 的 init 方法同样。

Servlet 建立于用户第一次调用对应于该 Servlet 的 URL 时,可是您也能够指定 Servlet 在服务器第一次启动时被加载。

service() 方法

service() 方法是执行实际任务的主要方法。Servlet 容器(即 Web 服务器)调用 service() 方法来处理来自客户端(浏览器)的请求,并把格式化的响应写回给客户端。

每次服务器接收到一个 Servlet 请求时,服务器会产生一个新的线程并调用服务。service() 方法检查 HTTP 请求类型(GET、POST、PUT、DELETE 等),并在适当的时候调用 doGet、doPost、doPut,doDelete 等方法。

 destroy() 方法

destroy() 方法只会被调用一次,在 Servlet 生命周期结束时被调用。destroy() 方法可让您的 Servlet 关闭数据库链接、中止后台线程、把 Cookie 列表或点击计数器写入到磁盘,并执行其余相似的清理活动。

在调用 destroy() 方法以后,servlet 对象被标记为垃圾回收。

 示例

执行后:

之后继续请求时:

可见,就绪请求时只有service()方法执行!

相关面试题

怎样理解Servlet的单实例多线程?**

不一样的用户同时对同一个业务(如注册)发出请求,那这个时候容器里产生的有是几个servlet实例呢?

答案是:只有一个servlet实例。一个servlet是在第一次被访问时加载到内存并实例化的。一样的业务请求共享一个servlet实例。不一样的业务请求通常对应不一样的servlet。

因为Servlet/JSP默认是以多线程模式执行的,因此,在编写代码时须要很是细致地考虑多线程的安全性问题。

JSP的中存在的多线程问题:

当客户端第一次请求某一个JSP文件时,服务端把该JSP编译成一个CLASS文件,并建立一个该类的实例,而后建立一个线程处理CLIENT端的请求。若是有多个客户端同时请求该JSP文件,则服务端会建立多个线程。每一个客户端请求对应一个线程。以多线程方式执行可大大下降对系统的资源需求,提升系统的并发量及响应时间。

对JSP中可能用的的变量说明以下:

实例变量: 实例变量是在堆中分配的,并被属于该实例的全部线程共享,因此不是线程安全的。

JSP系统提供的8个类变量

JSP中用到的OUT,REQUEST,RESPONSE,SESSION,CONFIG,PAGE,PAGECONXT是线程安全的(由于每一个线程对应的request,respone对象都是不同的,不存在共享问题),APPLICATION在整个系统内被使用,因此不是线程安全的。

局部变量: 局部变量在堆栈中分配,由于每一个线程都有它本身的堆栈空间,因此是线程安全的

静态类: 静态类不用被实例化,就可直接使用,也不是线程安全的

外部资源: 在程序中可能会有多个线程或进程同时操做同一个资源(如:多个线程或进程同时对一个文件进行写操做).此时也要注意同步问题.

Servlet单实例多线程机制:

Servlet采用多线程来处理多个请求同时访问。servlet依赖于一个线程池来服务请求。线程池其实是一系列的工做者线程集合。Servlet使用一个调度线程来管理工做者线程。

当容器收到一个Servlet请求,调度线程从线程池中选出一个工做者线程,将请求传递给该工做者线程,而后由该线程来执行Servlet的service方法。

当这个线程正在执行的时候,容器收到另一个请求,调度线程一样从线程池中选出另外一个工做者线程来服务新的请求,容器并不关心这个请求是否访问的是同一个Servlet.当容器同时收到对同一个Servlet的多个请求的时候,那么这个Servlet的service()方法将在多线程中并发执行。

Servlet容器默认采用单实例多线程的方式来处理请求,这样减小产生Servlet实例的开销,提高了对请求的响应时间,对于Tomcat能够在server.xml中经过<Connector>元素设置线程池中线程的数目。 

如何开发线程安全的Servlet

一、实现 SingleThreadModel 接口

该接口指定了系统如何处理对同一个Servlet的调用。若是一个Servlet被这个接口指定,那么在这个Servlet中的service方法将不会有两个线程被同时执行,固然也就不存在线程安全的问题。这种方法只要将前面的Concurrent Test类的类头定义更改成:

<pre>Public class Concurrent Test extends HttpServlet implements SingleThreadModel {
…………
} </pre>

同步对共享数据的操做

使用synchronized 关键字能保证一次只有一个线程能够访问被保护的区段

避免使用实例变量

本实例中的线程安全问题是由实例变量形成的,只要在Servlet里面的任何方法里面都不使用实例变量,那么该Servlet就是线程安全的。

1) Struts2的Action是原型,非单实例的;会对每个请求,产生一个Action的实例来处理

Struts1 Action是单实例的

mvc的controller也是如此。所以开发时要求必须是线程安全的,由于仅有Action的一个实例来处理全部的请求。单例策略限制了Struts1 Action能做的事,而且要在开发时特别当心。Action资源必须是线程安全的或同步的。

2) Struts1的Action,Spring的Ioc容器管理的bean 默认是单实例的.

Spring的Ioc容器管理的bean 默认是单实例的。

Struts2 Action对象为每个请求产生一个实例,所以没有线程安全问题。(实际上,servlet容器给每一个请求产生许多可丢弃的对象,而且不会致使性能和垃圾回收问题)。

当Spring管理Struts2的Action时,bean默认是单实例的,能够经过配置参数将其设置为原型。(scope="prototype )

5、servlet与jsp的区别

1.jsp经编译后就变成了Servlet.(JSP的本质就是Servlet,JVM只能识别java的类,不能识别JSP的代码,Web容器将JSP的代码编译成JVM可以识别的java类)

2.jsp更擅长表现于页面显示,servlet更擅长于逻辑控制.

3.Servlet中没有内置对象,内置对象都是必须经过HttpServletRequest对象,HttpServletResponse对象以及HttpServlet对象获得.Jsp是Servlet的一种简化,使用Jsp只须要完成程序员须要输出到客户端的内容,Jsp中的Java脚本如何镶嵌到一个类中,由Jsp容器完成。而Servlet则是个完整的Java类,这个类的Service方法用于生成对客户端的响应。

4.对于静态HTML标签,Servlet都必须使用页面输出流逐行输出

参考文章

https://www.w3cschool.cn/serv...
https://blog.csdn.net/qq_1978...
https://blog.csdn.net/qiuhuan...
https://blog.csdn.net/zt15732...
https://blog.csdn.net/android...

微信公众号

我的公众号:黄小斜

黄小斜是跨考软件工程的 985 硕士,自学 Java 两年,拿到了 BAT 等近十家大厂 offer,从技术小白成长为阿里工程师。

做者专一于 JAVA 后端技术栈,热衷于分享程序员干货、学习经验、求职心得和程序人生,目前黄小斜的CSDN博客有百万+访问量,知乎粉丝2W+,全网已有10W+读者。

黄小斜是一个斜杠青年,坚持学习和写做,相信终身学习的力量,但愿和更多的程序员交朋友,一块儿进步和成长!

原创电子书:
关注危险公众号【黄小斜】后回复【原创电子书】便可领取我原创的电子书《菜鸟程序员修炼手册:从技术小白到阿里巴巴Java工程师》这份电子书总结了我2年的Java学习之路,包括学习方法、技术总结、求职经验和面试技巧等内容,已经帮助不少的程序员拿到了心仪的offer!

程序员3T技术学习资源: 一些程序员学习技术的资源大礼包,关注公众号后,后台回复关键字 “资料” 便可免费无套路获取,包括Java、python、C++、大数据、机器学习、前端、移动端等方向的技术资料。

技术公众号:Java技术江湖

若是你们想要实时关注我更新的文章以及分享的干货的话,能够关注个人微信公众号【Java技术江湖】

这是一位阿里 Java 工程师的技术小站。做者黄小斜,专一 Java 相关技术:SSM、SpringBoot、MySQL、分布式、中间件、集群、Linux、网络、多线程,偶尔讲点Docker、ELK,同时也分享技术干货和学习经验,致力于Java全栈开发!

(关注公众号后回复”Java“便可领取 Java基础、进阶、项目和架构师等免费学习资料,更有数据库、分布式、微服务等热门技术学习视频,内容丰富,兼顾原理和实践,另外也将赠送做者原创的Java学习指南、Java程序员面试指南等干货资源)

Java工程师必备学习资源: 一些Java工程师经常使用学习资源,关注公众号后,后台回复关键字 “Java” 便可免费无套路获取。

个人公众号

相关文章
相关标签/搜索