如何从另一个Docker容器中的内容提供服务/更新内容

时间:2019-12-09 04:16:10

标签: node.js docker nginx

我正在尝试运行nginx提供的NodeJS。我想代理到NodeJS服务器,并提供图片,CSS,JS等静态内容。

这是我的docker-compose文件:

version: "3.7"

services:
  web:
    build: .
    image: 127.0.0.1:5000/test
    volumes:
      - public:/app/public
    deploy:
      replicas: 2

  nginx:
    image: nginx:stable-alpine
    ports:
      - 80:80
    volumes:
      - ./nginx/nginx.conf:/etc/nginx/conf.d/default.conf:ro
      # share files from web
      - public:/static:ro

volumes:
  public:

我的Dockerfile运行npx webpack -p来构建所有静态文件(/app/public),然后使用node /app/src/server.min.js运行NodeJS服务器。 NodeJS为带有ajax端点的服务器端React提供服务,以最小化页面更新。正如我上面提到的,nginx容器提供静态内容(css,js,图像等)。

问题是我无法更新静态文件。创建并填充该卷后,这些文件将无法更改,即我无法更新CSS或JS。

通过docker-compose up或docker stack deploy可以看到此行为。

是否有某种方式可以重新创建卷,或在容器之间以其他方式提供文件?

1 个答案:

答案 0 :(得分:1)

您可以在此处采用三种基本方法。

首先是在构建时,将这些静态资产复制到Docker空间之外的某个位置,Nginx或其他可以托管这些静态资源的地方。如果您仍在AWS中运行,则可以直接在S3之外为它们提供服务;如果您在本地环境中,请使用主机路径而不是命名卷。这基本上只是避免了“仅在首次使用时”的卷行为,但是它需要在Docker之外进行一些工作。

您可以将相同的内容构建到两个图像中,而不必尝试使用卷共享它。您必须为nginx映像添加第二个Dockerfile,并且如果有某种构建管道(Webpack?)来构建静态内容,则必须确保其在前面运行。像

这样的Dockerfile行
COPY --from=127.0.0.1:5000/test /app/public /static

可能会工作。

您还可以让web映像在启动时手动复制其自身的数据,而不是依靠Docker来为您完成此操作。您可以有一个入口点脚本,例如

#!/bin/sh
if [ -d /static ]; then
  cp -r /app/public/* /static
fi
exec "$@"

将其添加到图像中,然后将共享卷安装在两个容器中的/static上。

所有这些情况都避免了Docker自动填充卷的行为。由于这个问题,我通常会尽量避免这种情况:它只会在您运行容器时第一次 发生,但实际上您经常进行更新,重新部署,等。,但是该卷已经存在,因此Docker将不会对其进行更新。 (尽管此行为可以在不进行修改的情况下运行标准Docker映像,但在Kubernetes中也根本不起作用。)

相关问题