必须用eclipse-temurin替代openjdk官方镜像,因其已弃用、无安全更新、易致CVE漏洞和JVM崩溃;eclipse-temurin提供LTS支持、TCK认证、多平台兼容及严格镜像命名(如jammy),保障生产环境稳定与安全。

直接用 eclipse-temurin 替代已弃用的 openjdk 官方镜像,否则构建可能失败或存在安全风险。
为什么不能继续用 openjdk:17-jdk-slim 这类镜像
官方 library/openjdk 镜像自 2024 年起已正式弃用,仅保留早期预览版(Early Access)更新,不再接收安全补丁和 LTS 支持。生产环境使用会导致 CVE 漏洞无法修复、JVM 行为不一致等问题。
- 常见报错:拉取时提示
manifest unknown或构建后容器启动即退出(尤其在 Alpine 系统上 JVM 崩溃) - 替代方案必须选主流维护分支:
eclipse-temurin(跨平台兼容强)、amazoncorretto(AWS 生产验证)、ibm-semeru-runtimes(内存敏感场景) - 标签命名更严格:比如
eclipse-temurin:17-jre-jammy中jammy明确指 Ubuntu 22.04,避免隐式依赖差异
ENTRYPOINT 和 CMD 到底该用哪个
对单个可执行 JAR,优先用 ENTRYPOINT;若需运行时覆盖 JVM 参数或 profile,再配合 CMD 作为默认参数传入。
-
ENTRYPOINT ["java", "-jar", "app.jar"]:固定主命令,容器启动时必执行,适合无动态参数场景 -
ENTRYPOINT ["java", "-jar", "app.jar"]+CMD ["--spring.profiles.active=prod"]:运行docker run myapp --debug会覆盖CMD,最终执行java -jar app.jar --debug - 错误写法:
CMD java -jar app.jar(shell 形式)会绕过 PID 1,导致 SIGTERM 无法正确传递给 JVM,应用无法优雅停机
如何安全注入 JVM 参数和 Spring 配置
不要硬编码在 ENTRYPOINT 里,而是通过环境变量 + 启动脚本解耦,兼顾灵活性与可读性。
使用 Python 脚本下载 Docker 镜像并打包为 tar 文件。用户说“下载镜像”“拉取镜像”“pull xxx”“帮我下载 nginx 镜像”等时触发。支持 SOCKS5 代理直连(推荐)和国内镜像站加速两种模式。
立即学习“Java免费学习笔记(深入)”;
- 在
Dockerfile中设默认值:ENV JAVA_OPTS="-Xms512m -Xmx1024m",但允许外部覆盖 - 用
sh -c包裹启动逻辑(仅当必须拼接参数时):ENTRYPOINT ["sh", "-c", "java $JAVA_OPTS -jar /app.jar"] - Spring Boot 推荐方式:用
SPRING_PROFILES_ACTIVE环境变量代替硬编码,docker run -e SPRING_PROFILES_ACTIVE=prod即可生效 - 注意:Alpine 镜像中
glibc缺失可能导致-XX:+UseZGC失败,改用eclipse-temurin:17-jre-jammy更稳妥
多阶段构建不是可选项,是必需步骤
直接 COPY 构建产物的镜像体积常超 300MB,而多阶段能压到 80MB 以内,且消除构建工具暴露风险。
- 第一阶段用完整 JDK(如
eclipse-temurin:17-jdk-jammy)执行mvn package - 第二阶段用最小 JRE(如
eclipse-temurin:17-jre-jammy)COPYtarget/*.jar - 禁止在最终镜像中残留
src/、pom.xml、.m2等非运行文件 - 额外收益:构建缓存更高效 —— 只要
pom.xml不变,Maven 依赖层不会重复下载
最容易被忽略的是基础镜像的发行版一致性:本地开发用 Ubuntu,CI 用 Alpine,生产又切回 Debian,这种混用会让 /proc/sys/vm/max_map_count、ulimit、time zone 等系统级行为不可控。统一用 jammy(Ubuntu 22.04)或 bookworm(Debian 12)后缀镜像,比调 JVM 参数还重要。

















