Docker组合:确保在运行CMD之前安装卷

我已经build立了一个容器,它有nginx和HTTPS里面的一些configuration。 证书由另一个容器使用https://letsencrypt.org/自动生成。 nginx容器还提供了一些默认的自签名证书,直到certbot容器生成好的为止。 这是我的configuration看起来如何:

version: '2' services: # Nginx, the master of puppets, listens in port 80 nginx: image: mycompany/nginx:v1.2.8 depends_on: [api, admin, front, postgres, redis, certbot] ports: ["80:80", "443:443"] volumes: - acme_challenge:/var/www/acme_challenge - ssl_certs:/var/certs environment: ACME_CHALLENGE_PATH: /var/www/acme_challenge # Where will the container put the default certs DEFAULT_SSL_CERTS_PATH: /var/default_certs # Use temporary self signed keys by default SSL_CERTIFICATE: /var/default_certs/selfsigned.crt SSL_CERTIFICATE_KEY: /var/default_certs/selfsigned.key # Once certbot generates certs I change config to this and recreate the container # SSL_CERTIFICATE: /var/cerst/mycompany.com/fullchain.pem # SSL_CERTIFICATE_KEY: /var/certs/mycompany.com/privkey.pem # Certbot renews SSL certificates periodically certbot: image: mycompany/certbot:v1.0.9 restart: on-failure:3 environment: - WEBROOT_PATH=/var/www/acme_challenge - SIGNING_EMAIL=info@yavende.com - DOMAINS=mycompany.com, api.mycompany.com volumes: - acme_challenge:/var/www/acme_challenge - ssl_certs:/etc/letsencrypt/live volumes: acme_challenge: ssl_certs: 

这或多或less是如何工作的:

  • nginx容器被configuration为使用一些自签名证书
  • docker docker compose up -d并行启动certbot和nginx。
  • 同时certbot运行一个进程来生成证书。 假设这个成功了。
  • 过了一段时间,我连接到nginx容器并运行ls /var/certs和certbot生成的证书在那里。 太好了!

  • 我修改了nginx容器的configuration以使用这些新证书(通过env vars SSL_CERTIFICATE *)并重新创build容器。

  • Nginx无法运行,因为这些文件不存在,即使我知道这些文件在那里(用很多方法检查)

我怀疑图像( CMD )的命令是否运行,而不pipe是否还附着到容器的卷。 这是真的? 我应该写一些bash等到这个文件存在吗?

免责声明:这是我自己的docker形象插件。

为了达到这个目的,我做了一个很好的基于nginx的docker镜像,具有诸如自动letsencryptpipe理,http基本authentication,虚拟主机等function,通过一个简单的jsonconfiguration通过一个环境variables来pipe理。 我在生产中使用它,所以它是稳定的。

你可以在这里find它,在tcjn/json-webrouter

所有你需要做的就是把这样的东西传递给CONFIG环境variables:

 {"servers": [ {"ServerName": "example.com", "Target": "192.168.2.52:32407", "Https": true}, {"ServerName": "*.example.com", "Target": "192.168.2.52:4444", "Https": true}, {"ServerName": "secret.example.com", "Target": "192.168.2.52:34505", "Https": true, "Auth": {"Realm": "Login for secret stuff", "Set": "secret_users"}} ], "auth": { "secret_users": {"bob": "HASH GENERATED BY openssl passwd"} }} 

是的,它就像"Https": true一样简单"Https": true 。 你可以在github回购中find所有可能的选项。