一个让java程序员有杀人的冲动的Xerces冲突问题
History
- Xerces是Java生态圈使用最广泛的XML解析器,基本上所有的类库和框架都会在一定程度上使用它(即使没有直接引用,也有可能间接引用)
- Xerces在官网中发布的包是没有标注版本的,2.11.0的jar命名为xercesImpl.jar而不是xercesImpl-2.11.0.jar.
- Xerces不使用Maven,不会上传官方的release版本到Maven的中央仓库。
- Xerces以前是发布一个jar包,但是之后分成两个jar包发布,一个包含API的xml-apis.jar和另一个包含其实现的xercesImpl.jar。许多老点儿的Maven Pom仍然依赖xerces.jar。更早的时候Xerces发布一个xmlParserAPIs.jar,也有些很古老很古老的pom会依赖这个jar。
- 发布到Maven仓库的一些jar经常会依赖版本不同的xml-apis和xercesImpl。举例来说,依赖的xml-apis的版本可能是1.3.03而依赖的xercesImpl版本可能就是2.8.0,即使两个包都是来自
Xerces 2.8.0。因为人们使用xml-apis.jar只想使用它某个版本的特定的API。 - 更麻烦的是,JRE中JAXP(Java API for XML Processing)的Reference implementation(参考实现?)使用的XML解析器就是用的这个鸟Xerces。实现类被重新打包进了com.sun.,从而导致直接引用这些类很危险,因为他们在某些JRE中可能不会包含。然而,Xerces中并不是所有的方法都通过java.和javax.*的API暴露。举例来说,就没有实现Xerces序列化的API。
- 基本上所有的servlet容器(JBoss, Jetty, Glassfish, Tomcat, ====),都包含一份或多份Xerces在他们的/lib包下。
问题
Maven解决jar包冲突
正是由于以上的一个或几个问题,许多组织会在他们的pom中重新构建自己的Xerces。当你的工程比较小而且你在用maven中央仓库的时候,这没什么问题。但是当你用Artifactory或者Nexus代理你的多个仓库时(JBoss的,Hibernate的,==),可能就出现问题了。
举例来说,A组织可能以如下方式依赖xml-apis:
<groupId>org.apache.xerces</groupId>
<artifactId>xml-apis</artifactId>
<version>2.9.1</version>
而B组织可能以如下方式依赖同样的jar包:
<groupId>xml-apis</groupId>
<artifactId>xml-apis</artifactId>
<version>1.3.04</version>
尽管B的jar版本比A的jar版本低,但是maven并不知道他们俩是同一个artifact,因为两个jar的groupId不同,那么,最后maven解决版本的冲突而是把两个jar同时引入项目。如下图:
类加载器Hell
上面提到的,JRE会在JAXP RI中包含Xerces。当你把maven依赖的所有的Xerces都标记成<exclusion>或者<provided>虽然看起来没什么问题,但是你依赖的第三方代码可能和你使用的JDK中的JAXP中Xerces版本不兼容。除此之外,你还要应付servlet容器中的包含的Xerces。这给了你几个选择:
- 删除servlet中的Xerces,然后祈祷你的容器可以在JAXP提供的版本上运行。
- 保留servlet中的那个版本,然后祈祷你的应用框架可以在servlet提供的Xerces版本上正常运行。
- 如果最后你的产品有那么一个或者两个没解决的版本冲突(如果你的应用很大的话,这是很容易出现的情况),你很快就会发现你正处于类加载器地狱(ClassLoader Hell),疑惑类加载器到底他妈的挑了那个版本在运行?在window或者linux上会不会挑同一个版本(很有可能不会)。
解决方案?
我们尝试把所有的Xerces的maven依赖标记成 或者,但是由于这鸟货的别名太多了(xml-apis, xerces, xercesImpl, xmlParserAPIs,====),这有时候并无卵用。另外,我们依赖的第三方包或者框架很可能不会跑在JAXP的版本或者servlet容器提供的Xerces版本上。
到底怎么解决?
目前他们的解决方案如下:
可以尝试使用maven enforcer插件中的banned dependency。这个rule可以让你禁止所有你不喜欢的别名,而且只会加入你喜欢的。
一个让java程序员有杀人的冲动的Xerces冲突问题的更多相关文章
- [转载]一个标准java程序员的进阶过程
第一阶段:Java程序员 技术名称 内 容 说明 Java语法基础 基本语法.数组.类.继承.多态.抽象类.接口.object对象.常用类(Math\Arrarys\S ...
- 面试挂了阿里却拿到网易offer,一个三年Java程序员的面试总结!
前言 15年毕业到现在有三年多了,最近去面试了阿里集团(菜鸟网络,蚂蚁金服),网易,滴滴,点我达,最终收到点我达,网易offer,蚂蚁金服二面挂掉,菜鸟网络一个月了还在流程中... 最终有幸去了网易. ...
- 正式工作的前奏——一个Java程序员的实习总结(1)
不知不觉,到深圳实习已经三个礼拜了.跟在暑假的三个半月实习不一样,这次收获更多,感受更好,算是摆脱了那次实习给我带来的阴影(这个会放到以后才说). 在知乎上,有这么一个问题,你现在最想跟刚工作时的你说 ...
- 做为一个Java程序员,你需要哪些傍身的技能?
最近总有些断断续续的思考,想想从我入行以来,我到底学会了什么,做成过什么,以后要做什么,如何提升自己······· 工作3年了,常听人说3年,5年,10年是程序员的坎,每过一个都会有新的想法,新的改变 ...
- 如何成为一个优秀的java程序员
Java程序员有许多应遵循的守则或最佳实践方式.本文概述了每个开发者最应该遵循的10条守则或戒律,如果不遵循它们,将会导致灾难性后果. 1. 为代码添加注释(Add comments to your ...
- 一个10年Java程序员的年终总结,献给还在迷茫中的你
我越来越担心我作为一个Java程序员的未来. 恍然间,发现自己在这个行业里已经摸爬滚打将近10年了,原以为自己就凭已有的项目经验和工作经历怎么着也应该算得上是一个业内比较资历的人士了,但是今年在换工作 ...
- 0~5年一个Java程序员的晋升之路
在程序界流行着一种默认的说法叫“黄金5年”,也就是一个程序员从入职的时候算起,前五年的选择直接影响着整个职业生涯中的职业发展方向和薪资走向,如何走好这5年,彻底从一个刚入行的菜鸟蜕变成可以以不变应万变 ...
- 一个3年Java程序员的坎与选择
前言 LZ 15年本科毕业,不知不觉3年过去了,去年底裸辞回到成都来发展,年后开始找工作,面试了几家公司,现在整理整理做个总结,也方便规划下一个3到5年以及和广大想要进阶的Java程序员同胞们共勉. ...
- 对于长沙互联网发展,一个外来两年Java程序员的所见所感所愿
惟楚有材,于斯为盛 本文有感于2019长沙互联网求职招聘大会,内容比较多,但都是我自己的一些所见.所感和所愿. 2019年3月的最后一天,参加2019长沙互联网求职招聘大会,看到了很多的招聘企业,也看 ...
- (转)java程序员进入名企需要掌握哪些,立一个flag
想要成为合格的Java程序员或工程师到底需要具备哪些专业技能,在面试之前到底需要准备哪些东西呢?面试时面试官想了解你的什么专业技能,以下都是一个合格Java软件工程师所要具备的. 一.专业技能 熟练的 ...
随机推荐
- 1. 常用的一些系统性能排查linux命令
目录 一.CPU 1.1 top命令--CPU性能 1.2 负载 -- CPU 任务排队情况 1.3 vmstat -- CPU 繁忙程度 二.内存 2.1 top命令 三.IO 3.1 iostat ...
- SV OOP-1
内容 面向对象编程 面向对象的基本概念 对象没有办法直接操作,需要通过handle(指向对象的指针)进行操作 面向对象的基本术语 面向对象的优势 类的定义 实例化对象 new() - 产生具体对象,开 ...
- 【C/C++】输出文件的相对路径
FILE 在有些编译器上会输出带路径的文件名,删除路径可使用函数 strrchr #include <string.h> #include <stdio.h> #define ...
- 【OpenVINO】基于 OpenVINO C# API 部署 RT-DETR 模型
RT-DETR是在DETR模型基础上进行改进的,一种基于 DETR 架构的实时端到端检测器,它通过使用一系列新的技术和算法,实现了更高效的训练和推理,在前文我们发表了<基于 OpenVINO ...
- JVM大页内存的学习与使用
JVM大页内存的学习与使用 原理和背景 操作系统是计算机的重要组成部分. 现代的操作系统一般都采用 段页式内存管理. 段一般是为了管理和权限 页主要是为了虚拟内存和物理内存的映射. 分页管理可以让物理 ...
- [转帖]SQL Server 中如何移动tempdb到新的位置
https://www.cnblogs.com/OpenCoder/p/10322904.html 操作步骤:1.检查tempdb的逻辑名字和它的存在位置.可以使用下面语句: SELECT name, ...
- [转帖]OceanBase 中租户管理
https://zhuanlan.zhihu.com/p/464504887 概述 租户的概念类似于传统数据库的数据库实例.租户也叫实例,拥有一定的资源能力(如CPU.内存和空间).租户下可以建立数据 ...
- HTTPD 搭建正向代理 使无网络访问权限的服务器能够访问互联网服务的快捷办法
背景 公司有保密要求比较高,数据安全要求比较高的企业客户,要求核心业务服务器部允许直接访问互联网,但是因为我们有一些OCR识别以及发票查验等的场景需要连接云端的服务才可以正常使用, 所以这里面就存在安 ...
- 依据HTML标准再探Javascript事件循环及其与浏览器渲染的关系
Javascript的一些基础概念 JavaScript执行引擎在宿主环境中是单线程的,这意味着在同一时间内只能执行一个任务.在Javascript运行期间,引擎会创建和维护相应的堆(heap)和栈( ...
- echarts去掉y轴线、设置x轴线的颜色、x轴文字颜色
<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title> ...