将Let's Encrypt文件复制到Docker容器中

5

我不是docker的专家,只是在逐渐熟悉。我想将在主机上生成的ssl证书复制到我的docker容器中。我读过可以使用docker-compose文件中的volumes参数来实现,但在启动服务器时它总是提示无法在工作目录中找到已复制的文件。

文件结构

- repo
   - backend
      - api
         - static
            - ssl
         - dockerfile
   - frontend
   - docker-compose.yml

Dockerfile

FROM node:14-alpine

ENV NODE_ENV=production SERVER_PORT_HTTP=80 SERVER_PORT_HTTPS=443

WORKDIR /usr/src/app

RUN npm install

COPY . .

EXPOSE ${SERVER_PORT_HTTP} ${SERVER_PORT_HTTPS}

CMD [ "npm", "run", "start" ]

Docker-Compose

version: "3"

services:
  api:
    build:
      context: ./backend/api
    ports:
      - "80:80"
      - "443:443"
    volumes:
      - /etc/letsencrypt/live/api.example.com:/static/ssl
    restart: unless-stopped

实际错误是什么?是什么导致您的应用程序知道要查找“/static/ssl”目录;那个特定的目录是它通常期望找到证书的地方吗? - David Maze
1
如果在构建阶段不强制执行它,您可以使用docker cp - Marte Valerio Falcone
@DavidMaze 是的,我想通过让nodejs处理ssl来减少复杂性 - 相对于使用额外的容器和nginx。我告诉我的服务器在项目文件夹/static/ssl中查找证书。在我的主机上,我运行一个cronjob将证书更新到/etc/letsencrypt/live/api.example.com,但它不会将它们复制或链接到容器中。因此,我会得到“Error: ENOENT:没有这样的文件或目录,打开'./static/ssl/privkey.pem'”错误。 - nixn
当前目录下的./static/ssl与根目录下的/static/ssl不同。尝试将挂载目标更改为/usr/src/app/static/ssl - David Maze
1个回答

7

您所做的一切都是正确的,问题在于文件。如果您查看它们,您会发现它们不是普通的文件,而是链接:

root@fbe56bc38ad6:/# ls /etc/letsencrypt/live/example.com/ -l
total 4
-rw-r--r-- 1 root root 692 Jul 24  2020 README
lrwxrwxrwx 1 root root  44 Mar 22 00:03 cert.pem -> ../../archive/example.com/cert5.pem
lrwxrwxrwx 1 root root  45 Mar 22 00:03 chain.pem -> ../../archive/example.com/chain5.pem
lrwxrwxrwx 1 root root  49 Mar 22 00:03 fullchain.pem -> ../../archive/example.com/fullchain5.pem
lrwxrwxrwx 1 root root  47 Mar 22 00:03 privkey.pem -> ../../archive/example.com/privkey5.pem
lrwxrwxrwx 1 root root  42 Mar  1 12:57 example.com -> /etc/letsencrypt/live/example.com
lrwxrwxrwx 1 root root  33 Mar  1 12:57 ssl-dhparams.pem -> /etc/letsencrypt/ssl-dhparams.pem

所以您安装了一堆指向不存在位置的相对链接。

我建议在容器中将/etc/letsencrypt挂载到/etc/letsencrypt

    volumes:
      - /etc/letsencrypt:/etc/letsencrypt

然后使您的应用程序查找位于/etc/letsencrypt/live/example.com的文件,或在/static/ssl上创建另一个指向/etc/letsencrypt/live/example.com的链接:

ln -s /etc/letsencrypt/live/example.com /static/ssl

谢谢您提供的解决方案。它可以直接使用,唯一需要注意的是,我必须像您提到的那样,在服务器配置中放置绝对路径以加载证书。您能否向我展示如何在docker-compose文件中创建您答案中的第二个链接的示例? - nixn
1
@nixn 很抱歉,您无法轻松地使用docker-compose管理链接。不过,您可以使用Dockerfile创建一个:RUN mkdir /static && ln -s /etc/letsencrypt/live/example.com /static/ssl - anemyte

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接