3.6. 输入 Secret 和 ConfigMap
有时候,构建操作需要凭证或其他配置数据才能访问依赖的资源,但又不希望将这些信息放在源代码控制中。您可以定义输入 secret 和输入 ConfigMap 来实现这一目的。
例如,在使用 Maven 构建 Java 应用程序时,可以设置通过私钥访问的 Maven Central 或 JCenter 的私有镜像。要从该私有镜像下载库,您必须提供以下内容:
- 配置了镜像的 URL 和连接设置的 settings.xml 文件。
- 设置文件中引用的私钥,例如 ~/.ssh/id_rsa。
为安全起见,不应在应用程序镜像中公开您的凭证。
示例中描述的是 Java 应用程序,但您可以使用相同的方法将 SSL 证书添加到 /etc/ssl/certs 目录,以及添加 API 密钥或令牌、许可证文件等。
3.6.1. 添加输入 secret 和 ConfigMap
有时候,构建操作需要凭证或其他配置数据才能访问依赖的资源,但又不希望将这些信息放在源代码控制中。您可以定义输入 secret 和输入 ConfigMap 来实现这一目的。
流程
将输入 secret 和/或 ConfigMap 添加到现有的 BuildConfig
中:
如果 ConfigMap 不存在,则进行创建:
$ oc create configmap settings-mvn \ --from-file=settings.xml=<path/to/settings.xml>
这会创建一个名为 settings-mvn 的新 ConfigMap,其包含 settings.xml 文件的纯文本内容。
如果 secret 不存在,则进行创建:
$ oc create secret generic secret-mvn \ --from-file=id_rsa=<path/to/.ssh/id_rsa>
这会创建一个名为 secret-mvn 的新 secret,其包含 id_rsa 私钥的 base64 编码内容。
将 ConfigMap 和 secret 添加到现有
BuildConfig
的source
部分中:source: git: uri: https://github.com/wildfly/quickstart.git contextDir: helloworld configMaps: - configMap: name: settings-mvn secrets: - secret: name: secret-mvn
要在新 BuildConfig
中包含 secret 和 ConfigMap,请运行以下命令:
$ oc new-build \ openshift/wildfly-101-centos7~https://github.com/wildfly/quickstart.git \ --context-dir helloworld --build-secret “secret-mvn” \ --build-config-map "settings-mvn"
在构建期间,settings.xml 和 id_rsa 文件将复制到源代码所在的目录中。在 OpenShift Container Platform S2I 构建器镜像中,这是镜像的工作目录,使用 Dockerfile 中的 WORKDIR
指令设置。如果要指定其他目录,请在定义中添加 destinationDir
:
source: git: uri: https://github.com/wildfly/quickstart.git contextDir: helloworld configMaps: - configMap: name: settings-mvn destinationDir: ".m2" secrets: - secret: name: secret-mvn destinationDir: ".ssh"
您还可以指定创建新 BuildConfig
时的目标目录:
$ oc new-build \ openshift/wildfly-101-centos7~https://github.com/wildfly/quickstart.git \ --context-dir helloworld --build-secret “secret-mvn:.ssh” \ --build-config-map "settings-mvn:.m2"
在这两种情况下,settings.xml 文件都添加到构建环境的 ./.m2 目录中,而 id_rsa 密钥则添加到 ./.ssh目录中。
3.6.2. Source-to-Image 策略
采用 Source
策略时,所有定义的输入 secret 都复制到对应的 destinationDir
中。如果 destinationDir
留空,则 secret 会放置到构建器镜像的工作目录中。
destinationDir
是相对路径时采用相同的规则;secret 将放置到相对于镜像工作目录的路径中。如果构建器镜像中不存在 destinationDir
路径中的最终目录,则会创建该目录。destinationDir
中的所有上述目录都必须存在,否则会发生错误。
输入 secret 将以全局可写(具有 0666
权限)形式添加,并且在执行 assemble 脚本后其大小会被截断为零。也就是说,生成的镜像中会包括这些 secret 文件,但出于安全原因,它们将为空。
assemble 脚本完成后不会截断输入 ConfigMap。
3.6.3. Docker 策略
采用 Docker
策略时,您可以使用 Dockerfile 中的 ADD
和 COPY
指令,将所有定义的输入 secret 添加到容器镜像中。
如果没有为 secret 指定 destinationDir
,则文件将复制到 Dockerfile 所在的同一目录中。如果将一个相对路径指定为 destinationDir
,则 secret 将复制到相对于 Dockerfile 所在位置的这个目录中。这样,secret 文件可供 Docker 构建操作使用,作为构建期间使用的上下文目录的一部分。
引用 secret 和 ConfigMap 数据的 Dockerfile 示例
FROM centos/ruby-22-centos7 USER root COPY ./secret-dir /secrets COPY ./config / # Create a shell script that will output secrets and ConfigMaps when the image is run RUN echo '#!/bin/sh' > /input_report.sh RUN echo '(test -f /secrets/secret1 && echo -n "secret1=" && cat /secrets/secret1)' >> /input_report.sh RUN echo '(test -f /config && echo -n "relative-configMap=" && cat /config)' >> /input_report.sh RUN chmod 755 /input_report.sh CMD ["/bin/sh", "-c", "/input_report.sh"]
用户通常应该从最终的应用程序镜像中移除输入 secret,以便从该镜像运行的容器中不会存在这些 secret。但是,secret 仍然存在于它们添加到的层中的镜像本身内。这一移除应该是 Dockerfile 本身的一部分。
3.6.4. Custom 策略
使用 Custom
策略时,所有定义的输入 secret 和 ConfigMap 都位于 /var/run/secrets/openshift.io/build 目录下的构建器容器内。自定义构建镜像负责适当地使用这些 secret 和 ConfigMap。Custom
策略也允许按照 Custom 策略选项中所述定义 secret。
现有策略 secret 与输入 secret 之间没有技术差异。但是,构建器镜像可以区分它们并以不同的方式加以使用,具体取决于您的构建用例。
输入 secret 始终挂载到 /var/run/secrets/openshift.io/build 目录中,或您的构建器可以解析 $BUILD
环境变量(包含完整构建对象)。