class 增量发包改造为 jar 包方式发布
liuian 2025-07-09 14:16 48 浏览
大纲
- class 增量发包介绍
- 项目目录结构介绍
- jar 包方式发布落地方案
class 增量发包介绍
当前项目的迭代修复都是通过 class 增量包来发版本的
将改动的代码 class 增量打包,如下图
class 发包方式优点
- class 增量发布,增量包体积较小
- 出现问题时,可以本地打log编译后,临时替换对应 class,便于调试
- 可以方便的看出本地迭代包文件变动情况 (用户不太关心)
但是也存在一些问题,开发人员维护困难,主要体现在以下几个点
- 每次编译后需要开发人员根据变动记录,手动收集本次迭代变动 class,容易出现错漏
- 本地打包后,一个 class可能会生成 n 个 class 文件 (FileToolsUI$1.class,FileToolsUI$2.class); ( 在 idea 中是看不出来的,必须在目录下才能看到) 导致增量包经常出问题...
- 经常要维护一个稳定版本的全量基线包
- 由于是 class 增量升级,误打包或重构删除的类,客户那边依旧会冗余,不利于重构; (而当前项目代码臃肿,项目亟需重构 很多java文件代码量的比较大 3k,5k,7k代码; )
于是大家商量一下想改变升级包提供方式,通过提供全量可 jar 包升级
项目目录结构介绍
项目工程结构如下
KingDomFileToolCombine
java 源代码
resources 资源目录1
source 资源目录 2
doc 文档
lib 外部依赖 jar 包存放目录由于早期项目没有使用构建工具,当初导入项目也是花了些时间;
具体可以查看 idea 导入并配置非标准maven工程
jar 包方式发布落地方案
改造后要求满足以下需求
- 当前项目 jar包形式发布
- 外部依赖单独存放在 lib目录下 (减少升级包体积)
- 配置文件单独存放在jar包的同级目录的bin目录下 (方便用户调整配置)
使用 maven 打 jar'包方案实现步骤如下
- 添加 pom.xml 使用 maven 管理依赖
- 使用 maven <systemPath>管理本地 jar 包
- 选择maven构建插件,打 jar 包
- 刷新 maven 依赖; (最好是手动删除 project structure中的依赖,然后刷新maven)
- mvn clean package 打 jar 包
- cd 到目录下 java -jar xxx.jar 启动应用
pom,xml 配置如下:
<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>com.szkingdom.filetool</groupId>
<artifactId>KingDomFileToolCombine</artifactId>
<version>V3.0.0</version>
<packaging>jar</packaging>
<properties>
<maven.compiler.source>7</maven.compiler.source>
<maven.compiler.target>7</maven.compiler.target>
<!-- Java版本 -->
<java.version>1.7</java.version>
<!-- 通过${hutool.version}来使用 -->
<spring.version>3.2.2.RELEASE</spring.version>
</properties>
<dependencies>
<!-- 使用 maven <systemPath>管理本地 jar 包
项目依赖的外部jar 是放在/lib目录下 (有的jar存在多版本)
- 1 <scope>system</scope>
- 2 <systemPath>${project.basedir}/lib/dom4j-1.6.1.jar</systemPath>
- 3 实在不知道 groupId 的用了自定义值替换; 比如local
- 4 在maven-dependency-plugin 打包到 lib 目录时,会改变jar名称为 (artifactId-version.jar)
- 5 配置完成后重新刷新 maven 依赖 (idea 中建议先手动移除
project structure>modules>dependencies 中的依赖,刷新后maven会自动配置)
-->
<dependency>
<groupId>org.dom4j</groupId>
<artifactId>dom4j</artifactId>
<version>1.6.1</version>
<!--system,类似provided,需要显式提供依赖的jar以后,Maven就不会在Repository中查找它-->
<scope>system</scope>
<systemPath>${project.basedir}/lib/dom4j-1.6.1.jar</systemPath>
</dependency>
<dependency>
<groupId>bouncycastle</groupId>
<artifactId>bcprov-jdk15</artifactId>
<!--
在maven-dependency-plugin 打包到 lib 目录时,会改变 jar 名称为 (artifactId-version.jar; )
将原 jar包数字拆分到 <version>;可以实现重新打包后名称不变 如: bcprov-jdk15-133.jar
-->
<version>133</version>
<scope>system</scope>
<systemPath>${project.basedir}/lib/bcprov-jdk15-133.jar</systemPath>
</dependency>
<dependency>
<!--实在不知道 groupId 的用了自定义值替换; 比如local-->
<groupId>local</groupId>
<artifactId>chinapnr</artifactId>
<!--实在不知道 version 的用了自定义值替换; 比如localversion;
在maven-dependency-plugin 打包到 lib 目录时,
会改变 jar 名称为 (artifactId-version.jar;如: chinapnr-localversion.jar )
需要配合 maven-jar-plugin <Class-Path>标签一起使用,
配置的 class-path jar名称为 chinapnr-localversion.jar
-->
<version>localversion</version>
<scope>system</scope>
<systemPath>${project.basedir}/lib/chinapnr.jar</systemPath>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-beans</artifactId>
<version>${spring.version}</version>
<scope>system</scope>
<systemPath>${project.basedir}/lib/spring-beans-3.2.2.RELEASE.jar</systemPath>
</dependency>
</dependencies>
<build>
<!--构建后 jar 文件名称-->
<finalName>kingDomFileToolCombine</finalName>
<!--java 源代码所在目录 默认 src/main/java-->
<sourceDirectory>java</sourceDirectory>
<!--配置文件所在目录 默认 src/main/resources-->
<scriptSourceDirectory>source</scriptSourceDirectory>
<!--<!–构建目录 默认target–>-->
<directory>bin</directory>
<!--编译后class存放目录 默认target/classes-->
<outputDirectory>bin</outputDirectory>
<!--资源文件夹,可配置多个-->
<resources>
<resource>
<directory>resources</directory>
</resource>
<resource>
<directory>source</directory>
</resource>
</resources>
<!--插件打包-->
<plugins>
<!--在打包阶段将依赖的jar包导出到lib目录下-->
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-dependency-plugin</artifactId>
<executions>
<execution>
<id>copy-dependencies</id>
<phase>package</phase>
<goals>
<goal>copy-dependencies</goal>
</goals>
<configuration>
<type>jar</type>
<includeTypes>jar</includeTypes>
<outputDirectory>out/lib</outputDirectory>
</configuration>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-jar-plugin</artifactId>
<version>2.4</version>
<configuration>
<archive>
<!-- 生成MANIFEST.MF的设置 -->
<manifest>
<useUniqueVersions>false</useUniqueVersions>
<!-- jar启动入口类 -->
<mainClass>com.szkingdom.FileTools.UI.FileToolsSurface</mainClass>
<!-- 为依赖包添加路径, 这些路径会写在MANIFEST文件的Class-Path下 -->
<addClasspath>true</addClasspath>
</manifest>
<manifestEntries>
<!--将依赖.jar 写进MANIFEST.MF文件中的Class-Path-->
<Class-Path>lib/bcprov-jdk15-133.jar lib/cipher-localversion.jar</Class-Path>
</manifestEntries>
</archive>
<!-- 指定打包后 jar包的位置,设置为根目录下 /out -->
<outputDirectory>out</outputDirectory>
<excludes>
<exclude>*.jar</exclude> <!--排除打包后的 jar文件本身-->
</excludes>
</configuration>
</plugin>
</plugins>
</build>
</project>打包启动 jar 后报错记录解决
mvn clean package 打包 后 cd 到 jar 所在目录 java -jar 启动程序
#### Error assembling JAR: A zip file cannot include itself
- 装配JAR错误:zip文件不能包含自身
```asp
<excludes>
<exclude>*.jar</exclude> <!--排除打包后的 jar文件本身-->
</excludes>
```
#### java -jar 运行程序报错, java.lang.NoClassDefFoundError
- java.lang.NoClassDefFoundError 找不到外部依赖的 jar
- 解决:
- 1 打包时插件配置 <Class-Path>
- 2 需要将 lib 目录放到 jar同级别目录
#### java -jar 运行程序报错, java.lang.Error: Properties init: Could not determine current working directory.
- 原因: 找不到当前所在目录; 每次重新 mvn clear package 时 ,旧的命令行窗口所在目录已经被清除了
- 解决: 重新 cd 到 jar 目录 运行 java -jar
代码改造,之前读取 classpath 下的配置,改造为从 jar 包外文件中读取
//编写配置文件加载工具类
public class ConfigFileUtil {
/**
* 文件分割路径 ,mac windows 适配
*/
public final static String PATH_SPLIT = File.separator;
private static String CONFIG_FILE_PATH;
static {
//System.out.println(" 相对于当前用户目录的相对路径 user.dir :" + System.getProperty("user.dir"));
//获取当前 jar 包路径 .....jar
String jarFilePath = FileUtil.class.getProtectionDomain().getCodeSource().getLocation().getPath();
System.out.println(" jar文件所在路径为 :" + jarFilePath);
try {
jarFilePath=URLDecoder.decode(jarFilePath, "utf-8");// 转化为utf-8编码,支持中文
} catch (UnsupportedEncodingException e) {
e.printStackTrace();
}
File file = new File(jarFilePath);
CONFIG_FILE_PATH = file.getParent();
System.out.println(" 配置文件所在路径为 :" + CONFIG_FILE_PATH);
}
public static String getFileAbsolutePath(String underBinPath) {
String filePath = "";
if (underBinPath.startsWith("bin")) {
filePath = FileUtil.CONFIG_FILE_PATH + FileUtil.PATH_SPLIT + underBinPath;
} else {
filePath = FileUtil.CONFIG_FILE_PATH + FileUtil.PATH_SPLIT + "bin" + FileUtil.PATH_SPLIT + underBinPath;
}
System.out.println(" 配置文件所在绝对路径为 :" + filePath);
return filePath;
}
/**
* @param underBinPath 存放在 /src/main/resources/bin 下的相对路径
* @return
*/
public static FileInputStream getConfigFileInputStream(String underBinPath) {
FileInputStream is = null;
try {
String fileAbsolutePath = getFileAbsolutePath(underBinPath);
is = new FileInputStream(fileAbsolutePath);
} catch (FileNotFoundException e) {
e.printStackTrace();
}
return is;
}
public static FileOutputStream getConfigFileOutPutStream(String underBinPath) {
FileOutputStream os = null;
try {
String fileAbsolutePath = getFileAbsolutePath(underBinPath);
os = new FileOutputStream(fileAbsolutePath);
} catch (FileNotFoundException e) {
e.printStackTrace();
}
return os;
}项目问题每天不重样,遇到问题解决问题, 调整升级方式为后续代码重构做铺垫
相关推荐
- 壁纸图片2025最新款(电脑桌面壁纸图片2025最新款)
-
要更换2023最新款壁纸图片,可以按照以下步骤操作:首先,找到您想要更换的壁纸图片并下载到您的设备上。其次,进入您的设备设置,找到“壁纸”或“桌面壁纸”选项,并点击进入。然后,选择“更换壁纸”并在相册...
- 清理垃圾的神器(清理垃圾的神器是什么)
-
1、《腾讯手机管家》这款可以帮助用户进行强力的清理,加速告别空间卡顿,缓慢延迟的问题的软件当中,用户可以随时随地登录软件进行自动清理和自动清理,自动清理包括图片,视频,语音文件在内的各种换成文件,为手...
- 苹果笔记本怎样重装系统(苹果笔记本怎样重装系统还原)
-
苹果笔记本电脑系统可以通过以下步骤进行重装:1.备份数据:在开始重装前,需要备份你的重要数据。你可以将数据存储到外部硬盘、云存储或其他可靠的设备中。2.下载安装器:从AppStore中下载macOS...
- 手机wifi打不开怎么办
-
手机wifi打不开的原因,可能集中在该手机出现了手机文件丢失、手机版本不稳定、手机文件出错以及手机wifi模块摔坏等故障造成的。手机wifi打不开修复教程1.wcnss_qcom_cfg文件丢失导...
- bios恢复出厂设置后无法开机
-
可通过进入BIOS界面设置bios恢复出厂设置的方法解决,步骤如下:1、通过按Delete或数字键盘中的Del键进入BIOS。2、按箭头键输入并将光标移动到“加载设置默认值”项,然后按enter确认。...
- 电脑硬盘打不开怎么办(电脑硬盘打不开怎么办)
-
电脑硬盘坏了是不能开机的。硬盘坏道的修复方法:1、逻辑坏道的修复对于逻辑坏道,Windows自带的“磁盘扫描程序(Scandisk)”就是最简便常用的解决手段。如果硬盘出现了坏道,我们可在Window...
- linux系统备份与还原工具(linux系统备份与还原工具在哪)
-
用GHOST对LINUX系统做备份1:要求将安装了LINUX系统的硬盘(原盘)整盘刻至另一硬盘(目标盘)。2:所需工具:DOS系统引导盘,GHOST2003(版本低的对文件格式不能很好的支持),原盘(...
- pdf怎么转换成xml格式(如何将pdf格式转换成xml格式)
-
将PDF转换为XML需要使用专业的PDF转换工具。以下是一些常用的PDF转XML工具:1.AdobeAcrobatDC:AdobeAcrobatDC是一款功能强大的PDF编辑软件,其中包括P...
- windows7iso文件(iso文件 win7)
-
利用winrar可以直接打开iso文件,如果双击不能直接打开需要设置winrar,步骤如下:1、启动winrar,点击选项菜单设置命令;2、点击综合选项卡,点击全部选择,点击确定即可。具体操作方法步骤...
- 路由器ip地址是什么意思(路由器的ip地址是)
-
路由器IP地址是指连接到互联网的路由器在局域网内的唯一标识符,一般为192.168.1.1或192.168.0.1等地址。通过路由器IP地址,用户可以通过浏览器等工具登录到路由器管理界面,进行网络设置...
-
- mediaplayer播放记录在哪里(mediaplayer历史记录)
-
《WindowsMediaPlayer》无法播放该文件,表示《WindowsMediaPlayer》目前的版本不支持该视频的格式编码。解决方法: 1.如果安装的是正版操作系统,点帮助→检查更新,稍待片刻,WindowsMed...
-
2026-01-14 02:37 liuian
- 电脑xp怎么换系统win7(电脑xp系统换win7教程)
-
第一种方法:自助安装win7系统 我们在进行自助安装win7系统之前我们要保证我们的电脑是联网的。为了能更加顺利的完成对xp系统的升级,我们的电脑最好是能高速上网的,只有能联网我们才可以下载最新的系...
- appstore官方网站(appstore.apple.com)
-
Appstore即applicationstore,通常理解为应用商店。Appstore是苹果公司基于iPhone的软件应用商店,向iPhone的用户提供第三方的应用软件服务,这是苹果开创的一...
- 电脑开不了机怎么办显示英文字母
-
win7操作系统电脑在开机的时候屏幕界面出现CLIENTMACADDR,然后就一直停在了这个界面,要等很长时间才能进入系统登入界面。出现这样问题的原因是什么?这是因为网卡启用了BOOTROM芯片...
- win7此windows副本不是正版(win7 此windows副本不是正版)
-
win7系统提示副本不是正版解决方法:1.打开设备,调出运行窗口,输入命令“cmd”,并按下回车键;2.这时命令提示符窗口便会自动弹出;3.输入命令“SLMGR-REARM”,再按下回车键;4.命令...
- 一周热门
-
-
飞牛OS入门安装遇到问题,如何解决?
-
如何在 iPhone 和 Android 上恢复已删除的抖音消息
-
Boost高性能并发无锁队列指南:boost::lockfree::queue
-
大模型手册: 保姆级用CherryStudio知识库
-
用什么工具在Win中查看8G大的log文件?
-
如何在 Windows 10 或 11 上通过命令行安装 Node.js 和 NPM
-
威联通NAS安装阿里云盘WebDAV服务并添加到Infuse
-
Trae IDE 如何与 GitHub 无缝对接?
-
idea插件之maven search(工欲善其事,必先利其器)
-
如何修改图片拍摄日期?快速修改图片拍摄日期的6种方法
-
- 最近发表
- 标签列表
-
- python判断字典是否为空 (50)
- crontab每周一执行 (48)
- aes和des区别 (43)
- bash脚本和shell脚本的区别 (35)
- canvas库 (33)
- dataframe筛选满足条件的行 (35)
- gitlab日志 (33)
- lua xpcall (36)
- blob转json (33)
- python判断是否在列表中 (34)
- python html转pdf (36)
- 安装指定版本npm (37)
- idea搜索jar包内容 (33)
- css鼠标悬停出现隐藏的文字 (34)
- linux nacos启动命令 (33)
- gitlab 日志 (36)
- adb pull (37)
- python判断元素在不在列表里 (34)
- python 字典删除元素 (34)
- vscode切换git分支 (35)
- python bytes转16进制 (35)
- grep前后几行 (34)
- hashmap转list (35)
- c++ 字符串查找 (35)
- mysql刷新权限 (34)
