以下是针对 SpringBoot Jar 包瘦身及外置三方依赖的完整方案总结,结合生产环境最佳实践和最新技术版本(Spring Boot 3.2.4, Maven 3.9+)整理而成。核心思路是通过依赖外置(Dependency Externalization)减小主 Jar 体积,提升部署效率。
一、方案概述
| 方案 | 适用场景 | 瘦身效果 | 生产稳定性 |
|---|---|---|---|
| Maven 依赖外置 | 标准 Web 项目,频繁更新业务代码 | 主 Jar 降至 1-5MB | ⭐⭐⭐⭐⭐ |
| Assembly 分发包 | 需标准化部署(含启动脚本/依赖) | 整体体积不变 | ⭐⭐⭐⭐ |
| Docker 分层构建 | 容器化部署环境 | 镜像层复用 | ⭐⭐⭐⭐ |
二、具体实现方法
方案 1:Maven 依赖外置(推荐生产使用)
原理:通过 spring-boot-maven-plugin 排除主 Jar 中的三方依赖,改用 -Dloader.path 启动时加载外部 lib 目录。
步骤:
-
修改
pom.xml配置<build> <plugins> <!-- 1. 配置 Spring Boot 插件排除所有依赖 --> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> <version>3.2.4</version> <!-- 使用最新稳定版 --> <configuration> <mainClass>com.example.Application</mainClass> <layout>ZIP</layout> <!-- 关键:启用外部依赖加载 --> <includes> <include> <groupId>nothing</groupId> <!-- 排除所有三方依赖 --> <artifactId>nothing</artifactId> </include> </includes> </configuration> </plugin> <!-- 2. 复制依赖到 target/lib 目录 --> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-dependency-plugin</artifactId> <version>3.6.1</version> <executions> <execution> <id>copy-dependencies</id> <phase>package</phase> <goals><goal>copy-dependencies</goal></goals> <configuration> <outputDirectory>${project.build.directory}/lib</outputDirectory> <overWriteIfNewer>true</overWriteIfNewer> <includeScope>runtime</includeScope> </configuration> </execution> </executions> </plugin> </plugins> </build> -
打包与部署
mvn clean package # 生成瘦身 Jar 和 lib 目录生成文件结构:
target/ ├── app.jar # 瘦身后主 Jar (仅业务代码) └── lib/ # 所有三方依赖 Jar -
启动命令
java -Dloader.path=./lib -jar app.jar
生产验证:
- 主 Jar 从 150MB → 1.3MB,依赖不变时只需更新主 Jar。
- 启动参数
-Dloader.path由 Spring Boot 的LaunchedURLClassLoader原生支持,稳定性高。
方案 2:Assembly 分发包(适合运维标准化)
原理:通过 maven-assembly-plugin 生成包含启动脚本、主 Jar 和 lib 目录的完整分发包,首次部署后仅需更新主 Jar。
步骤:
-
添加
assembly.xml描述文件<!-- src/main/assembly/assembly.xml --> <assembly> <id>bin</id> <formats><format>tar.gz</format></formats> <!-- 支持 zip/tar.gz --> <fileSets> <fileSet> <directory>${project.build.directory}</directory> <includes> <include>*.jar</include> <!-- 主应用 Jar --> </includes> <outputDirectory>/</outputDirectory> </fileSet> <fileSet> <directory>${project.build.directory}/lib</directory> <outputDirectory>/lib</outputDirectory> <!-- 依赖目录 --> </fileSet> </fileSets> <files> <file> <source>src/main/resources/start.sh</source> <!-- 启动脚本 --> <outputDirectory>/</outputDirectory> <fileMode>755</fileMode> </file> </files> </assembly> -
编写启动脚本
start.sh#!/bin/bash java -Dloader.path=./lib -jar ${project.build.finalName}.jar -
配置
pom.xml<plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-assembly-plugin</artifactId> <version>3.6.0</version> <configuration> <descriptors> <descriptor>src/main/assembly/assembly.xml</descriptor> </descriptors> </configuration> <executions> <execution> <phase>package</phase> <goals><goal>single</goal></goals> </execution> </executions> </plugin>
部署流程:
- 首次部署:上传分发包(如
app-bin.tar.gz),解压后运行./start.sh。 - 后续更新:只替换主 Jar(如
app.jar),无需重启服务(结合actuator热更新)。
三、生产环境优化与注意事项
-
依赖版本一致性
- 使用
mvn dependency:tree检查冲突,避免外置 lib 与主 Jar 版本不兼容。 - 建议在父 POM 中统一管理依赖版本(如 Spring Boot Dependency Management)。
- 使用
-
Docker 镜像优化
利用分层构建减少镜像体积:FROM eclipse-temurin:17-jre # 独立层:依赖(变更少) COPY target/lib /app/lib # 独立层:主 Jar(频繁变更) COPY target/app.jar /app/app.jar CMD ["java", "-Dloader.path=/app/lib", "-jar", "/app/app.jar"]- 依赖未更新时,Docker 构建跳过 lib 层,加速部署。
-
配置文件外置
结合spring.config.location实现配置与代码分离:java -Dloader.path=./lib -jar app.jar --spring.config.location=file:/etc/app/config/ -
类加载隔离问题
-
若外置 Jar 与 Spring Boot 内嵌库冲突(如 Tomcat 版本),需在
<excludes>中排除内嵌依赖。 -
示例:排除内嵌 Tomcat
<excludes> <exclude> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-tomcat</artifactId> </exclude> </excludes>
-
-
监控与调试
- 启动后检查:
http://localhost:8080/actuator/env验证loader.path是否生效。 - 日志排查:若出现
ClassNotFoundException,检查 lib 目录权限及路径。
- 启动后检查:
四、版本与兼容性说明
| 组件 | 推荐版本 | 关键变更说明 |
|---|---|---|
| Spring Boot Maven Plugin | 3.2.4 | layout=ZIP 模式稳定支持外部依赖加载 |
| Maven Dependency Plugin | 3.6.1 | 支持按作用域(scope)过滤依赖 |
| Java | ≥17 | 兼容 Spring Boot 3.x,低版本需用 Spring Boot 2.7(维护至2025年底) |
总结
推荐路径:
- 🚀 标准生产项目 → 方案 1(Maven 依赖外置),配置简单、维护成本低。
- 🔧 需标准化交付 → 方案 2(Assembly 分发包),整合脚本与依赖。
预期效果:
- 主 Jar 体积下降 90%~99%(从百 MB 降至 MB 级)。
- 依赖不变时,部署流量减少 90% 以上,显著提升 CI/CD 效率。
21万+

被折叠的 条评论
为什么被折叠?



