docker-compose在node_modules上的卷,但是是空的

我很新的Docker,我想映射我的计算机上的node_modules文件夹(用于debugging目的)。

这是我的docker-compose.yml

web: build: . ports: - "3000:3000" links: - db environment: PORT: 3000 volumes: - .:/usr/src/app - /usr/src/app/node_modules db: image: mongo:3.3 ports: - "27017:27017" command: "--smallfiles --logpath=/dev/null" 

我与Mac的Docker。 当我运行docker-compose up -d都一切正常,但是它在我的电脑上创build了一个node_modules文件夹,但是它是空的。 我进入我的容器的bash和ls node_modules,所有的包在那里。

我怎样才能得到我的电脑上的容器上的内容呢?

谢谢

TL; DR工作示例,克隆并尝试: https //github.com/xbx/base-server


您首先需要在计算机(外部映像)中使用node_modules进行debugging(在运行容器之前)。

如果你只想debuggingnode_modules:

 volumes: - /path/to/node_modules:/usr/src/app/node_modules 

如果你想debugging你的代码和node_modules:

 volumes: - .:/usr/src/app/ 

请记住,您至less需要在容器外部运行npm install (或者复制docker docker build生成的npm_modules)。 现在让我想想如果你需要更多的细节。


编辑 。 所以,在OSX中不需要npm,你可以:

  1. docker build然后docker cp <container-id>:/path/to/node-modules ./local-node-modules/ 。 然后在你的docker-compose.yml文件中安装这些文件,并且随心所欲。
  2. 或者, docker build和那里(Dockerfile)做npm install在另一个目录。 然后在你的命令(CMD或者docker-compose命令)中拷贝( cp )到正确的目录,但是这个目录是从你的计算机(docker-compose.yml中的一个卷)挂载的,然后麻烦你想要的东西。

编辑2.(选项2) 工作的例子,克隆和尝试: https //github.com/xbx/base-server我做了所有自动在这个repo分叉从你的。

Dockerfile

 FROM node:6.3 # Install app dependencies RUN mkdir /build-dir WORKDIR /build-dir COPY package.json /build-dir RUN npm install -g babel babel-runtime babel-register mocha nodemon RUN npm install # Create app directory RUN mkdir -p /usr/src/app WORKDIR /usr/src/app RUN ln -s /build-dir/node_modules node_modules # Bundle app source COPY . /usr/src/app EXPOSE 1234 CMD [ "npm", "start" ] 

泊坞窗,compose.yml

 web: build: . ports: - "1234:1234" links: - db # liaison avec la DB environment: PORT: 1234 command: /command.sh volumes: - ./src/:/usr/src/app/src/ - ./node_modules:/usr/src/app/node_modules - ./command.sh:/command.sh db: image: mongo:3.3 ports: - "27017:27017" command: "--smallfiles --logpath=/dev/null" 

command.sh

 #!/bin/bash cp -r /build-dir/node_modules/ /usr/src/app/ exec npm start 

请克隆我的回购和做docker-compose up 。 它做你想要的。 PS:可以改进,以更好的方式做同样的事情(即最佳实践等)

我在OSX中,它适用于我。

首先,有一个操作的顺序。 在构build映像时,卷不会被挂载,只有在运行容器时才会挂载。 因此,当您完成构build时,所有更改将只存在于图像中,而不是任何卷中。 如果你在一个目录上挂载一个卷,它会覆盖那个位置的图像,从视图中隐藏这些内容(有一个初始化exception,见下文)。


接下来是卷语法:

  volumes: - .:/usr/src/app - /usr/src/app/node_modules 

告诉docker-compose从当前目录创build一个主卷到容器内的/usr/src/app ,然后将/usr/src/app/node_modules到由/usr/src/app/node_modules维护的匿名卷。 后者将在docker volume ls显示为具有相对无用的长uuidstring的docker volume ls

要将/usr/src/app/node_modules到主机上的文件夹,您需要在上面包含文件夹名称和冒号。 例如/host/dir/node_modules:/usr/src/app/node_modules

命名卷与主机卷有点不同,因为在docker volume ls可以看到一个名字。 您只需使用名称而不是path来引用这些卷。 因此, node_modules:/usr/src/app/node_modules将创build一个名为node_modules的卷,您可以使用该名称在容器中装入卷。

我不同意描述命名卷,因为它们具有与主卷相关的function。 通过使用该位置的映像内容对其进行初始化,Docker可以帮助您处理已命名的卷。 因此,在上面的例子中,如果指定的卷node_modules是空的(或新的),它将首先将映像的内容复制到/ usr / src / app / node_modules到这个卷,然后将其挂载到容器中。

对于主机卷,您将永远不会看到任何初始化,无论在该位置,甚至是空目录,都是您在容器中看到的。 无法从该目录位置的映像中获取内容,以便首先将该内容复制到该位置的主机卷。 这也意味着容器内需要的目录权限不会自动inheritance,您需要手动设置容器内部的主机目录的权限。


最后,还有一个小问题,那就是用于Windows和Mac的Docker,它们在虚拟机内部运行,并且主机卷被挂载到虚拟机上。 要将卷装载到主机,必须将应用程序configuration为将主机中的文件夹共享到虚拟机,然后将虚拟机中的卷挂载到容器中。 默认情况下,在Mac上包含/ Users文件夹,但是如果使用其他目录,例如a / Projects目录,甚至小写/用户(unix和bsd区分大小写),则不会看到来自你的Mac里面的容器。


随着基础知识的覆盖,一个可能的解决scheme是重新devise你的工作stream程,从图像中的目录内容复制到主机。 首先,您需要将文件复制到图像中的其他位置。 然后,您需要将文件从保存的映像位置复制到容器启动时的卷安装位置。 当你做后者的时候,你应该注意到你打败了拥有一个容量(持久性)的目的,并且可能要考虑增加一些逻辑来更有select性地关于你何时运行这个拷贝。 首先,将一个entrypoint.sh添加到您的构build中,如下所示:

 #!/bin/sh # copy from the image backup location to the volume mount cp -a /usr/src/app_backup/node_modules/* /usr/src/app/node_modules/ # this next line runs the docker command exec "$@" 

然后更新您的Dockerfile以包含入口点和备份命令:

 FROM node:6.3 # Create app directory RUN mkdir -p /usr/src/app WORKDIR /usr/src/app # Install app dependencies COPY package.json /usr/src/app/ RUN npm install -g babel babel-runtime babel-register mocha nodemon RUN npm install # Bundle app source COPY . /usr/src/app RUN cp -a /usr/src/app/. /usr/src/app_backup EXPOSE 1234 ENTRYPOINT [ "/usr/src/app/entrypoint.sh" ] CMD [ "npm", "start" ] 

然后从docker-compose.yml中删除额外的音量:

  volumes: - .:/usr/src/app 

更改:

  volumes: - .:/usr/src/app - /usr/src/app/node_modules 

至:

  volumes: - .:/usr/src/app 

它会将node_modules放入本地映射卷中。 /usr/src/app/node_modules存储在不同的卷中,您需要通过docker inspect {container-name}来查找位置。 如果您确实想要指定位置,请将其指定为:

- /path/to/my_node_modules:/usr/src/app/node_modules