」工欲善其事,必先利其器。「—孔子《論語.錄靈公》
首頁 > 程式設計 > 使用 Buildpack 建立 Spring Boot 應用程式的 Docker 映像

使用 Buildpack 建立 Spring Boot 應用程式的 Docker 映像

發佈於2024-11-05
瀏覽:777

Creating Docker Image of Spring Boot Application using Buildpacks

介绍

您已经创建了一个 Spring Boot 应用程序。它在您的本地计算机上运行良好,现在您需要将该应用程序部署到其他地方。在某些平台上,您可以直接提交jar文件,它将被部署。在某些地方,您可以启动虚拟机,下载源代码,构建并运行它。但是,大多数时候您需要使用容器来部署应用程序。大多数时候,Docker 用于在容器中构建和运行镜像。此外,当您将 jar 文件上传到某些平台时,应用程序会在后台的容器内运行。

因此,在本博客中,我们将看到 3 种不同的方法来为给定的 Spring Boot 应用程序构建 Docker 映像。让我们开始吧:

基础容器镜像

为任何应用程序构建 Docker 映像的简单且不充分的方法是使用一个简单的 Dockerfile,它将 jar 文件复制到映像中并使用 java -jar 命令运行它。

创建 Dockerfile

这是可以放在项目根目录的 Dockerfile:

FROM eclipse-temurin:21-jre-ubi9-minimal

ARG JAR_FILE

COPY ${JAR_FILE} application.jar

ENTRYPOINT ["java", "-jar", "/application.jar"]

我们指定了一个参数 JAR_FILE,它是要使用的 jar 文件的位置。

构建 Docker 镜像

创建上述Dockerfile后,使用以下步骤创建Docker镜像:

  1. 为 Spring Boot 项目构建 jar 文件:

    ./gradlew bootJar # For Gradle build system
    

    或者

    ./mvnw spring-boot:build-jar # For Maven build system
    
  2. 使用 Dockerfile 使用最新的 jar 文件构建 Docker 映像。在以下命令中,将 {IMAGE_NAME} 替换为所需的映像名称,将 {JAR_FILE} 替换为生成的 jar 文件的路径。图像名称还包含一个标签,例如 - mycompany/product-service:0.0.1-SNAPSHOT:

    docker build --build-arg JAR_FILE={JAR_FILE} --tag {IMAGE_NAME} .
    
  3. 验证 Docker 镜像是否是使用以下命令构建的。您应该能够看到上面命令中指定名称的图像:

    docker images
    

使用分层 Jar 的高效容器镜像

虽然可以轻松地将 Spring Boot uber jar 打包为 Docker 映像(如前面的方法中所述),但在 Docker 映像中按原样复制和运行 fat jar 有很多缺点。例如,

  • 在不解压的情况下运行 uber jar 会产生一些额外的开销。
  • 将应用程序的代码及其所有依赖项放在单个层中并不是最佳选择。

由于我们编译代码的频率比升级 Spring Boot 版本的频率高,因此最好将各个部分分开一些。如果我们将那些很少更改的jar文件放在应用层之前的层中,那么Doc​​ker通常只需要更改底层,并且可以从其缓存中选取其余的。

启用分层 Jar

要创建分层的 Docker 镜像,我们需要首先创建分层的 jar。如今,它在 Gradle 和 Maven 中默认启用。您可以使用以下设置启用或禁用分层 jar 行为:

// build.gradle
tasks.named("bootJar") {
    layered {
        enabled = false
    }
}
// build.gradle.kts
tasks.named("bootJar") {
   layered {
      enabled.set(false)
   }
}


   
      
         
            org.springframework.boot
            spring-boot-maven-plugin
            
               
                  true
               
            
         
      
   

您甚至可以调整图层的创建方式。请参阅 gradle 或 maven 配置的文档。

创建 Dockerfile

下面是 Dockerfile,可用于利用分层 jar 并创建 Spring Boot 应用程序的分层 Docker 映像。

# Perform the extraction in a separate builder container
FROM eclipse-temurin:21-jre-ubi9-minimal AS builder

WORKDIR /builder

# This points to the built jar file in the target folder
# Adjust this to 'build/libs/*.jar' if you're using Gradle
ARG JAR_FILE=target/*.jar

# Copy the jar file to the working directory and rename it to application.jar
COPY ${JAR_FILE} application.jar

# Extract the jar file using an efficient layout
RUN java -Djarmode=tools -jar application.jar extract --layers --destination extracted

# This is the runtime container
FROM eclipse-temurin:21-jre-ubi9-minimal

WORKDIR /application

# Copy the extracted jar contents from the builder container into the working directory in the runtime container
# Every copy step creates a new docker layer
# This allows docker to only pull the changes it really needs
COPY --from=builder /builder/extracted/dependencies/ ./
COPY --from=builder /builder/extracted/spring-boot-loader/ ./
COPY --from=builder /builder/extracted/snapshot-dependencies/ ./
COPY --from=builder /builder/extracted/application/ ./

# Start the application jar - this is not the uber jar used by the builder
# This jar only contains application code and references to the extracted jar files
# This layout is efficient to start up and CDS friendly
ENTRYPOINT ["java", "-jar", "application.jar"]

构建 Docker 镜像

构建分层 Docker 镜像的步骤与构建基本 Docker 镜像相同。请参考那里。

云原生构建包

如果我告诉你无需创建 Dockerfile 就可以创建 Docker 映像怎么办?我们可以使用 Cloud Native Buildpacks 直接从 Gralde 或 Maven 插件构建 docker 镜像。一些平台(如 Heroku 或 Cloud Foundry)使用 Buildpack 将提供的 jar 文件转换为可运行的映像。

Spring Boot 包括直接对 Maven 和 Gradle 的构建包支持。我们不需要包含任何额外的插件。只需运行以下命令:

./gradlew bootBuildImage # For gradle build system

或者

./mvnw spring-boot:build-image # For maven build system

上述命令生成默认名称为 {PROJECT_NAME}:${PROJECT_VERSION} 的图像。如果要配置生成图片的名称,可以按照以下步骤操作:

为 Gradle 构建系统配置镜像名称

我们可以配置 bootBuildImage 任务来设置镜像的名称,如下所示:

// For build.gradle.kts
val imagePrefix = "javarush"
val dockerImageName = "docker-example"
tasks.named("bootBuildImage") {
   imageName.set("${imagePrefix}/${dockerImageName}:${version}")
}
// For build.gradle
def imagePrefix = "javarush"
def dockerImageName = "docker-example"
tasks.named("bootBuildImage") {
   imageName = "${imagePrefix}/${dockerImageName}:${version}"
}

为 Maven 构建系统配置镜像名称

我们可以配置 spring-boot-maven-plugin 使用另一个镜像名称,如下所示:


   javarush


...


    
        
            
                org.springframework.boot
                spring-boot-maven-plugin
                
                    
                        ${imagePrefix}/${project.artifactId}:${project.version}
                    
                
            
        
    

运行命令时配置镜像名称

我们甚至可以在运行构建镜像的命令时定义镜像的名称。

./gradlew bootBuildImage --imageName=javarush/docker-example:1.0.0 # For grade build system

./mvnw spring-boot:build-image -Dspring-boot.build-image.imageName=javarush/docker-example:1.0.0 # For maven build system

可以查看文档进一步配置Gradle或Maven插件。
这是我为任何 Spring Boot 应用程序创建 Docker 映像的首选方法。

运行 Docker 容器

创建 docker 镜像后,您需要确保它按预期工作。确保镜像创建完成后,可以直接使用 docker run 命令运行它。例如,

docker run -p "8080:8080" {IMAGE_NAME}

但是,这不是图像在生产应用程序中的使用方式。 Docker Compose 用于运行和管理多个 docker 镜像。

结论

在这篇博客中,我们了解了如何使用不同的方法为 Spring Boot 应用程序构建 Docker 镜像。能够为您的应用程序构建 Docker 镜像是一项必须了解的技能,因为镜像是交付的内容。感谢您阅读本文直到最后。我很感激。我会在下一篇与你见面。一如既往,欢迎所有反馈和建议。

版本聲明 本文轉載於:https://dev.to/himanshu-pareek/creating-docker-image-of-spring-boot-application-using-buildpacks-5dbo?1如有侵犯,請聯絡[email protected]刪除
最新教學 更多>

免責聲明: 提供的所有資源部分來自互聯網,如果有侵犯您的版權或其他權益,請說明詳細緣由並提供版權或權益證明然後發到郵箱:[email protected] 我們會在第一時間內為您處理。

Copyright© 2022 湘ICP备2022001581号-3