什么?编译了三个版本Tomcat源码后,我才发现这个bug

Tomcat源码阅读与深度解析 本文还有配套的精品资源,点击获取 简介:Tomcat是Java Web开发中广泛使用的开源应用服务器,负责处理Servlet和JSP。深入阅读Tomcat源码对开发者优化应用程序性能、问题排查和定制化开发十分有益。本文将深入探讨Tomcat的核心组件、工作原理及源码分析的关键点,帮助开发者全面理解其内部运作机制。 1. Tomcat开源特性及社区贡献 在现代... 阅读详情

背景

一产品是基于多模块开发的 SpringBoot 项目,发布时导出多个 war 包部署在同一个 Tomcat 。模块有五六个,发布时最大的问题就是每个包都很大,主要是各个模块的 WEB-INF/lib 下包含大量相同 jar ,因此有必要将公共包摘出来放到 Tomcat 的共享目录下。

然而,在捣鼓了两天后,我对 Tomcat 的多应用部署时共享公共包的能力产生了怀疑。理论上,同一个 Tomcat 下部署多个应用时,可以将所有共享 jar 放在 shared/lib 目录下,然后配置 shared.loader 就可以了。

实践的时候,抽取了公共包后,多个 war 部署时始终报错, WEB-INF/lib 下明明有对应的 Spring 框架包,还是报 Caused by: java.lang.NoClassDefFoundError: org/springframework/beans/factory/FactoryBean 异常,反复测试,还是无法确定哪些包应该作为公共包。

所以,决定从源头来搞明白这个类加载过程,在编译的 Tomcat 版本下断点跟踪一下到底是怎么回事儿。第一件事儿,先编译 Tomcat 源码。

Tomcat 源码编译

Tomcat 源码导入 IDEA 的过程比较简单,步骤为:

1.下载 ANT 工具,最新版本为 1.10.9,配置环境变量 ANT_HOME:

什么?编译了三个版本Tomcat源码后,我才发现这个bug

 

2.下载 tomcat 源码,根据操作系统选择 zip 或者 tar.gz 文件;

3.进入源码目录,使用 ant 命令编译源码;

什么?编译了三个版本Tomcat源码后,我才发现这个bug

 

此操作耗时较长,耐心等待编译完成:

什么?编译了三个版本Tomcat源码后,我才发现这个bug

 

4. 创建一个 catalina-home 目录,将 output/build 目录下的所有文件拷贝到 catalina-home 目录下,将其作为 Tomcat 的工作目录:

什么?编译了三个版本Tomcat源码后,我才发现这个bug

 

5.进入源码目录,创建 pom.xml 添加依赖:

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
 
    <modelVersion>4.0.0</modelVersion>
    <groupId>org.apache.tomcat</groupId>
    <artifactId>Tomcat8.0</artifactId>
    <name>Tomcat8.0</name>
    <version>8.0</version>
 
    <build>
        <finalName>Tomcat8.0</finalName>
        <sourceDirectory>java</sourceDirectory>
        <!--<testSourceDirectory>test</testSourceDirectory>-->
        <resources>
            <resource>
                <directory>java</directory>
            </resource>
        </resources>
        <!--<testResources>-->
            <!--<testResource>-->
                <!--<directory>test</directory>-->
            <!--</testResource>-->
        <!--</testResources>-->
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>
                <version>3.1</version>
                <configuration>
                    <encoding>UTF-8</encoding>
                    <source>1.7</source>
                    <target>1.7</target>
                </configuration>
            </plugin>
        </plugins>
    </build>
 
    <dependencies>
        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>4.12</version>
            <scope>test</scope>
        </dependency>
        <dependency>
            <groupId>org.easymock</groupId>
            <artifactId>easymock</artifactId>
            <version>3.4</version>
        </dependency>
        <dependency>
            <groupId>ant</groupId>
            <artifactId>ant</artifactId>
            <version>1.7.0</version>
        </dependency>
        <dependency>
            <groupId>wsdl4j</groupId>
            <artifactId>wsdl4j</artifactId>
            <version>1.6.2</version>
        </dependency>
        <dependency>
            <groupId>javax.xml</groupId>
            <artifactId>jaxrpc</artifactId>
            <version>1.1</version>
        </dependency>
        <dependency>
            <groupId>org.eclipse.jdt.core.compiler</groupId>
            <artifactId>ecj</artifactId>
            <version>4.5.1</version>
        </dependency>
    </dependencies>
</project>

6.导入 IDEA 源码,配置启动参数 -Dcatalina.home="F:\Study\TomcateStudy\2021Tomcat\catalina-home" 。

总的来说,编译源码流程比较简单,但最开始因为随便选择了最新版本,导致无法启动,这可能是官网版本发布时的缺陷吧,反正换个版本就没有问题。

选错版本的问题

首先,在 MAC 操作系统下,随便选择了最新版本 tomcat8.5.63 的 tar.gz 版本,下载后,编译时报错。先报 @Version@ 校验错误:

Error:osgi: [Tomcat8.5] Invalid value for Bundle-Version, @VERSION@ does not

修改为一个特定值后,又报下面的错误:

什么?编译了三个版本Tomcat源码后,我才发现这个bug

 

最初怀疑是 IDEA 配置问题,于是又在 windows 操作系统下,还是用最新版本的 tomcat8.5.63 的 zip 版本下载源码,配置参数如下:

什么?编译了三个版本Tomcat源码后,我才发现这个bug

 

奇怪的是,它能够编译通过、正常运行:

什么?编译了三个版本Tomcat源码后,我才发现这个bug

 

结论:Tomcat8.5.63 版本的 tar.gz 源码的 jdbc-pool 模块打包生成的 MANIFEST.MF 文件有问题,编译源码的时候应该避免使用该版本。本来以为哪个版本都一样,就随便选了最新版本,结果就踩坑了。

最后,更换为 Tomcat8.5.59 版本,MAC 下就能正确启动了。

什么?编译了三个版本Tomcat源码后,我才发现这个bug

 

控制台乱码问题

最后解决控制台乱码问题,主要涉及到两个类,它们使用了默认编码导致输出乱码的。具体操作如下,详细参考:

第一步,修改 org.apache.tomcat.util.res.StringManager 类的 getString(final String key, final Object... args) 方法,获得 value 后再转码:

try{
     value = new String(value.getBytes("ISO-8859-1"),"UTF-8");
 }catch (Exception e ){
     e.printStackTrace();
 }

第二步,修改 org.apache.jasper.compiler.Localizer 类的 getMessage(String errCode) 方法,在返回之前进行转码:

 try{
     errMsg = new String(errMsg.getBytes("ISO-8859-1"),"UTF-8");
 }catch (Exception e ){
     e.printStackTrace();
 }

再重启 Tomcat 应用,输出信息就正常了:

什么?编译了三个版本Tomcat源码后,我才发现这个bug

 

启示录

到现在为止,还没找到答案的几个问题是:

  1. 多应用共享 lib 的原则是什么?
  2. 哪些包应该放在 shared/lib 下?【我是将纯第三方 jar ,无相关依赖的】
  3. 为什么只 WEB-INF/lib 下只保留某个应用自身的 jar 而且包含 SpringBoot 的 starter 依赖,还是报类异常?
告别Sourceforge安装器!手把手教你下载MinGW-w64离线包并配置环境变量(Windows 10/11) 本文详细介绍了如何在Windows 10/11系统上通过下载MinGW-w64离线包并配置环境变量,完全绕过Sourceforge安装器的问题。从选择正确的版本、解压到本地目录,到设置系统环境变量和验证编译环境,手把手指导开发者快速搭建稳定的GCC编译环境,解决常见的安装困扰。 阅读详情

相关推荐

STM32嵌入式开发实战:如何用miniLZO压缩算法节省70%存储空间(附完整工程)

本文详细介绍了如何在STM32嵌入式开发中使用miniLZO无损压缩算法实现高达70%的存储空间节省。通过对比分析不同轻量级算法,重点讲解miniLZO的内存优化配置、分块压缩策略和完整工程实现,帮助开发者有效解决嵌入式系统中的存储瓶颈问题。

ss78901的博客 881

Error:osgi: [tomcat7] Invalid value for Bundle-Version, @VERSION@ does not match [0-9]{1,9}(\.[0-9]{

编译tomcat源码时报错: 将apache-tomcat-8.5.23-src\modules\jdbc-pool\resources\MANIFEST.MF中的Bundle-Version: @VERSION@,把Bundle-Version: 8即可

远行的博客 1881

Unity轻量级框架QFramework:四层架构与命令事件驱动的实战指南

在Unity游戏开发中,软件架构是确保项目可维护性和可扩展性的核心。通过分层架构(如MVC、DDD)和事件驱动设计,开发者能够有效管理代码复杂度,实现模块间的解耦与高效通信。QFramework作为一个轻量级框架,精准地运用了这些原理,通过严格定义的四层架构(表现层、系统层、数据层、工具层)和命令/事件通信规则,为中小型项目提供了“约束下的自由”。其核心价值在于以极简的代码(不足1000行)强制实施清晰的职责分离,如使用命令模式集中管理状态变更,并通过事件驱动实现响应式更新。这种设计特别适用于解决项目规模扩

weixin_42521032的博客 262

编译了三个版本 Tomcat 源码后,我可能发现了一个 bug

本周对 Tomcat 的多应用部署时共享公共包的能力产生了怀疑,理论上,同一个 Tomcat 下部署多个应用时,可以将所有共享 jar 放在 `shared/lib` 目录下,然后配置 `shared.loader` 就可以了。 实际实践的时候,多个 SpringBoot 导出的 war 部署在 Tomcat 下时,抽取了公共包后,启动时 `WEB-INF/lib` 下明明有对应的 Spring 框架包,还是报 `Caused by: java.lang.NoClassDefFoundError: or

本博客纯属个人网络笔记,如对阁下有用,甚喜;否则,关掉即可,不喜勿喷。专心写代码,不做键盘侠! 520

DOA估计算法从原理到仿真——CBF、Capon、MUSIC算法

从原理出发理解并实现经典的DOA估计算法

m0_55845774的博客 1万+

Windows11上CUDA 12.3配PyTorch踩坑记:一条官网命令救了我的GPU加速

本文详细介绍了在Windows 11上配置CUDA 12.3与PyTorch的完整指南,包括环境准备、安装要点、兼容性解决方案和性能验证。通过官方推荐的conda命令和实用技巧,帮助开发者解决常见问题,实现高效的GPU加速,提升深度学习开发效率。

weixin_42528974的博客 109

TomCat安装配置与多版本冲突处理

Tomcat安装与配置,冲突处理、改端口

qq_31412321的博客 2374

PWM调节DCDC参数计算原理

SOC芯片的核电压、GPU电压、NPU电压、GPU电压等,都会根据性能和实际应用场景来进行电压和频率的调整。 即动态电压频率调整DVFS(Dynamic Voltage and Frequency scaling),优化性能和功耗。

电子绿洲的博客 3167

IDEA导入Tomcat源码的踩坑日常

最近在向中级开发工程师的路上迈进,所以特意学习下IDEA的使用以及Tomcat源码(主要是最近在Tomcat会话保持上,sessionId的产生及如何给前台产生cookie上有所歧义,特此研究下) 废话不多说 上硬货,IDEA导入tomcat源码时 会碰到各种恶样的坑,特此记录下,一方面是记录,一方面看到的同学一个提醒 tomcat源码下载地址,每个版本的源码都有,分为分为tar.gz 以及zi...

qq_33135813的博客 3085

【脑电信号处理与特征提取】P2-夏晓磊:脑电的神经起源与测量

ElectroEncephaloGraphyTherefore, EEG produces a graphed representation of the electrical activity occurring in a person’s brain.(把一个人的大脑中的电活动画出来)脑电头皮表面记录到的大脑活动产生的电信号(微伏)。(记录位置:硬脑膜/大脑皮层表面- ECoG,神经元群- LFP与MUR/MUA:活动位置:心电、眼电、肌电等)脑电图电压随时间变化的波形图。

m0_51474171的博客 1896

GEE APP:基于Sentinel-2遥感影像的植被指数(NDVI)和水体指数(NDWI)可视化应用

本文介绍了利用Google Earth Engine(GEE)平台处理Sentinel-2卫星数据的方法,重点讲解NDVI(归一化植被指数)和NDWI(归一化水体指数)的计算与应用。内容包括环境准备、数据加载与处理、指数计算原理、可视化方法以及实际应用案例。教程详细展示了如何定义研究区域、加载影像数据、进行指数运算,并生成专业统计报告和图例。文章还提供了常见问题解答和最佳实践建议,为生态环境监测、农业评估和水资源管理等场景提供了实用工具。通过JavaScript代码示例,读者可以快速掌握GEE平台的遥感影像

此星光明博客 273

tomcat源码导入idea

对于一个开发者来说,要想提高自己,学习tomcat源码还是很有必要的,但是初学者导入tomcat会遇到一些问题,本文记载着自己 导入tomcat8.0到idea踩过得一些坑。 准备工作 Tomcat源码地址:http://mirror.bit.edu.cn/apache/tomcat/tomcat-8/v8.0.53/src/apache-tomcat-8.0.53-src.zip IDEA工具:...

weixin_33969116的博客 467

【漏洞复现】用友U9 UMWebService.asmx 任意文件读取漏洞

用友U9存在任意文件读取漏洞,未授权的攻击者可以通过该漏洞读取服务器任意文件,造成敏感信息泄露。

qq_67810151的博客 620

搭建Tomcat源码阅读环境,无bug运行调试。答应我,和我一起学习Tomcat,不要放弃!

全网最好,没有之一,无bug运行Tomcat源码。经验分享,学习总结。

你学废了吗? 4551

win10 跳过U8环境检测的IE WebControls.rar

win10 安装u8的时候 提示IE WebControls 不通过,这个工具可以欺骗u8的检查。 跳过U8环境检测的IE WebControls。提示导入失败后,重新检测通过。

Camera2Demo

在Camera2 的基础上进行封装,使得Camera2一堆初始化逻辑与Activity分离,降低耦合度,完成预览拍照并保存的操作

关于apache-tomcat-9.0.30-src编译过程中停止在ecj-4.13.jar问题的解决办法

这是源码包中的一个bug造成,打开build.properties.default,找到如下标红的行,把最后一个/去掉,重新编译。 jdt.release=R-4.13-201909161045/ # ----- Eclipse JDT, version 4.7 or later -----# # See https://cwiki.apache.org/confluence/disp...

招财猫_Martin 的专栏 691

VC中sqlite的使用

在VC中对sqlite的使用,实现数据库大批数据的快速插入,读取数据库中的数据在ListCtrl中显示

hadoop源码编译出现的bug

出现这种bug先是看ant的环境是否配置好,若是好的那么 就是因为tomcat插件没有下载完全,需要手动下载放到相应的文件夹下面。 文件夹的位置有两个。 /opt/hadoop-2.7.2-src/hadoop-common-project/hadoop-kms/downloads /opt/hadoop-2.7.2-src/hadoop-hdfs-project/hadoop-h...

qq_38140644的博客 324

霍尼韦尔SoftMaster使用说明

霍尼韦尔SoftMaster使用说明

搭建Tomcat源码阅读环境,无bug运行调试。答应我,和我一起学习Tomcat,不要放弃!(1)

现在正是金三银四的春招高潮,前阵子小编一直在搭建自己的网站,并整理了全套的**【一线互联网大厂Java核心面试题库+解析】:包括Java基础、异常、集合、并发编程、JVM、Spring全家桶、MyBatis、Redis、数据库、中间件MQ、Dubbo、Linux、Tomcat、ZooKeeper、Netty等等**网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。需要这份系统化的资料的朋友,可以添加V获取:vip1024b (备注Java)

2401_84439899的博客 1095

Tomcat源码解析

转载:http://www.blogjava.net/hlq37/archive/2011/01/20/343277.html   自己最近在学习Java Web编程,先是读了Sun公司的官方文档Java EE 5的tutorial(http://java.sun.com/javaee/5/docs/tutorial/doc/)中的关键章节,然后学了一阵Java Passion里的相关在线课程

雷雨中的双桅船 1345

Apache Tomcat 源码分析环境搭建

Apache Tomcat®软件是Java Servlet、JavaServer页面、Java 语言表达式和 Java WebSocket 技术的开源实现。Java Servlet、JavaServer页面、Java 表达式语言和 Java WebSocket 规范都是在 Java 社区进程下开发的。 Apache Tomcat 软件是在开放和参与的环境中开发的,并在 Apache 许可版本 2 ...

carl.zhao的专栏 1643

tomcat源码解析

转载:http://www.blogjava.net/hlq37/archive/2011/01/20/343277.html   自己最近在学习Java Web编程,先是读了Sun公司的官方文档Java EE 5的tutorial(http://java.sun.com/j

shuhuai007的专栏 992

Tomcat源码编译学习

这方面很多牛人已经有过经验总结,百度一下你就知道。一下推荐一篇蛮好但不完美的文章http://hi.baidu.com/%C4%C8%CE%F7%D0%A1%D1%FD/blog/item/bc4dedad05c7550c4b36d68c.html 一些注意事项:1 JDK一定要是tiger,而不能是mustang。2 关于那个eclipse jdt的链接可以自己上网搜一个

Gentle_bird的专栏 693

Myeclipse启动tomcat,程序不报错,但是项目启动不起来

今天遇上一个bug,打开myeclpse的工作空间,显示报错,重新更新maven,启动tomcat发现项目起不来。查询了一系列的资料之后,发现可能是java build path 和deployment assembly有一方面有问题了 java build path :myeclipse中使用tomcat使用启动web项目的流程是 java build path编译项目源代码生成的class文件放到buildpath的设置路径中 web deployment assembly:根据web deploy

weixin_37863088的博客 2137

旧版本web项目,如何用新JDK和Tomcat在Ecplise运行。

原本是用JDK 1.6和Tomcat 6运行,现在想升级到JDK1.8和Tomcat 9运行。在本地搭建环境时候设置了很久,遇到了这个问题。因为设置了JDK1.8来运行,但是web项目里面配置了JDK1.6来运行。原本只设置运行时候加载指定版本的JDK就行,没想到编译也需要选同样的版本(第3点)。选Java -> 电鸡Installed JREs -> 选择JDK 1.8版本。翻译过来就是编译的版本跟项目JDK设置的版本不一样,导致源码兼容有问题。彻底的解决办法:设置一样的JDK版本,包括编译和运行。

weixin_41001025的博客 338

tomcat7.0支持什么版本的jdk_这一次我动了JDK代码

为什么要阅读源码在求职找工作中,无论你是菜鸟还是老鸟,都逃不过面试官对Java底层源码的拷问。我在公司面试求职者,首先问的就是对Java源码的掌握程度,io底层源码、Collection实现类源码,其中最多的那是面试恶魔HashMap的源码。以前很不明白为什么对于底层写死的东西要弄清楚,后来发现能够在短时间内评判一个人实力水平的方式,也就只有看他对源码的熟悉程度。日常学习、写业务、工作中...

weixin_39688451的博客 2780

IntelliJ+Tomcat部署draw.io开发环境:从源码编译到消除乱码的全流程指南

本文提供了一份详细的指南,指导开发者使用IntelliJ IDEA和Apache Tomcat从源码部署draw.io开发环境。文章重点解决了在Windows或Linux系统中常见的编码乱码问题,并涵盖了从环境准备、项目导入、依赖配置到最终构建WAR包并成功运行的全流程,旨在为深度定制和二次开发draw.io打下坚实基础。

weixin_28839549的博客 99

Planetj 开源包读取压缩文件BUG分析过程

第一弹,Planetj 开源包读取压缩文件BUG。   BUG描述:   在Tomcat 7 以上的服务器上运行,访问ODIN系统登录页面速度很慢。      2. BUG定位过程(猜测与验证):   &是否是后端tomcat 转发到页面慢 ----&gt;&gt;&gt; 经验证,首页面后端处理很少,参考URL访问日志进入与返回处理都正常。   &推测是前端脚本在Chrome上运行...

javachenxi的专栏 278
上一篇: 系统的数据一致性到底是在说什么?我到今天才算真明白了
下一篇: SpringBoot接口幂等性实现的4种方案,真的够用了
爱玛士
博客等级 码龄7年 720粉丝 253原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值