第3章--Tomcat

Tomcat安装与运行

Tomcat:目前最常用的基于java的web应用服务器

本课程中所有的Java代码最终都需要部署到Tomcat中运行

Tomcat的配置文件是XML的

互联网公司基本上服务端程序都是跑在类Unix平台

Tomcat:源代码为Java;为开源软件

Apache Software Foundation(Apache软件基金会)出品:制作开源软件的非盈利组织;

安装:

1. 依赖JDK(源代码为Java)

2. 下载: http://tomcat.apache.org/

编译好的二进制包 apache-tomcat-version.tar.gz

解压:在目录下 tar xzvf filename

3. 配置环境变量 CATALINA_HOME

CATALINA是Tomcat的一个组件,该组件会调用用户的Java代码

配置过程:

(本机目录/Users/shenglin/Develop/apache-tomcat-8.5.9)

export CATALINA_HOME=directory     // temporarily config

4. 验证安装是否成功

启动Tomcat

类Unix平台:     $CATALINA_HOME/bin/startup.sh

或 $CATALINA_HOME/bin/catalina.sh start

使用chrome验证Tomcat是否安装成功

Tomcat的默认端口是8080

因此在chrome地址栏里输入127.0.0.1:8080(localhost:8080) 加载后显示的便是tomcat默认主界面

--> Tomcat安装成功

Tomcat的资源:

静态资源(HTML页面)

动态资源(通过代码生成页面 --> Servlet )

--> e.g.

case study:饭馆网站

创建Soymilk.html(卖豆浆页面--静态)

    1. <pre name="code" class="html"><html>
    2. <body>
    3. <h1>Soy Milk</h1>
    4. </body>
    5. </html> </pre>
    6. <pre></pre>

卖面条页面--动态:涉及Servlet(跟着做就行,之后详解)

创建WEB-INF/classes 目录

在该目录下创建com.netease包

functionality:卖面条

创建NoodleServlet.java

[java] view plain copy
    1. <pre name="code" class="html">package com.netease;
    2. import java.io.IOException;
    3. import java.io.PrintWriter;
    4. import java.util.Date;
    5. import javax.servlet.ServletException;
    6. import javax.servlet.http.HttpServlet;
    7. import javax.servlet.http.HttpServletRequest;
    8. import javax.servlet.http.HttpServletResponse;
    9. public class NoodleServlet extends HttpServlet {
    10. protected void doGet(HttpServletRequest request, HttpServletResponse
    11. response) throws ServletException, IOException {
    12. PrintWriter writer = response.getWriter();
    13. String vegetable = request.getParameter("vegetable");
    14. if(vegetable == null) {
    15. vegetable = "Tomato";
    16. }
    17. writer.println("<html><body>");
    18. writer.println("<h1> Noodle with " + vegetable + "</h1>");
    19. writer.println("</body></html>");
    20. }
    21. }</pre>
    22. <pre></pre>

在WEB-INF下创建配置文件web.xml

[html] view plain copy
    1. <?xml version="1.0" encoding="UTF-8"?>
    2. <web-app version="3.0">
    3. <display-name>Restaurant</display-name>
    4. <servlet>
    5. <servlet-name>noodles</servlet-name>
    6. <servlet-class>
    7. com.netease.NoodleServlet
    8. </servlet-class>
    9. </servlet>
    10. <servlet-mapping>
    11. <servlet-name>noodles</servlet-name>
    12. <url-pattern>/noodles</url-pattern>
    13. </servlet-mapping>
    14. </web-app>

创建完成,开始编译class NoodleServlet.java (记得开启Tomcat)

javac -cp $CATALINA_HOME/lib/servlet-api.jar NoodleServlet.java

找到apache-tomcat的目录--webapps,将restaurant放入webapps文件夹中

hierarchy:

在chrome里尝试访问restaurant

1. 豆浆页面(静态HTML)

地址栏输入:http://127.0.0.1:8080/Restaurant/Soymilk.html

2. 面条页面(动态Java)

地址栏输入:http://127.0.0.1:8080/Restaurant/noodles

(default)

what if: http://127.0.0.1:8080/Restaurant/noodles?vegetable=Pear

Works as well!

关闭Tomcat

$CATALINA_HOME/bin/shutdown.sh

$CATALINA_HOME/bin/catalina.sh stop

验证Tomcat是否关闭

Chrome中输入上述地址,This site can't be reached.

Tomcat的组成,架构与配置部署

Tomcat的组成

bin/   ---   可执行文件(如startup.sh, shutdown.sh)

由于Tomcat为Java程序,启动时该怎么加入参数呢?

JVM启动参数配置 --> 通过配置环境变量JAVA_OPTS的方式:

常用参数:

-server   告诉JVM该应用为服务器应用,使JVM自动做一些优化

-Xms512m   调整JVM中初始堆内存大小

-Xmx512m   调整JVM中最大堆内存大小

e.g.

之后正常启动Tomcat即可 startup.sh

conf/   ---   配置文件

重要的配置文件 server.xml

<Server>
<Service> (可有多个)
<Connector><pre name="code" class="html"></pre><pre name="code"
class="html"><span> </span>(可有多个)用于接受用户请求</pre><pre
name="code" class="html">
</Connector>
<Engine> 一个Service只能用有一个Engine,用于处理Connector接收到的请求
<Host> (可有多个)虚拟主机
<Context></pre><pre name="code" class="html"><span>
</span>(可有多个)一个Context其实就是一个Web应用
</Connext>
</Host>
</Engine>
</Service>
</Server></pre>
<pre></pre>
将Context之外包裹着的一层一层称为Container(容器)
<p></p>
<p>对应的组件实现:</p>
<pre></pre>
<pre></pre>  

Connector -- 实现组件为Coyote(实现多种Connector,默认为BIO Connector (阻塞式))

Container -- 具体实现的组件为Catalina(之前的配置里也指的是这个)

Tomcat组件是如何完成web请求处理的?

浏览器 --- Connector (从socket上读取数据,并解析数据) --> Container

浏览器 <--- Connector --- Container (根据Connector传来的数据做决定,生成对应的具体响应)

浏览器发一个请求,请求被Connector处理(进行socket操作,从socket读取数据,对请求进行解析)

解析后的请求内容被Container (Catalina)处理,做出对应响应,响应通过Connector传递给浏览器

(Connector:完成网络相关处理

Container:执行Web应用的代码)

Connector参数配置:

port:端口号

address:配置Connector所监听的网络请求的地址(实际上很多服务器是有不止一个IP的,默认会在所有地址上监听)

protocol:默认HTTP/1.1

connectionTimeout:客户端连接超时时间(ms)(若客户端不关闭连接也不发送请求(此时服务器端资源被占))

acceptCount:系统繁忙时 (无空闲线程存在),新的请求需要排队,配置队列的最大值 (默认为100)。若队长超过100,则请求会被拒绝。

maxConnections:connector能支持的同时最大连接数 (线程池中线程的数量) (达到最大值时将没有空闲线程处理新请求)

(弹性) 线程池:如果来一条请求就创建一个线程,事后销毁,会很耗时。所以,事先创建一定数目的线程,当有任务时,从池中取出,用完后再放回池内

最小空闲线程数:minSpareThreads(当没有任务时,等待任务的线程数,保证有请求时最快处理)

最大线程数:maxThreads

e.g.

服务器端开发NB: 改动configuration文件之前的备份

conf目录下: cp server.xml server.xml.bak  // back up

修改server.xml文件中的conf(需重启Tomcat才会生效)

线程池:

可在server.xml中将port改为8181,将minSpareThreads和maxThreads改为1

在Connector中加入executor="tomcatThreadPool"

(btw, it is acceptable to set minSpareThreads and maxThreads inside Connector directly)

重启Tomcat后效果(使用curl发送请求(和使用chrome的效果是一样的))

若同时有两个终端发出请求,则第二个终端需要排队等待服务器回应(因为maxThreads=1)

lib/   ---   Tomcat的依赖库

logs/   ---   默认存放日志的文件夹

日志的作用:记录Tomcat的运行情况(用于问题定位和调试)

日志分类:

系统运行日志:Tomcat的运行信息和状态

应用日志:用户程序的日志,servlet课程中讲解

访问日志:记录HTTP请求访问 (Access Log)

如何配置访问日志:

server.xml

directory:存放日志的目录

prefix:日志文件名前缀

suffix:日志文件名后缀

fileDateFormat="yyyy-MM-dd.HH."   时间戳格式(默认yyyy-MM-dd.)

rotatable="true"  将日志文件切割(依据fileDateFormat指定的时间戳切割)

pattern:日志格式

%r:请求行的内容

%s:status codeHTTP响应的状态码

%m:method

%a:client ip

%t:time

%b:the number of bytes sent

%{User-Agent}i :user agent

,etc.

输出的log文件 e.g.

temp/   ---   临时文件夹(web应用执行时产生的临时文件)

work/   ---   供web应用使用(一般用来放置Tomcat运行过程中产生的一些文件)

webapps/   ---   默认的应用部署目录

如何在Tomcat中部署Web应用

手动部署:将web应用拷贝到webapps/目录下

常用部署:将web应用做成一个应用包(War包),方便共享。

e.g.

总结

Tomcat的安装

Tomcat的启动与停止

Tomcat的目录结构

Tomcat的配置文件

server.xml与Tomcat的架构

Tomcat的常见配置项

Connector的配置

线程池的配置

日志的配置

部署Web应用

Tomcat请求处理过程跟踪

打开并调试server

停留在acceptSocket处

向server发送请求

curl -X POST 'http://localhost:8080/server-example/user/specify?userName=server&userPassword=123'

server端向前执行

processSocket()

SocketWrapper();

execute(new SocketProcessor());  // another thread (request handling)

SocketProcessor()

request.getRequestProcessor();

getInputBuffer().parseRequestLine():开始解析请求行(找method名,找url,找协议等)

getInputBuffer().parseHeaders():开始解析请求头(while loop - key_value pairs)

prepareRequest():处理部分请求解析--准备工作

adapter.service(request, repsonse):派发请求

CoyoteAdapter:

匹配url至对应servlet

servlet中具体的service:connector.getService().getContainer().getPipeline().getFirst().invoke(request, response);

得到具体method=req.getMethod(); doPost(req, resp);

UserServlet.process(request, response); // 用户代码

userName,userPassword...

返回一个html页面

request.finishRequest(); response.finishResponse();

request.recycle(); response.recycle();

What is next?

手动部署很麻烦 --> Maven来管理Java Web开发过程

Tomcat单元测验:http://www.cnblogs.com/windJcoder/p/5387987.html

Tomcat单元作业:https://my.oschina.net/hava/blog/735565

Java开发工程师(Web方向) - 01.Java Web开发入门 - 第3章.Tomcat的更多相关文章

  1. Java开发工程师(Web方向) - 01.Java Web开发入门 - 第6章.蜂巢

    第6章--蜂巢 蜂巢简介 网站开发完,就需要测试.部署.在服务器上运行. 网易蜂巢: 采用Docker容器化技术的云计算平台 https://c.163.com 容器管理:容器可被视作为云主机的服务器 ...

  2. Java开发工程师(Web方向) - 01.Java Web开发入门 - 第4章.Maven

    第4章--Maven Maven实战 Java Web应用的部署: 手动式: 编译:javac -cp $CATALINA_HOME/lib/servlet-api.jar web-inf/class ...

  3. Java开发工程师(Web方向) - 01.Java Web开发入门 - 第1章.Web应用开发概述

    第1章--Web应用开发概述 Web应用开发概述 浏览器-服务器架构(BS-architecture) browser/ App    ---- request ---->    server ...

  4. Java开发工程师(Web方向) - 01.Java Web开发入门 - 第5章.Git

    第5章--Git 版本控制简介 VCS (version control system) 版本控制系统:记录若干文件的修订记录的系统,帮助查阅/回到某个历史版本 LVCS本地 CVCS集中式(Cent ...

  5. Java开发工程师(Web方向) - 01.Java Web开发入门 - 第2章.HTTP协议简介

    第2章--HTTP协议简介 HTTP协议简介 Abstract: HTTP协议的特性,HTTP请求/响应的过程,HTTP请求/响应的报文格式等知识,最后会演示如何通过Chrome提供的开发者工具,去跟 ...

  6. Java后端开发工程师是否该转大数据开发?

    撰写我对java后端开发工程师选择方向的想法,写给在java后端选择转方向的人 背景 看到一些java开发工程师,对java后端薪酬太悲观了.认为换去大数据领域就会高工资.觉得java后端没有前途.我 ...

  7. Java软件工程师面试题:Java运行时异常与一般异常有什么不一样?

    异常表示程序运行过程中可能出现的非正常状态,运行时异常表示虚拟机的通常操作中可能遇到的异常,是一种常见运行错误.java编译器要求方法必须声明抛出可能发生的非运行时异常,但是并不要求必须声明抛出未被捕 ...

  8. 【转】测试开发工程师必备软硬能力&高级测试开发工程师需要具备什么能力?

    对于测试的基本知识,可以查看软件测试相关书籍 对于在公司成为一位优秀的测试开发工程师,我觉得下面这篇文章涉及到的是我们需要的,稍微进行改动https://blog.csdn.net/sinat_210 ...

  9. Android开发工程师面试题总结。android开发面试经验

    1:Android中五种数据存储方式分别是什么?他们的特点?     (1)SharedPreference,存放较少的五种类型的数据,只能在同一个包内使用,生成XML的格式存放在设备中 (2) SQ ...

随机推荐

  1. 实例:接口并发限流RateLimiter

    需求:接口每秒最多只能相应1个请求 1.创建 全局类对象 import com.google.common.util.concurrent.RateLimiter; import org.spring ...

  2. 课时46.label标签(掌握)

    我们点击QQ注册页面,发现了一个问题,当我们点击密码两个字的时候,输入框聚焦了,而点击确认密码的时候,输入框也聚焦了,而我们上节课做的页面,这么点击,并不聚焦 1.默认情况下文字和输入框是没有关联关系 ...

  3. http1.X与2.0

    HTTP HTTP 1.X HTTP是建立在TCP协议上的,HTTP协议的瓶颈及优化都是基于TCP协议本身的特性. TCP建立连接时有三次握手 会有1.5RTT的延迟,为了避免每次请求都经历握手待来的 ...

  4. window下安装composer

    1.什么是composer 一个智能的下载工具.比如说我的项目要安装yii框架,而yii是依赖于其他东西的,仅仅安装yii是不够的,这样会导致我的项目也不能正常运行:怎么办呢,我们可以一个一个手动的将 ...

  5. C++分享笔记:扑克牌的洗牌发牌游戏设计

    笔者在大学二年级期间,做过的一次C++程序设计:扑克牌的洗牌发牌游戏.具体内容是:除去大王和小王,将52张扑克牌洗牌,并发出5张牌.然后判断这5张牌中有几张相同大小的牌,是否是一条链,有几个同花等. ...

  6. Jquery中绑定事件与普通事件的区别

    (“#panel”).bind(“click”,function(){ 与$(“#panel”).click(function(){ 有什么区别 ? 绑定可以同时加多个事件 如:$(“#panel”) ...

  7. Hibernate 事务不回滚

    问题:               这几天在做开发时,发现事务不回滚了,Service是用AOP加的事务,数据库是MySql, 表全部是InnoDB:   方法回滚是采用spring的手动回滚:   ...

  8. Eclipse易卡死

    在用eclipse编辑项目的时候,经常卡死,经过查询知道原来是我的JDK和eclipse版本对应的不好,我们都知道,eclipse的环境需要配置. 当时情况是这样的 2.容易出现卡死或者如图所示的情况 ...

  9. python学习——函数进阶

    首先来看下面这个函数. def func(x,y): bigger = x if x > y else y return bigger ret = func(10,20) print(ret) ...

  10. DOM中的事件傳播機制

    要講到事件傳播機制之前,首先要瞭解的是 什麼是事件? 事件,發生在靜態頁面與動態行為之間的交互行為.是JavaScript 和 HTML的交互是通过事件实现的.比如,按鈕的點擊,鼠標的滑過,鍵盤的輸入 ...