使用卷的docker-compose up“没有该文件或目录”

3

我是一个docker初学者,尤其是docker compose方面。在创建我的初始简单的docker环境时,我遇到了第一个错误,但是我不知道为什么会出现这个错误。我在stackoverflow上尝试寻找解决方案,但没有找到可以帮助我的内容。

$ docker-compose up
Removing errorinstance_app_1
Recreating 8a358dfcb306_8a358dfcb306_8a358dfcb306_errorinstance_app_1 ...
Recreating 8a358dfcb306_8a358dfcb306_8a358dfcb306_errorinstance_app_1 ... error
ERROR: for 8a358dfcb306_8a358dfcb306_8a358dfcb306_errorinstance_app_1 Cannot start service app: oci runtime error: container_linux.go:265: starting container process caused "exec: \"./run.sh\": stat ./run.sh: no such file or directory"
ERROR: for app Cannot start service app: oci runtime error: container_linux.go:265: starting container process caused "exec: \"./run.sh\": stat ./run.sh: no such file or directory"
ERROR: Encountered errors while bringing up the project.

以下是我的文件夹结构:

  • Project
    • docker-compose.yml
    • Docker
      • Java
        • Dockerfile
    • src
      • run.sh

以下是我的docker-compose.yml:

 version: '2'
    services:
      app:
        build:
            dockerfile: ./Docker/Java/Dockerfile
            context: .
        volumes:
            - ./src:/usr/local/etc/
        working_dir: /usr/local/etc/
        command: ./run.sh

以下是我的 Docker 文件:

FROM java:7-jdk-alpine
# WORKDIR /usr/local/etc

run.sh

echo "Hello world."

是的,我知道我可以在docker-compose文件中实现这个解决方案。但是将来我需要扩展Dockerfile。

有人能帮帮我吗?或者有人看到问题了吗?


1
请问您能否更改命令:/bin/bash,并检查脚本是否存在于/usr/local/etc/目录中以及它具有哪些权限? - Sergiu
注释掉该命令,启动一个bash会话。一旦进入,您应该在提到的工作目录中...还要像@Sergiu提到的那样检查执行权限。 - sebagomez
更改命令时,我收到了“未找到”异常。将该命令直接放在Dockerfile中会出现“/bin/sh:bash:未找到”的错误。将该命令放在docker-compose文件中会出现“ERROR:for java 无法启动服务app:oci运行时错误:container_linux.go:265:启动容器进程导致“exec:\”/bin/bash\“:stat /bin/bash:没有那个文件或目录”。也尝试过只使用“bash”。 - SNO
将CMD /bin/bash直接添加到dockerfile中并运行docker run -it <nam> /bin/bash。它可以工作。但为什么无法从docker-compose文件中运行bin/bash命令? - SNO
4个回答

2
问题出在您在dockerfile中使用的基础docker镜像上:
FROM java:7-jdk-alpine

您正在尝试通过运行run.sh bash脚本来启动容器。但是上述镜像本身不支持bash

您可以在此处查看上述镜像的文档。引用必要部分如下:

java:alpine

...

为了最小化镜像大小,Alpine-based镜像通常不包含其他相关工具(例如git或bash)。使用此镜像作为基础,在您自己的Dockerfile中添加所需内容(如果您不熟悉,请参阅alpine镜像说明以了解如何安装软件包)。

这就是问题所在。

现在,我可以想到两个解决方案:

  1. Just use java:7-jdk as base image instead of java:7-jdk-alpine
  2. Install bash on top of the base image java:7-jdk-alpine by changing dockerfile to:

    FROM java:7-jdk-alpine
    RUN apk update && apk upgrade && apk add bash
    #WORKDIR /usr/local/etc
    

    *source of steps to install bash in alpine linux is here


0
最简单的解决方法是在容器中执行bash会话,然后在容器内部检查指定路径中是否存在文件。如果文件不在路径中,则必须在创建图像时通过Dockerfile或通过docker-compose中的卷包含该文件。
另一个要检查的事项是您正在使用的相对路径。当您检查docker容器中文件的存在性时,这将变得清晰。
我建议您在docker-compose文件中创建一个卷,因为这是最简单和最好的方法。
我有一个问题想问你,为什么要将Dockerfile文件放在Java路径中?
这不是一个好主意或者遵循的指导方针。 正确的方法是将dockerfile文件放入环境文件夹中,这样dockerfile文件就与应用程序的java源代码无关了。

谢谢您的答复。我还有以下附加问题:如何运行docker exec -it CONTAINER_NAME bash命令?目前我的docker-compose抛出了文件未找到错误,因此我没有任何正在运行的实例可以运行此命令。您说的环境文件夹是什么意思?能给我一个例子吗?非常感谢。 - SNO

0

我经常遇到这个错误,经过大量的调查,发现一些图像文件已经损坏了。

删除这些文件并重新构建解决了问题。这不是Docker安装或配置本身的问题。


0

看起来docker compose找不到你的run.sh文件。这个文件需要包含在你的docker镜像中。

将你的Dockerfile更改为以下内容,然后使用docker build -t <YOUR_IMAGE_NAME> .重新构建镜像。

FROM java:7-jdk-alpine
ADD run.sh /usr/local/etc/run.sh

当你的镜像重建完成后,再次运行docker-compose up命令。


1
非常感谢您的帮助。我有一个问题。我的理解是,docker-compose中的“volumes”设置应该将文件映射到镜像中,这样我就不需要添加任何文件了? - SNO
1
docker-compose的volumes将文件映射到正在运行的容器中(即在容器运行时),而不是镜像。在您的docker-compose配置中,您正在说“启动容器时运行run.sh脚本”,但是run.sh不存在,因为它不是镜像的一部分。run.sh文件需要在构建时添加。 - grizzthedj
1
啊,好的。知道了。所以,假设我有多个文件由run.sh触发。我需要“ADD”所有这些文件吗?你有什么“最佳实践”可以告诉我如何以清晰的方式处理它?对于开发,我的源文件夹包括Java文件太大(几个GB),每次都要添加所有文件或始终构建新的Docker映像。 - SNO
您可以添加整个目录,这样您就不必在Dockerfile中执行多个“ADD”语句。由于您已经有一个卷将本地开发文件夹“src /”映射到“/ usr / local / etc /”,因此您不应该在每次代码更改后重新构建镜像。只有在部署到DEV,QA或PROD环境时才需要重新构建。 - grizzthedj

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接