【问题标题】:Quarkus Image: Cannot run program "keytool": error=2, No such file or directoryQuarkus 图像:无法运行程序“keytool”:错误=2,没有这样的文件或目录
【发布时间】:2021-06-22 15:32:39
【问题描述】:

我有一个在 Java 11 上运行并使用 Quarkus 框架的 Java 项目。在项目代码的某处有这一行:

Process proc = Runtime.getRuntime()
                        .exec("keytool -keystore " + trustStore.toString() + " -alias postgresql " + "-storepass \""
                                + trustCredentials.toString() + "\" -noprompt -import -file " + caRoot.toString());

以上行是使用 keytool 命令将证书添加到信任库。

在尝试将我的 java 项目构建到 Fast-Jar 然后运行该 jar 时出现问题。未找到 Keytool 命令:

java.io.IOException: Cannot run program "keytool": error=2, No such file or directory
    at java.lang.ProcessBuilder.start(ProcessBuilder.java:1128) ~[?:?]
    at java.lang.ProcessBuilder.start(ProcessBuilder.java:1071) ~[?:?]
    at java.lang.Runtime.exec(Runtime.java:592) ~[?:?]
    at java.lang.Runtime.exec(Runtime.java:416) ~[?:?]
    at java.lang.Runtime.exec(Runtime.java:313) ~[?:?]

我不太明白为什么会发生这种情况。我知道 keytool 是随 java 安装一起提供的,我已经检查过了,它似乎安装在我的图像上。我也明白 PATH 变量可能需要更新。但是,在 Linux 机器上(我的图像是基于它的),keytool 安装在 /usr/bin 下,这已经是路径的一部分。作为另一个测试,我还尝试在 java 代码中指定 keytool 的路径,即:

Process proc = Runtime.getRuntime()
                        .exec("/usr/bin/keytool -keystore " ...blah 

仍然出现同样的错误。也许这个问题可能与 quarkus 如何构建它的图像有关?

这大致就是我在 gitlab-ci.yml 中构建我的快速 Jar 映像的方式:

- export JOB_CONTAINER_ID=`docker ps -q -f "label=com.gitlab.gitlab-runner.type=build" -f "label=com.gitlab.gitlab-runner.job.id=$CI_JOB_ID"`
      - export TOKEN=$CI_BUILD_TOKEN
      - docker login -u gitlab-ci-token -p $CI_BUILD_TOKEN $CI_REGISTRY
      - |
         docker build -t temp-image-builder -f - . << EOF
         FROM ${DIND_BUILD_IMAGE}
         COPY . /project
         EOF
      - docker run --rm --privileged --name=temp-image-builder --user root -w /project
         -v /var/run/docker.sock:/var/run/docker.sock
         -e "CI_PROJECT_DIR=$CI_PROJECT_DIR" -e "TOKEN=$TOKEN" -e "QUARKUS_PROFILE=$QUARKUS_PROFILE" -e "TAG=$TAG"
         -e "IMAGE_NAME=${CI_REGISTRY_IMAGE}/${SERVICE_NAME}:${TAG}" -e "ENFORCE_RELEASE_GATE=on"
         -e "CI_COMMIT_REF_NAME=$CI_COMMIT_REF_NAME" -e "GITLAB_USER_LOGIN=$GITLAB_USER_LOGIN"
         -e "CI_PROJECT_NAME=$CI_PROJECT_NAME" -e "CI_PROJECT_URL=$CI_PROJECT_URL" -e "CI_JOB_ID=$CI_JOB_ID"
         --entrypoint /bin/bash temp-image-builder:latest '-c'
            '
               ./gradlew -Pversion="${TAG}"
                  clean build
                  -Dquarkus.package.type=fast-jar
                  -Dquarkus.profile="${QUARKUS_PROFILE}"
                  -Dquarkus.jib.base-registry-username=gitlab-ci-token -Dquarkus.jib.base-registry-password="$TOKEN"
                  -Dquarkus.container-image.tag="${TAG}"
                  -Dquarkus.container-image.build=true
            '
      - docker push ${CI_REGISTRY_IMAGE}/${SERVICE_NAME}:${TAG}

${DIND_BUILD_IMAGE} 是另一个基于 java-11 alpine 图像的图像。

试图解决这个问题真的很令人沮丧,这似乎是一件很简单的事情,但到目前为止我还没有运气。任何关于可能出错的建议将不胜感激。谢谢。

【问题讨论】:

  • 你定义了 caroot 吗? caRoot.toString()
  • 都是在某个地方定义的,只是觉得没必要展示。我还注意到它不仅仅是 keytool 命令,它是我想的任何命令。我尝试执行 .exec("ls /") 并收到命令未找到错误

标签: java quarkus keytool


【解决方案1】:

原来这确实是一个 PATH 问题。我误认为 keytool 在 usr/bin 下。使用这个名为"dive" 的工具,我能够找出keytool 的位置。不幸的是,我不确定是否可以使用 jib 将 PATH 变量更新到 keytool 所在的位置,但至少我可以运行 exec 并包含 keytool 路径(即 .exec(path/to/tool/keytool . ..blah)) 并且它会成功运行

【讨论】:

    猜你喜欢
    • 2018-01-30
    • 2016-08-22
    • 1970-01-01
    • 2020-11-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-04-22
    相关资源
    最近更新 更多