无法从env_file中声明的文件读取环境变量 [英] Failed to read environment variables from the file declared in env_file

查看:106
本文介绍了无法从env_file中声明的文件读取环境变量的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在我的docker-compose.yml中,我定义了两个服务, app db .

In my docker-compose.yml, I defined two services, app and db.

version: "3.7"

services:
  app:
    image: my_app
    container_name: my-app
    ports:
      - ${MY_PORT}:${MY_PORT}
    env_file:
      - ./app.env
    ...
    depends_on:
      - db
    environment:
      - DATABASE_URL=${DB_URL}
  db:
    image: my_db
    container_name: my-db
    env_file:
      - ./db.env
    ports:
      - ${DB_PORT}:${DB_PORT}

如上所述,我在 env_file 选项中定义了两个env文件,分别是 app.env db.env .code> app 和 db 服务.

As you can see above, I have defined two env files, app.env and db.env in the env_file option of app and db services.

app.env:

MY_PORT=8081

db.env:

DB_PORT=4040
DB_URL=postgres://myapp:app@db:4040/myapp

我想检查我的docker-compose是否可以成功读取环境变量.因此,我运行命令 docker-compose config .但是输出是

I want to check if my docker-compose can successfully read the environment variables. So, I run the command docker-compose config. However the output is

$ docker-compose config
WARNING: The MY_PORT variable is not set. Defaulting to a blank string.
WARNING: The DB_URL variable is not set. Defaulting to a blank string.
WARNING: The DB_PORT variable is not set. Defaulting to a blank string.
ERROR: The Compose file './docker-compose.yml' is invalid because:
services.app.ports is invalid: Invalid port ":", should be [[remote_ip:]remote_port[-remote_port]:]port[/protocol]
services.db.ports is invalid: Invalid port ":", should be [[remote_ip:]remote_port[-remote_port]:]port[/protocol]

为什么我的docker compose无法从我在docker-compose.yml中的 env_file 选项中声明的那些env文件中读取环境变量?

Why my docker compose can't read environment variables from those env files I declared in the env_file option in my docker-compose.yml?

此外,我还有另一个问题,那就是我知道通常不应该对环境文件进行版本控制,因为它可能包含凭据.env文件应如何正常用于不同的环境,例如开发,登台和生产环境?成像不同的环境对于这些变量具有不同的值.有人可以提供一些例子吗?

Besides, I have another question, that's I understand that normally the env file shouldn't be version controlled since it could contain credentials. How normally should the env file be used for different environment e.g. development, staging and production environments? Imaging different environment has different values for those variables. Could someone please provide some examples?

推荐答案

失败的原因是,您正在定义外部变量 app.env 的环境变量db.env 文件(并在 env_file 选项中指定)仅在启动的容器内设置-而不用于docker-compose内部的变量扩展.yml 文件,由docker-compose解析.

The reason this is failing, is that the environment variables that you are defining the the external named app.env and db.env files, and specifying in the env_file option, are only being set inside the container that is started - and are not used for variable expansion inside the docker-compose.yml file when parsed by docker-compose.

这很容易与在与 docker-compose.yml 文件相同位置提供名为 .env 的文件的选项混淆.由于docker-compose会在 docker-compose.yml 文件(或您用指定的文件旁边)旁边查找专门命名为 .env 的文件> -f 开关)-并在解析文件之前,使用该文件中的环境变量在 docker-compose.yml 文件中进行变量扩展.

This is easily confused with the option of supplying a file named .env in the same location as the docker-compose.yml file. Since docker-compose will look for a file specifically named .env next to the docker-compose.yml file (or next to the file that you are specifying with the -f switch) - and use the environment variables in that file for variable expansion in the docker-compose.yml file, before parsing it.

换句话说:

  • 将在容器内设置环境变量只是一项方便的功能,它使您可以从 docker-compose.yml 文件
  • 中外部化环境变量.在由docker-compose解析之前,这些文件中的
  • 环境变量将用于 docker-compose.yml 文件中的变量扩展.
  • Will set environment variables inside your container, is is just a convenience feature that allows you to externalise the environment variables from the docker-compose.yml file
  • Environment variables in these files will NOT be used for variable expansion in the docker-compose.yml file before parsed by docker-compose.
  • 在解析之前将用于 docker-compose.yml 文件内的环境变量扩展.
  • 设置启动容器内的环境变量.
  • Will be used for environment variable expansion inside the docker-compose.yml file before parsing.
  • Will NOT set environment variables inside the started container.

如果将值迁移到单个 .env 文件中,并将其与 docker-compose.yml 文件放置在同一目录中,这应该可以工作.

If you migrate your values into a single .env file and place it in the same directory as your docker-compose.yml file, this should work.

据我所理解的第二个问题,您在问应该如何使用 .env 文件或 env_file 选项为不同的环境配置服务.

As I understand your second question, you are asking how the .env file, or the env_file option should be used to configure your services for your different environments.

我认为对此没有一个简单而单一的答案.它可以通过多种方式解决.但这还取决于您要部署到什么?是kubernetes吗?Docker群?还是只有一个节点的Docker主机?

I do not think that there is a simple and single answer to this. It can be solved in a number of ways. But it also depends on what you are deploying to? Is it kubernetes? Docker swarm? Or just a single node docker host?

Kubernetes和Docker群有不同的方法来帮助您解决这一问题.

Kubernetes and Docker swarm have different means of helping you out with this.

这些是高度安全的解决方案,其中可以限制秘密操作员,并且秘密信息不会被没有访问权限的开发人员或操作员看到.

Those are highly secure solutions, where operators of the secrets can be limited, and the secrets will not be seen by developers or operators that do not have access.

但是对于单节点泊坞窗主机,不是以群集模式运行(秘密仅在群集模式下工作),确实没有很多不错的选择.据我所知,您将不得不在构建中手动管理此问题并部署管道.

But for the single node docker host, not operating in swarm mode (secrets only work in swarm mode), there really isn't a lot of fancy options. You will have to manage this pretty manually in your build and deploy pipes as far as I am aware.

您很对,服务的敏感配置不应与服务定义放在同一存储库中.数据库的root密码或生产环境的服务发现服务的凭据之类的内容无需位于源旁边.

You are right that the sensitive configuration of your services, should not go in the same repository as the service definition. Things like root password for a database, or credentials to your service discovery service for your production environment do not need to live next to the sources.

传统上,另一个存储库将包含此存储库-给您机会限制具有此访问权限的人群.构建/部署服务器/服务将签出您的服务的新修订版,也许会对其进行构建,然后签出配置存储库,并从那里开始使用配置进行服务.并且,请确保随后删除配置文件.

Traditionally, another repository would contain this - giving you the oppotunity to limit the group of people that have this access. The build/deployment server/service will check out the new revision of your service, build it perhaps, and then check out the configuration repository and start the services with the configurations from there. And, make sure to remove the configuration files afterwards.

对于单个节点docker主机部署方案,这将是我推荐的解决方案-两个存储库,以及一些脚本,这些脚本可确保在部署期间放置正确的.env文件,然后再次将其删除.

That would be the solution I would recommend for a single node docker host deployment regime - two repositories, and some scripting that ensures that the correct .env file is put in place during deployment, and removed again.

我希望这对您有帮助吗?

I hope this is helpful?

这篇关于无法从env_file中声明的文件读取环境变量的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆