我包含了我在下面的github repo上写的README的内容。
Dockerfile
的简单nodejs项目。/
),它从package.json
打印本地npm依赖项的版本。这用于验证测试用例过程的结果。node_modules
覆盖在第一个卷的顶部。docker rm
和docker rmi
清除与此repo项目相关的所有先前容器和图片。test2_run1
标记。此状态表示使用本地NPM依赖项1.0.0版的项目。docker-compose build
。如果正确执行了步骤2,则所有步骤都应该在没有任何缓存使用的情
请注意npm install
命令期间本地NPM依赖关系的版本,例如: +-- my-npm@1.0.0
。docker-compose up
。浏览到http://localhost:8000
。该页面应报告版本1.0.0
。up
命令的终端上的Ctrl-C。)test2_run2
标记。这会将a small change引入NPM的index.js
文件和版本
将package.json
添加到1.0.1
。docker-compose build
。 只有COPY ./my-npm ...
之前的说明才能使用缓存。(例如,docker输出会为该指令输出---> Using cache
。)所有后续步骤都应由docker运行。这是因为步骤7中引入NPM包的更改应该使COPY ./my-npm ...
命令的高速缓存无效,因此,后续步骤也是如此。确认在npm install
命令期间,新摘要的NPM将打印在摘要树输出中,例如, +-- my-npm@1.0.1
。docker-compose up
。浏览到http://localhost:8000
。该页面应报告版本1.0.1
。预期行为:步骤9中的页面应报告1.0.1
。也就是说,本地npm的变化应该通过docker-compose up
反映在容器中。
实际行为:步骤9中的页面报告1.0.0
。
请注意,docker本身正在按预期重新构建图像。观察到的问题不是docker重新使用缓存的图像,而是输出
显示它重新运行NPM安装并显示本地NPM依赖项的新版本。问题是docker-compose
没有看到
构成dctest_service1
容器的基础图像已更新。
事实上,在容器中运行bash可以让我们看到容器有更新的my-npm
模块文件,但是node_modules
版本陈旧:
# docker exec -it dctest_service1_1 bash
app@6bf2671b75c6:~/service1$ grep version my-npm/package.json node_modules/my-npm/package.json
my-npm/package.json: "version": "1.0.1",
node_modules/my-npm/package.json: "version": "1.0.0"
app@6bf2671b75c6:~/service1$
解决方法:使用docker rm
删除dctest_service1
容器。然后重新运行docker-compose up
,它将使用现有图像重新创建容器。值得注意的是,此步骤不会重建基础图像。在重新创建容器时,docker-compose
似乎想要使用具有更新node_modules
的较新卷。
请参阅output
目录,了解第一次运行(步骤4和5)和第二次运行(步骤8和9)期间打印的输出。
我基于this tutorial ("Lessons from Building a Node App in Docker")得到了nodejs
Dockerfile
。具体来说,请注意本教程使用卷技巧将node_modules
目录从容器本身挂载到主机上等效的目录之上。 E.g:
volumes:
- .:/home/app/my-app
- /home/app/my-app/node_modules
我遇到了一个问题,即package.json的更新按预期触发npm install
(与使用docker缓存相反),但在使用docker-compose up
启动服务时,结果容器以某种方式最终得到了node_modules
数据的旧版本,因为目录中缺少新添加的NPM包。但是,如果通过CMD
手动运行指定的docker-compose run --rm
,那么我执行会看到更新的卷!
我可以通过以下几种方式确认:
node_modules
时间戳容器通过" up":
启动app@88614c5599b6:~/my-app$ ls -l
...
drwxr-xr-x 743 app app 28672 Dec 12 16:41 node_modules
通过"运行"
启动容器app@bdcbfb37b4ba:~/my-app$ ls -l
...
drwxr-xr-x 737 app app 28672 Jan 9 02:25 node_modules
docker inspect
" Mount"条目号容器通过" up":
启动"Name": "180b82101433ab159a46ec1dd0edb9673bcaf09c98e7481aed7a32a87a94e76a",
"Source": "/var/lib/docker/volumes/180b82101433ab159a46ec1dd0edb9673bcaf09c98e7481aed7a32a87a94e76a/_data",
"Destination": "/home/app/my-app/node_modules",
通过"运行"
启动容器"Name": "8eb7454fb976830c389b54f9480b1128ab15de14ca0b167df8f3ce880fb55720",
"Source": "/var/lib/docker/volumes/8eb7454fb976830c389b54f9480b1128ab15de14ca0b167df8f3ce880fb55720/_data",
"Destination": "/home/app/my-app/node_modules",
我不确定这是否相关,但我也注意到(docker inspect
)Binds
下HostConfig
部分"Binds": [
"180b82101433ab159a46ec1dd0edb9673bcaf09c98e7481aed7a32a87a94e76a:/home/app/my-app/node_modules:rw",
"/Volumes/my-mount/my-app:/home/app/my-app:rw"
],
部分在两个案例之间有所不同:
容器通过" up":
启动"Binds": [
"/Volumes/my-mount/my-app:/home/app/my-app:rw"
],
通过"运行"
启动容器node_modules
(两者都显示主机信号源安装在图像上,但只有" up"显示带有docker-compose up
的辅助叠加音量,这似乎是另一个奇怪的皱纹。)
根据docker-compose CLI reference:
如果有服务的现有容器和服务 容器创建后,配置或映像已更改, docker-compose up通过停止和重新创建来获取更改 容器
因此,看起来--force-recreate
认为配置或图像没有改变。我只是不确定如何调试这个来确认。当然,我可以使用docker-compose build
来解决这个问题,但我想解决一下我的配置错误导致问题的原因。
更新:如果我在docker-compose up
之前做了明确的Dockefile
,问题仍然存在。因此,我现在对这一理论缺乏信心。
以下是整个FROM node:6.9.1
RUN useradd --user-group --create-home --shell /bin/false app
ENV HOME=/home/app
ENV APP=my-app
ENV NPM_CONFIG_LOGLEVEL warn
RUN npm install --global gulp-cli
COPY ./package.json $HOME/$APP/package.json
RUN chown -R app:app $HOME/*
USER app
WORKDIR $HOME/$APP
RUN npm install && npm cache clean
USER root
COPY . $HOME/$APP
RUN chown -R app:app $HOME/* && chmod u+x ./node_modules/.bin/* ./bin/*
USER app
ENTRYPOINT ["/home/app/my-app/bin/entrypoint.sh"]
CMD ["npm", "run", "start:dev"]
:
{{1}}
答案 0 :(得分:2)
命令docker-compose
使用docker-compose.yml文件作为容器service
的配置文件。默认情况下,它会在您运行的目录docker-compose
中查找此.yml配置文件。
所以可能是你的docker-compose.yml文件不是最新的,因为当你运行docker-compose up
时,你的某个卷没有被挂载。
docker run
忽略docker-compose.yml文件,只使用Dockerimage
构建容器。因此Dockerimage
文件和docker-compose.yml
文件之间可能存在配置差异。