有 Dockerfile
FROM openjdk:11.0.12-jre-slim
COPY target/app.jar /app.jar
COPY configs configs
ENTRYPOINT ["java","-jar","/app.jar"]
在檔案夾 configs 中包含 java 應用程式的 json 配置。構建 docker 命令是:
docker build --build-arg -f ~/IdeaProjects/app --no-cache -t app:latest
運行命令是:
docker run --entrypoint="cp configs var/opt/configs/ && java -jar app.jar" app:latest
讓我們忽略通過 COPY 命令復制 Dockerfile 中的配置的能力。不幸的是,這必須使用 --entrypoint 來完成。
執行 docker run 命令時出現錯誤:
docker:來自守護行程的錯誤回應:OCI 運行時創建失敗:container_linux.go:370:導致啟動容器行程:exec:“cp configs var/opt/configs/ && java -jar app.jar”:stat cp configs var/opt/ configs/ && java -jar app.jar:沒有這樣的檔案或目錄:未知。
你能解釋為什么在這種情況下發生錯誤嗎?
uj5u.com熱心網友回復:
我會用一個入口點包裝腳本來做到這一點。一個 Dockerfile 可以同時有 anENTRYPOINT和 a CMD; 如果這樣做,則將CMD作為引數傳遞給ENTRYPOINT. 這意味著您可以制作ENTRYPOINT首次設定的 shell 腳本,然后exec "$@"用CMD.
#!/bin/sh
# docker-entrypoint.sh
# copy the configuration to the right place
cp configs var/opt/configs/
# run the main container command
exec "$@"
在 Dockerfile 中,確保COPY腳本(它應該作為可執行檔案簽入源代碼管理)并將其設定為ENTRYPOINT.
...
COPY docker-entrypoint.sh .
ENTRYPOINT ["./docker-entrypoint.sh"] # must be JSON-array syntax
CMD ["java", "-jar", "/app.jar"] # what was previously ENTRYPOINT
當您運行容器時,可以直接替換CMD,因此您可以通過運行互動式 shell 代替java應用程式來仔細檢查這是否正確。
docker run -v "$PWD/alt-configs:/configs" --rm -it my-image sh
如果您確實需要在docker run此時覆寫這樣的命令,您顯示的命令將&&用于連續運行兩個命令。這需要運行一個 shell 才能正確理解,在這種情況下,您需要手動提供一個/bin/sh -c包裝器。
我仍然建議在您的 Dockerfile 中更改ENTRYPOINT為CMD;那么你可以運行一個相對簡單的
docker run \
... \
-v "$PWD/alt-configs:/configs" \
my-image \
/bin/sh -c 'cp configs var/opt/configs && java -jar /app.jar'
如果你使用--entrypoint,它只會從這個命令中取出第一個單詞,而且它是一個 Docker 選項,所以它需要出現在影像名稱之前。我建議設計您的影像以避免需要這種笨拙的構造。
docker run \
... \
-v "$PWD/alt-configs:/configs" \
--entrypoint /bin/sh \
my-image \
-c 'cp configs var/opt/configs && java -jar /app.jar'
您提議的命令有問題,因為它試圖將整個命令(包括嵌入的空格和 shell 運算子)作為單個單詞傳遞,但這會導致作業系統級行程處理嘗試查找帶有空格和與符號的可執行檔案檔案名,因此出現“沒有這樣的檔案或目錄”錯誤。
轉載請註明出處,本文鏈接:https://www.uj5u.com/qukuanlian/338571.html
上一篇:為什么AWSCodePipeline抱怨“Dockerfile”和“Dockerrun.aws.json”?
下一篇:似乎可以關閉docker容器
