Dockerfile 'COPY' command not copying files

I am running into a frustrating problem when trying to create and run a new docker container. When I upload my code to a Github repository and then use Docker Hub to build it, the build completes without any errors. However, when I try to create and then run the new container on my own server I find that the necessary files and directories have not been copied into the new container or into the local directories that were bound to the container directories (obviously). Strangely though, it does seem that the init.sh script referenced at the end of my Dockerfile is being copied because it runs, but it fails because the other files that were supposed to be copied into the WORKDIR are not there. I’ve tried different files structures and COPY commands to no avail, and all of the files and directories to be copied are in the root of the repository at the moment. Here is my current Dockerfile:

FROM node:latest

RUN mkdir -p /usr/src/app

WORKDIR /usr/src/app

COPY package*.json /usr/src/app/

RUN \
  npm install -g @adonisjs/cli && \
  npm install

COPY . /usr/src/app/

VOLUME /usr/src/app

RUN \
  cp /usr/src/app/init.sh /usr/local/bin/ && \
  chmod 755 /usr/local/bin/init.sh && \
  ln -s usr/local/bin/init.sh / # backwards compat

EXPOSE 8080
CMD ["/init.sh"]

And my docker create and docker run commands:

docker create --name='ferdi-server' -p '3333:80' -v '/mnt/cache/appdata/ferdi-server':'/usr/src/app' 'xthursdayx/ferdi-server-docker' 

docker run -d --name='ferdi-server' -p '3333:80' -v '/mnt/cache/appdata/ferdi-server':'/usr/src/app' 'xthursdayx/ferdi-server-docker'

Any ideas? I’ve been trying to figure this out for two days and am at a dead end.

FYI here are the file structures and COPY commands I’ve most recently tried

β”œβ”€β”€ Dockerfile
β”œβ”€β”€ init.sh
β”‚   └── api
β”‚       β”œβ”€β”€ package.json
β”‚       β”œβ”€β”€ package-lock.json
β”‚       β”œβ”€β”€ .env.example
β”‚       β”œβ”€β”€ etc
β”‚       β”œβ”€β”€ init.sh
β”‚       └── app
β”‚       |   └── directory
β”‚       └── config
β”‚           └── app.js
β”‚           └── etc.js

with command COPY api/ /usr/src/app/

and

β”œβ”€β”€ Dockerfile
β”œβ”€β”€ init.sh
β”œβ”€β”€ package.json
β”œβ”€β”€ package-lock.json
β”œβ”€β”€ .env.example
β”œβ”€β”€ etc
β”œβ”€β”€ init.sh
β”‚   └── app
β”‚   └── directory2
β”‚   └── config
β”‚       └── app.js
β”‚       └── etc.js

with command COPY . /usr/src/app/

Hello
Why are you use Copy and volume both command use in the dockerfile
COPY . /usr/src/app
VOLUME /usr/src/app
Copy command is a copy hole the source Folder to the destination Folder
or
Volume command is a Connected to your folder to container Folder

I’m not sure I totally understand your reply.

My intention was to use COPY . /usr/src/app (or COPY app/ /usr/src/app) to copy all the code in my docker repository into a directory (/usr/src/app) in the newly created docker container. I then was trying to use VOLUME to make this same directory connectable from the host.

I’ve seen many Dockerfiles that do this exact thing, so I’m confused why you seem to be saying that it is wrong to use both.

Yes you are right.
You can use Both copy and volume command but you are using copy and volume command to attach same directory

can you try to absolute path β€œCOPY . /usr/src/app/” instead of use dot

If you map a bind to a volume (this is what your docker run examples do), it will replace the entire folder in the container. The pre-existing files in the target folder effectivly become unavailable.

If you need to preserve files from the target folder, you will need to use a named volume, as its default behavior is to copy per-existing files into the volume. Now here is the fun part: you can create a named volume using the local driver of the type bind.

Thanks for the reply @meyay I think your suggestion is probably what I want to do, but I’m confused because I’ve run plenty of other people’s docker containers which used bind mounted directories that have had things copied into them during the build process. However, I’m not sure what they do differently.

Thanks for clarifying @rrpnarola that makes sense to me. I’ll try this out.

Clear as mud. Are you referring to a clarification that was made privately? Please share?

1 Like

I just wanted to chip in and say, having resolved a similar problem, that in my case the issue was with volume mirroring that I had set up in an upstream docker compose file driving the dockerfile. In my case I was mirroring my local directory with the working folder (so that my local changes could be reflected live in the container, which I actually didn’t need…). The volume mirroring happens at run time after the copy commands in my dockerfile had run, and ends up replicating my local folder to the working folder in the container, wiping the copy commands run during the build. In this thread, I believe OP had the same issue.

So it’s a gotcha to watch for when working with dockerfiles and mounted volumes!

Are you sure you meant to use the words mirroring and replication in the context of volumes?

When a host path is used as volume source, this host path will be bind mounted into the container path. This mount will eclipse the original content of the container path. Whatever changes are done in either location will happen in the same physical folder in the host’s file system.