复习-JVM何时结束

Java虚拟机的退出规则 :JVM在所有非守护线程都结束后才会退出。

  • 普通程序:main 线程执行完最后一行,main线程结束 → JVM没有其他非守护线程了 → JVM退出(平时可以写写测试代码)

  • 服务器程序:server.start() 启动了一些后台非守护线程(负责监听端口、处理请求),这些线程会一直运行,等待请求;(启动服务的场景)

所以tomcat,jetty这些都是会通过脚本启功一个非守护线程来保持服务的运行的。

来看看tomcat如何优雅的启动项目吧

复制代码
// Tomcat 的简化版启动代码
public class Bootstrap {
    public static void main(String[] args) {
        // 1. 初始化 Catalina(Tomcat的核心容器)
        Catalina catalina = new Catalina();
        
        // 2. 加载配置文件(server.xml)
        catalina.load();
        
        // 3. 启动!------没错,这里也是start()
        catalina.start();
        
        // 4. 重点来了:这里会调用await()方法
        catalina.await();
        
        // 5. 只有在收到关闭命令后,才会执行到这里
        catalina.stop();
    }
}

为什么要await一下呢?就是为了更优雅

复制代码
server.start();  // 启动后台线程处理请求
server.await();  // ★ main线程在这里等待,不会结束
// 直到收到 shutdown 命令,await() 才会返回
server.stop();   // 然后执行清理工作

不同启动方式的对比

特性 原生 HttpServer Tomcat
main线程状态 直接结束 await() 处阻塞等待
后台线程 存在,处理请求 存在,处理请求
如何停止 只能强制kill进程 可以通过shutdown命令优雅停止
控制台表现 看似"挂起"在那里 看似"挂起"在那里
关闭钩子 难以及时执行清理 可以执行清理(如保存Session)
  1. 更好的控制:main线程保持运行,可以随时响应关闭命令

  2. 优雅关闭:收到关闭命令后,可以等待正在处理的请求完成

  3. 清理资源:有机会保存Session、关闭连接池等

相关推荐
爱喝热水的呀哈喽1 小时前
openroad make各个阶段
服务器
闲云野鹤在人间3 小时前
docker 入门 | 第7章 容器监控 和 第8章 容器日志 详解
运维·docker·容器·架构·云计算
亚川楼宇自控系统数据中心厂家3 小时前
IBMS 集成如何打通数据中心的子系统数据孤
运维
蓝速科技3 小时前
桌面双屏翻译机量产调试:三类场景兼容性破局方案丨蓝速科技
运维·数据库·人工智能·科技·技术分享
见闻小天地3 小时前
脱硫脱硝塔选变频器避坑指南:四方DL500变频器使用体验分享
大数据·运维·人工智能·业界资讯
吴声子夜歌4 小时前
Shell编程实例——内务及管理任务(一)
linux·运维·shell
wdfk_prog5 小时前
ROS教程10:从 gtest 到 rostest——Unit Test、Node 集成测试、rosbag 与 rqt 验证闭环
运维·缓存·docker·容器·ros
吴声子夜歌5 小时前
Shell编程实例——高级脚本编程(一)
linux·运维·网络·shell
Huangjin007_6 小时前
【Linux 系统篇(二十一)】进程(九):进程等待 wait/waitpid、status状态参数
linux·运维·服务器
螺蛳粉 螺蛳粉6 小时前
mysql的备份与恢复
linux·运维·数据库·mysql