Docker compose拒绝应用环境变量



UPDATE
问题似乎与Dockerfile中的RUN命令有关。如果我删除它,构建会很好,而且环境变量显然会被提取,因为密码已经应用,我可以使用它进行连接。我不确定RUN命令中登录失败的原因,我见过很多使用类似代码的例子。

我正在编写一个非常基本的docker compose文件,为应用程序设置开发环境,我从数据库服务器开始,它是MSSQL。以下是docker-compose.yml文件的样子:

version: '3.8'
services:
mssql:
build:
context: .
dockerfile: docker/mssql/Dockerfile
ports:
- '1434:1433'
environment:
ACCEPT_EULA: "Y"
SA_PASSWORD: "YourStrong!Passw0rd"
volumes:
- mssql-data:/var/opt/mssql

正如你从我的dockerfile路径中看到的,它在一个子路径中,看起来像这样:

FROM mcr.microsoft.com/mssql/server:2019-latest
COPY ./docker/mssql/TESTDB.bak /var/opt/mssql/backup/TESTDB.bak
RUN ( /opt/mssql/bin/sqlservr --accept-eula & ) | grep -q "Service Broker manager has started" && /opt/mssql-tools/bin/sqlcmd -S localhost,1433 -U SA -P "YourStrong!Passw0rd" -Q 'RESTORE DATABASE TESTDB FROM DISK = "/var/opt/mssql/backup/TESTDB.bak" WITH MOVE "TESTDB_Data" to "/var/opt/mssql/data/TESTDB.mdf", MOVE "TESTDB_Log" to "/var/opt/mssql/data/TESTDB_log.ldf"'

(是的,我意识到RUN命令中的密码是多余的,我早些时候曾尝试在那里使用一个变量,由于它不起作用,我对它进行了硬编码。(

当我运行docker compose-up-d时,我总是收到这样的错误:

用户‘SA’登录失败我浪费了太多时间认为密码确实有问题,直到我意识到如果我直接在Dockerfile中添加环境变量,它就会起作用。所以在我的Dockerfile中,在RUN命令之上,我可以这样做:

ENV ACCEPT_EULA=Y
ENV SA_PASSWORD=YourStrong!Passw0rd

所以我得出结论,我的环境变量根本没有被读取。我尝试使用引号,不使用引号,而是使用env_file,但似乎什么都不起作用。我还尝试了以下格式,但没有成功:

environment
- ACCEPT_EULA=Y
- SA_PASSWORD=YourStrong!Passw0rd

我还尝试使用MSSQL_SA_PASSWORD而不是SA_PASSWORD,并且两者都在其中。我认为这不太可能是问题所在,尽管SA_PASSWORD运行良好。最后,我尝试使用2017年的图像,以防它是特定于图像的,但也不起作用。

我想一定是我错过了什么愚蠢的东西。我在词根中看到很多关于.env的讨论是不同的,但如果我理解正确的话,当人们试图在他们的docker-compose.yml文件中使用环境值时,他们会出错,这不是我在这里所做的。所以我准备在这件事上失去理智,因为这似乎是一件简单、基本的事情。

我认为您将Dockerfile中的ENV语句与运行映像时设置的环境变量混淆了。关键仍然在于文档的细节。它指出,它们与说dockerrun-e相同,而不是说dockerbuild。

造成更多混乱的是,当您使用ENV时,您正在为稍后运行图像时设置默认值:

https://docs.docker.com/engine/reference/builder/#env

如果你还没有,我非常建议你在继续撰写之前熟悉构建和运行你的图像,使用dockerrun和dockerbuild,这样就不会那么令人困惑了。

此处的构建问题源于构建时间运行时环境变量之间的混淆:使用environmentenv_file属性可以指定要为服务容器设置的环境变量

但是Dockerfile中的RUN命令是在映像的构建时执行的!要在构建新映像时传递变量,您应该使用构建args,正如您在评论中提到的:

services:
mssql:
build:
context: .
dockerfile: docker/mssql/Dockerfile
args:
SA_PASSWORD: "YourStrong!Passw0rd"
# ...

有了这个,您可以使用SA_PASSWORD作为构建ARG:

FROM mcr.microsoft.com/mssql/server:2019-latest
COPY ./docker/mssql/TESTDB.bak /var/opt/mssql/backup/TESTDB.bak
ARG SA_PASSWORD
RUN ( /opt/mssql/bin/sqlservr --accept-eula & ) | grep -q "Service Broker manager has started" && /opt/mssql-tools/bin/sqlcmd -S localhost,1433 -U SA -P "$SA_PASSWORD" -Q 'RESTORE DATABASE TESTDB FROM DISK = "/var/opt/mssql/backup/TESTDB.bak" WITH MOVE "TESTDB_Data" to "/var/opt/mssql/data/TESTDB.mdf", MOVE "TESTDB_Log" to "/var/opt/mssql/data/TESTDB_log.ldf"'

如果要将实际密码移动到.env文件,可以在compose.yml:中使用变量替换

services:
mssql:
build:
# ...
args:
SA_PASSWORD: "$SA_PASSWORD"
# ...

在您的docker-compose.yml中,您尝试过吗:

- ACCEPT_EULA=Y
- SA_PASSWORD=YourStrong!Passw0rd

上面的两个响应都很好,只是多了几件事:

SA_PASSWORD已弃用,而应使用MSSQL_SA_PASSWORD

用变量定义.env文件总是很好的,例如:

sapassword.env

MSSQL_SA_PASSWORD=YourStrong!Passw0rd

sqlserver.env

ACCEPT_EULA=Y
MSSQL_DATA_DIR=/var/opt/sqlserver/data
MSSQL_LOG_DIR=/var/opt/sqlserver/log
MSSQL_BACKUP_DIR=/var/opt/sqlserver/backup

在docker-compose.yml实例中,env文件的方式如下:

environment:
- sqlserver.env
- sapassword.env

最新更新