删除所有
volumes:
文件中的块。更具体地说,删除
卷:
安装在图像上的
/app
目录
这里发生的情况是,中有一个旧的应用程序副本
nextjs-app-build
命名卷。您成功地重建了映像,但随后将卷装载到其内容上,命名卷的内容完全替换了重建映像中的内容。
看起来您正试图利用特定Docker命名卷的特定行为,将文件从一个容器共享到另一个容器。当您将Docker命名的卷装载到容器(以及
只有
Docker命名的卷,而不是绑定装载或Kubernetes PersistentVolumeClaim或其他任何东西),第一次使用该卷时(以及
只有
如果卷完全为空),则将图像中的内容复制到卷中。这将导致第一个图像的内容被复制到卷中,然后将卷装入第二个容器中。但是,如果你更新了图像内容,卷就不会更新(Docker对其内容一无所知,并假设它有某种用户数据),你就会得到这种行为。
这就引出了一个问题:你的静态资产是如何进入反向代理的?
最简单的解决方案就是不去麻烦。在最现代的应用程序框架中,您可以在应用程序本身中设置一个静态文件服务器。这时,您可以将请求转发到后端,并让它处理自己的文件。
# in your nginx config
location / {
proxy_pass http://nextjs-app:3000/;
# with no try_files
}
另一种选择是
COPY
将文件转换为Nginx代理映像。您可以在同一个Dockerfile中执行此操作,作为结尾的附加阶段
FROM nginx AS proxy
COPY --from=builder /app /app # (...or to /var/www/html?)
COPY ./nginx-docker/convert-nginx.sh /etc/nginx
CMD ["/etc/nginx/convert-nginx.sh"]
然后在Compose文件中,您需要指定要使用Dockerfile的哪一部分。
version: '3.8'
services:
build:
context: .
target: runner # <-- add
restart: always
ports:
- '3000:3000'
nginx:
image: csrinu236/medium-nginx-app # Placeholder for pushing image to Dockerhub
build:
context: . # <-- change to top-level directory (same as app)
target: proxy # <-- add
depends_on:
- nextjs-app
restart: always
ports:
- '80:80'
- '443:443'
# also note no volumes:, and using the default Compose-provided networks:
你也可以
COPY --from
一个图像名称,它将允许您保留两个独立的Dockerfile(假设您正在分配
image:
两者的名称)。其中的一个技巧是Compose无法对图像构建进行排序,因此您必须先手动构建应用程序,然后再手动构建代理。