SOFA Jakarta Transformer是一个基于开源工具Eclipse Transformer的Java产物转换工具,目前主要用对Jar包从Java EE到Jakarta的转换。引用Eclipse Transformer的介绍:
The Eclipse Transformer project is part of the Eclipse Technology top-level project.
Eclipse Transformer provides tools and runtime components that transform Java binaries, such as individual class files and complete JARs and WARs, mapping changes to Java packages, type names, and related resource names.
While the initial impetus for the project was the Jakarta EE package renaming issue, the scope of the project is broader to support other renaming scenarios. For example, shading.
We operate under the Eclipse Code of Conduct to promote fairness, openness, and inclusion.
随着 Oracle 将 Java EE 交给 Eclipse 开始 Java EE 就成为了历史,取而代之的是新的 Jakarta EE 系列。对于开发者而言,最大的改变便是从 jakarta EE 9 开始, EE 相关的类的命名空间从 javax.* 迁移到了 jakarta.*。 对于这一变更,开源社区的组件也均在不同进度的进行升级适配:例如 Tomcat 从 10.x 版本开始便迁移到了 jakarta 命名空间。而 SpringBoot 3.x 版本也不再支持 Java EE 8,而是基于 Jakarta EE 9 构建,这使得我们基于 SpringBoot 3.x 开发的 SOFABoot 4.x 版本也将基于 Jakarta EE 9 构建,使用 javax 命名空间的组件需要进行 jakarta 命名空间的切换才能在 SOFABoot 4.x 环境使用。 因此,我们需要解决这一兼容性问题,使得这些 SDK 能够屏蔽 Java EE/Jakarta EE 的实现差异,低成本的同时支持两种命名空间。
传入自己要添加的自定义规则以及想要使用的场景来构造CustomRules(场景是指使用哪种默认规则配置,现在仅支持Jakarta规则以及无规则)
```java
List renameList = new ArrayList<>(Arrays.asList(“alipay-api/src/main/resources/jakarta-renames-test1.properties”, “alipay-api/src/main/resources/jakarta-renames-test2.properties”));
List textList = new ArrayList<>(Collections.singleton(“org.eclipse.transformer.jakarta/src/main/resources/org/eclipse/transformer/jakarta/jakarta-text-master.properties”));
List immediatesList = new ArrayList<>(Arrays.asList(“tr”, “javax.servlet”, “jaaaaa.servlet”, “tr”, “javax.servlet.http”, “jaaaaa.servlet.http”));
CustomRules customRules = new CustomRules.CustomRulesBuilder()
.setContainerType(ContainerType.Jakarta)
.setRenames(renameList)
.setTexts(textList)
.build();
2. 传入输入输出路径构造ApiTransformOptions
```java
ApiTransformOptions options = new ApiTransformOptions(customRules,
"/Users/someone/Documents/jars/xxx.jar",
"/Users/someone/Documents/xxx.jar");
简介
SOFA Jakarta Transformer是一个基于开源工具Eclipse Transformer的Java产物转换工具,目前主要用对Jar包从Java EE到Jakarta的转换。引用Eclipse Transformer的介绍:
其本质上就是能够通过配置好的转换规则执行对java,class,xml等文件以及JAR,WAR,ZIP等压缩包执行文本转换的工具,我们主要将其用在Java EE到Jakarta EE的转换场景中。
背景
随着 Oracle 将 Java EE 交给 Eclipse 开始 Java EE 就成为了历史,取而代之的是新的 Jakarta EE 系列。对于开发者而言,最大的改变便是从 jakarta EE 9 开始, EE 相关的类的命名空间从
javax.*迁移到了jakarta.*。对于这一变更,开源社区的组件也均在不同进度的进行升级适配:例如 Tomcat 从 10.x 版本开始便迁移到了 jakarta 命名空间。而 SpringBoot 3.x 版本也不再支持 Java EE 8,而是基于 Jakarta EE 9 构建,这使得我们基于 SpringBoot 3.x 开发的 SOFABoot 4.x 版本也将基于 Jakarta EE 9 构建,使用 javax 命名空间的组件需要进行 jakarta 命名空间的切换才能在 SOFABoot 4.x 环境使用。
因此,我们需要解决这一兼容性问题,使得这些 SDK 能够屏蔽 Java EE/Jakarta EE 的实现差异,低成本的同时支持两种命名空间。
能力
能对谁转换
能转换的对象主要分为两类:
单体类型:Class,Java,Jsp,XML,Manifest,Properties(-tf规则可以对任意类型文件都生效)
容器类型:包括目录,ZIP,JAR,WAR,RAR,EAR。会递归对下面包含的所有单体类型文件进行转换
能做什么转换
以下例子中的配置文件对于命令行,Maven插件和API均有效,命令则以命令行为例
Package重命名
作用域以及作用方式:
命令参数:-tr,–renames <配置文件路径>
例子:
jakarta-rename.properties(指定具体替换规则)
Package版本更新
作用域以及作用方式: Manifest文件,更新OSGi 属性”DynamicImport-Package”, “Export-Package”, “Import-Package”, “Subsystem-Content”, and “IBM-API-Package”中的指定package的版本。
命令参数:-tv,–versions <配置文件路径>
例子:
jakarta-versions.properties(指定每个package的版本范围)
字符串常量更新
作用域以及作用方式:
Class文件,对所有Class文件按照所给的映射做字符串常量替换(rename操作时也会对字符串常量做替换)
Java文件,同Class文件
命令参数:-td,–direct <配置文件路径>
例子:
jakarta-direct.properties(指定具体替换规则)
指定文本更新
作用域以及作用方式: 理论上只要是UTF8编码的文件就可以,对指定条件的文件进行文本替换,将所有匹配到的文本替换成指定文本(比较傻瓜,主要用于其他规则没覆盖到的文件如xml等)。采用两层properties文件来配置,第一层指定对符合条件的文件使用哪个规则文件,第二层中指定具体的替换规则
命令参数:-tf,–text <配置文件路径>
例子:
jakarta-text-master.properties(指定要对哪类文件使用哪个规则文件)
jakarta-web-xml.properties(指定具体替换规则)
指定跳过规则和编码规则
作用域以及作用方式: 所有文件都可以,可以配置某几个或某几类文件的解码格式(比如有些文件可能包含其他语言),也可以配置某几个或某几类文件在转换过程中被跳过(不执行所有转换规则)
命令参数:-ts,–selection <配置文件路径>
例子:
jakarta-selection.properties(指定具体规则)
pom.xml转换
作用域以及作用方式: 只对pom.xml文件生效,可以用来转换pom.xml的各个部分(目前根据当前的场景只支持了对module信息和dependency信息的更改,理论上可以支持pom.xml的任何部分)。还可以用来指定哪些module需要被转换(该作用当前只在Maven插件生效)
命令参数:-tm,–pom <配置文件路径>
例子:
jakarta-pom.json(指定具体规则)
注意:如果有选填的key-value项没有写出,比如一个module没有写targetGroupId,则直接会用其原始值
指定单条规则
作用域以及作用方式:作用域根据规则类型而定。该规则不是单独的一种规则,而是允许用户直接去指定单条前面所说的几种规则。前面几种转换都需要依赖于properties文件,如果在不想使用properties文件或者在properties文件外额外增加规则的话,就可以采用这种规则。
命令参数:-ti,–immediate ( tr | tv | td | tf ) key value
例子:命令行参数(一个-ti后只能跟随一条规则)
注意:目前指定单条规则只支持tr,tv,td,tf四种操作
使用
我是用户,如何使用
使用方式
当前主要有Maven插件,API和命令行三种使用方式,无论是哪种使用方式所做的转换都是上述几种类型,本质上只是接入方式不同。
API
List textList = new ArrayList<>(Collections.singleton(“org.eclipse.transformer.jakarta/src/main/resources/org/eclipse/transformer/jakarta/jakarta-text-master.properties”));
List immediatesList = new ArrayList<>(Arrays.asList(“tr”, “javax.servlet”, “jaaaaa.servlet”, “tr”, “javax.servlet.http”, “jaaaaa.servlet.http”));
CustomRules customRules = new CustomRules.CustomRulesBuilder() .setContainerType(ContainerType.Jakarta) .setRenames(renameList) .setTexts(textList) .build();
if (rc != Transformer.ResultCode.SUCCESS_RC) { logger.error(“fail to transform”); } else { logger.info(“success to transform”); }
注意:
各个命令(规则)有优先级,简单来说-ti>-tr, -tb, -td, -tf, -tr, -ts, -tm>默认规则。-tr, -tb, -td, -tf, -tr, -ts, -tm这几个指定规则配置文件的参数会覆盖掉选择的默认规则(比如jakarta规则),所以如果想保留选择的默认规则需要使用-ti来逐条追加规则(后续可以改造一下ti命令),而-ti指令所指定的规则会覆盖掉tr,tv,td,tf等指令所指定的配置文件中键值一样的规则 ```bash
假设参数如下,其中jakarta-renames-test.properties中有javax.servlet.jsp.el=xxx.servlet.jsp.el,这种情况下最后规则为c
tr jakarta-renames-test.properties -ti tr javax.servlet.jsp.el=jakarta.servlet.jsp.el ```
-tr, -tb, -td, -tf, -tr, -ts这些指令指定的规则配置文件支持绝对路径
-tr, -tb, -td, -tf, -tr, -ts这些指令都支持通过多次使用来指定多个规则配置文件,同一类规则下的多个配置文件中的规则会被合并,如果多个配置文件中出现键值相同的规则项则最后的配置文件会将前面的覆盖掉 ```bash
通过添加以下两个指令能将这两个
tr jakarta-renames-test1.properties -tr jakarta-renames-test2.properties
假设jakarta-renames-test1.properties如下
javax.activation=jakarta.activation javax.annotation.security=jakarta.annotation.security javax.batch.api.chunk=xxxxx.batch.xxx.chunk
假设jakarta-renames-test2.properties如下
javax.batch.api.chunk=jakarta.batch.api.chunk javax.batch.api.listener=jakarta.batch.api.listener
则最后的规则会变为:
javax.activation=jakarta.activation javax.annotation.security=jakarta.annotation.security javax.batch.api.chunk=jakarta.batch.api.chunk javax.batch.api.listener=jakarta.batch.api.listener
使用建议
Q:我只想做对我的Jar最简单的javax到jakarta的替换,没有要自定义的规则
A:直接指定好目标文件和输出文件的路径就ok了,不需要加任何参数
我是开发者,如何扩展
目前可扩展的主要有两个方向:
Transformer有别于其他类似工具最大的特点在于能够对构建产物如JAR包,Class文件进行文本替换,如果有其他场景需要这种能力则可以考虑Transformer。