Container Images

Container Image extensions

Jib

扩展 `quarkus-container-image-jib`由 Jib提供支持,用于执行容器映像构建。将 Jib 用于 Quarkus 的主要好处在于,所有依赖项(`target/lib`下找到的所有内容)都缓存在与实际应用程序不同的层中,从而使重建变得非常快速且占用空间较小(在发布时)。使用此扩展的另一个重要好处在于,它提供了创建容器映像而无需任何专用客户端工具(如 Docker)或运行守护程序进程(如 Docker 守护程序)的能力,而只需要将内容发布到容器映像注册表的能力。

要使用此功能,请将以下扩展名添加到您的项目:

CLI
quarkus extension add {add-extension-extensions}
Maven
./mvnw quarkus:add-extension -Dextensions='{add-extension-extensions}'
Gradle
./gradlew addExtension --extensions='{add-extension-extensions}'

在仅需要构建容器映像并且不需要发布到注册表的情况下(基本上通过设置 quarkus.container-image.build=true`并使 `quarkus.container-image.push`保持未设置状态——它默认为 `false),此扩展将创建一个容器映像并将其注册到 Docker 守护程序。这意味着尽管不用 Docker 构建映像,但它仍然是必需的。另外请注意,使用此模式时,在执行 `docker images`时,构建的容器映像 *will*将显示出来。

Including extra files

在某些情况下,需要将除 Quarkus 构建生成的之外的其他文件添加到容器映像中。为了支持这种情况,Quarkus 会将 src/main/jib`下的所有文件复制到构建的容器映像中(本质上与 Jib Maven 和 Gradle 插件支持的理念相同)。例如,如果存在 `src/main/jib/foo/bar,则 `/foo/bar`将被添加到容器文件系统中。

JVM Debugging

在某些情况下,可能需要在运行时有条件地启用构建的容器映像的 Java 调试。

当基础映像未更改时(因此使用了 ubi8/openjdk-11-runtimeubi8/openjdk-17-runtime`或 `ubi8/openjdk-21-runtime),则可以在启动时使 JVM 在调试端口上进行侦听,为此可使用 `quarkus.jib.jvm-additional-arguments`配置属性。

确切的配置为:

quarkus.jib.jvm-additional-arguments=-agentlib:jdwp=transport=dt_socket\\,server=y\\,suspend=n\\,address=*:5005

其他基础映像可能提供在设置环境变量时启用调试的启动脚本,在这种情况下,你将在启动容器时设置该环境变量。

Custom Entrypoint

可以使用 `quarkus.jib.jvm-entrypoint`配置属性完全覆盖容器入口点,因此可以使用它对 JVM 调试配置进行硬编码或指向处理详细信息的脚本。

例如,如果使用基础映像 ubi8/openjdk-11-runtime、`ubi8/openjdk-17-runtime`or `ubi8/openjdk-21-runtime`构建容器,则可以在应用程序配置文件中对入口点进行硬编码。

Example application.properties
quarkus.jib.jvm-entrypoint=java,-Dcustom.param=custom_value,-jar,quarkus-run.jar

或者,可以创建自定义启动脚本并在配置文件中引用它。如果需要使用环境变量设置应用程序参数,此方法会更好:

Example application.properties
quarkus.jib.jvm-entrypoint=/bin/sh,run-java.sh
Example src/main/jib/home/jboss/run-java.sh
java \
  -Djavax.net.ssl.trustStore=/deployments/truststore \
  -Djavax.net.ssl.trustStorePassword="$TRUST_STORE_PASSWORD" \
  -jar quarkus-run.jar

/home/jboss`是基础映像 `ubi8/openjdk-11-runtimeubi8/openjdk-17-runtime`和 `ubi8/openjdk-21-runtime (Dockerfile for ubi8/openjdk-17-runtime) 中所有 quarkus 二进制文件的工作目录

Multi-module projects and layering

在构建一个包含一个 Quarkus 应用程序(作为其中一个模块)的多模块项目和各种支持项目依赖项(作为其他模块)时,Quarkus 支持将这些支持模块放在与应用程序其他依赖项分开的容器映像层中,且预期这些支持模块将比常规的应用程序依赖项更频繁地发生更改——因此,如果应用程序依赖项未更改,将可以更快地进行重建。

为了启用此特性,需要将属性 quarkus.bootstrap.workspace-discovery`设置为 `true,方法是将其作为在调用构建工具时传入的系统属性,或作为构建工具属性。在 `application.properties`设置此属性会 *not*生效,因为需要在构建过程的非常早的阶段了解此属性。

AppCDS

在使用 Jib 生成容器镜像时,Quarkus 支持生成并包含 Application Class Data Sharing 存档。有关更多详细信息,请参见 AppCDS documentation

Docker

扩展 quarkus-container-image-docker 使用 src/main/docker 中的 Docker 二进制文件和生成的 Dockerfile 来执行 Docker 构建。

要使用此功能,请向项目添加以下扩展。

CLI
quarkus extension add {add-extension-extensions}
Maven
./mvnw quarkus:add-extension -Dextensions='{add-extension-extensions}'
Gradle
./gradlew addExtension --extensions='{add-extension-extensions}'

quarkus-container-image-docker 扩展能够使用 docker buildx buildcreating multi-platform (or multi-arch) 镜像。请参见下面 Docker Options 部分中的 quarkus.docker.buildx.* 配置项。

docker buildx build 仅在为单个平台构建时支持 loading the result of a builddocker images。所以,如果您在 quarkus.docker.buildx.platform 属性中指定多个参数,结果镜像将不会加载到 docker images。如果省略 quarkus.docker.buildx.platform 或只指定单个平台,它将被加载到 docker images。 这意味着,如果您想一次为多个平台构建镜像(即 quarkus.docker.buildx.platform=linux/amd64,linux/arm64),则需要将镜像直接作为构建流程的一部分(quarkus.container-image.push=true)推送。构建多平台镜像时,Docker buildx 不支持加载到本地注册表中。

Podman

扩展 quarkus-container-image-podman 使用 Podmansrc/main/docker 中生成的 Dockerfiles 来执行容器构建。

要使用此功能,请向项目添加以下扩展。

CLI
quarkus extension add {add-extension-extensions}
Maven
./mvnw quarkus:add-extension -Dextensions='{add-extension-extensions}'
Gradle
./gradlew addExtension --extensions='{add-extension-extensions}'
When to use Docker vs Podman extension

Docker extension 始终都与 Podman 向后兼容,因为 Podman 暴露了一个 Docker-compatible API。您可以使用 Docker 扩展来用 Podman 构建容器镜像(请参见 Using Podman with Quarkus guide)。 在分别执行 Docker 或 Podman 特有的操作时,请分别使用 quarkus-container-image-dockerquarkus-container-image-podman 扩展。 例如,Docker 和 Podman 的多平台镜像构建实现不同。Docker 使用 the buildx plugin,而 Podman 可以 natively 构建多平台镜像。由于这个原因,您需要使用特定的扩展来执行此功能。

OpenShift

扩展 quarkus-container-image-openshift 使用 OpenShift 二进制版本构建,以便在 OpenShift 集群内执行容器构建。二进制版本构建的想法是,您只需将伪像和它的依赖项上传到集群,在构建期间它们将被合并到构建器镜像(默认为 fabric8/s2i-java)。

这种方法的好处在于,它可以与 OpenShift 的 DeploymentConfig 结合使用,后者使得向集群推出变更变得更加容易。

要使用此功能,请向项目添加以下扩展。

CLI
quarkus extension add {add-extension-extensions}
Maven
./mvnw quarkus:add-extension -Dextensions='{add-extension-extensions}'
Gradle
./gradlew addExtension --extensions='{add-extension-extensions}'

OpenShift 构建要求创建 BuildConfig 和两个 ImageStream 资源,一个用于构建器镜像,一个用于输出镜像。Quarkus Kubernetes 扩展负责创建此类对象。

Buildpack

扩展 quarkus-container-image-buildpack 使用构建包来执行容器镜像构建。本质上,构建包会使用 Docker 守护程序来执行实际构建。虽然构建包支持 Docker 的替代品,但此扩展只支持 Docker。

此外,用户将必须配置要使用的构建镜像(未提供默认镜像)。例如:

quarkus.buildpack.jvm-builder-image=<jvm builder image>

或者对于本机:

quarkus.buildpack.native-builder-image=<native builder image>

要使用此功能,请向项目添加以下扩展。

CLI
quarkus extension add {add-extension-extensions}
Maven
./mvnw quarkus:add-extension -Dextensions='{add-extension-extensions}'
Gradle
./gradlew addExtension --extensions='{add-extension-extensions}'

使用构建包容器镜像扩展时,强烈建议在属性配置中避免添加 quarkus.container-image.build=true,因为它可能触发构建中的嵌套构建。最好将其作为选项传递给构建命令。

Building

要为你的项目构建一个容器镜像,请使用 Quarkus 支持的任何方法设置 quarkus.container-image.build=true

include::./_includes/devtools/build.adoc[]:!build-additional-parameters:

如果你想要构建本机容器镜像,并且已经有现有本机镜像,则可以设置 -Dquarkus.native.reuse-existing=true,这样本机镜像构建将不会重新运行。

Using @QuarkusIntegrationTest

要对生成的镜像运行测试,请使用 Quarkus 支持的任何方法设置 quarkus.container-image.build=true

Maven
./mvnw verify -Dquarkus.container-image.build=true
Gradle
./gradlew quarkusIntTest -Dquarkus.container-image.build=true

Pushing

要推送项目的容器镜像,请使用 Quarkus 支持的任何方法设置 quarkus.container-image.push=true

include::./_includes/devtools/build.adoc[]:!build-additional-parameters:

如果未设置注册中心(使用 quarkus.container-image.registry),那么将使用 `docker.io`作为默认值。

Selecting among multiple extensions

同时使用多个扩展作为同一构建的组成部分是没有意义的。当出现多个容器镜像扩展时,将引发一个错误来告知用户。用户可以移除不必要的扩展,也可以使用 `application.properties`选择一个扩展。

例如,如果 container-image-dockercontainer-image-podman`同时存在,用户需要使用 `container-image-docker

quarkus.container-image.builder=docker

Integrating with systemd-notify

要通过 Podman 和 Systemd 以 Linux 服务的形式部署 Quarkus 应用,如果正在构建容器镜像,则可能需要考虑将 Quarkus Systemd Notify Extension包含在你的应用中,方法如下:

CLI
quarkus extension add {add-extension-extensions}
Maven
./mvnw quarkus:add-extension -Dextensions='{add-extension-extensions}'
Gradle
./gradlew addExtension --extensions='{add-extension-extensions}'

Customizing

以下属性可用于自定义容器镜像构建流程。

Container Image Options

Unresolved include directive in modules/ROOT/pages/container-image.adoc - include::../../../target/quarkus-generated-doc/config/quarkus-container-image.adoc[]

Using CI Environments

各种 CI 环境提供了开箱即用的容器镜像注册中心,可以将其与容器镜像 Quarkus 扩展结合使用,以便轻松创建和推送 Quarkus 应用到该注册中心。

例如, GitLab 提供了这样的注册中心,并且在提供的 CI 环境中,CI_REGISTRY_IMAGE 环境变量可用(请参阅 GitLab 的 documentation 了解更多信息),可以在 Quarkus 中像这样使用:

quarkus.container-image.image=${CI_REGISTRY_IMAGE}

有关如何将属性与环境变量结合使用的更多信息,请参阅 this

Jib Options

除了通用的容器镜像选项外,container-image-jib 还提供了以下选项:

Unresolved include directive in modules/ROOT/pages/container-image.adoc - include::../../../target/quarkus-generated-doc/config/quarkus-container-image-jib.adoc[]

Docker Options

除了通用的容器镜像选项外,container-image-docker 还提供了以下选项:

Unresolved include directive in modules/ROOT/pages/container-image.adoc - include::../../../target/quarkus-generated-doc/config/quarkus-container-image-docker.adoc[]

Podman Options

除了通用的容器镜像选项外,container-image-podman 还提供了以下选项:

Unresolved include directive in modules/ROOT/pages/container-image.adoc - include::../../../target/quarkus-generated-doc/config/quarkus-container-image-podman.adoc[]

OpenShift Options

除了通用的容器镜像选项外,container-image-openshift 还提供了以下选项:

Unresolved include directive in modules/ROOT/pages/container-image.adoc - include::../../../target/quarkus-generated-doc/config/quarkus-container-image-openshift_quarkus.openshift.adoc[]