连接到docker compose mysql容器会拒绝访问,但运行相同映像的docker不会

连接到docker compose mysql容器会拒绝访问,但运行相同映像的docker不会,mysql,docker,docker-compose,Mysql,Docker,Docker Compose,我在连接使用docker compose启动的mysql docker容器时遇到一些问题。这是一篇很长的帖子(对不起!) 这是我的docker-compose.yml文件: db: image: mysql:5.7 ports: - "3306:3306" # I have tried both ports and expose "3306". Still doesn't work environment: - MYSQL_ROOT_PASSWORD="secret

我在连接使用docker compose启动的mysql docker容器时遇到一些问题。这是一篇很长的帖子(对不起!)

这是我的docker-compose.yml文件:

db:
  image: mysql:5.7
  ports:
    - "3306:3306" # I have tried both ports and expose "3306". Still doesn't work 
  environment:
    - MYSQL_ROOT_PASSWORD="secret"
    - MYSQL_USER="django"
    - MYSQL_PASSWORD="secret"
    - MYSQL_DATABASE="myAppDB"
然后:

好的,那么也许这与连接到docker compose容器有关? 如果我尝试从docker容器内部连接会怎么样

$> docker exec -it c7216f99ca0f /bin/bash
root@c7216f99ca0f:/#
root@c7216f99ca0f:/# mysql -u django -p                                                                                                                                                           
Enter password: 
ERROR 1045 (28000): Access denied for user 'django'@'localhost' (using password: YES)
$> docker exec -it 73071b929e82 /bin/bash
root@73071b929e82:/# mysql -u django -p                                                                                                                                                           
Enter password: 
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection id is 3
Server version: 5.7.12 MySQL Community Server (GPL)

Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved.

Oracle is a registered trademark of Oracle Corporation and/or its
affiliates. Other names may be trademarks of their respective
owners.

Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.

mysql> SHOW DATABASES;
+--------------------+
| Database           |
+--------------------+
| information_schema |
| myAppDB            |
+--------------------+
2 rows in set (0.00 sec)

mysql> 
好吧,docker mysql不让我连接,不知道为什么。让我们看看在没有docker compose的情况下尝试执行此操作时会发生什么:

$> docker run --name run-mysql -e MYSQL_ROOT_PASSWORD="secret" -e MYSQL_USER="django" -e MYSQL_PASSWORD="secret" -e MYSQL_DATABASE="myAppDB" -p "3306:3306" mysql:5.7
<<LOTS OF OUTPUT SAME AS BEFORE>>
        image: mysql/mysql-server:5.7
        dns: 8.8.8.8
        volumes:
            - mysql-data:/var/lib/mysql
        environment:
            MYSQL_ROOT_PASSWORD: 123456
            MYSQL_DATABASE: mydb
            MYSQL_USER: user
            MYSQL_PASSWORD: 123456           
        ports:
            - 3306:3306
这是我的容器(称为runmysql)。让我们连线

$> mysql -h 192.168.99.100 -P 3306 -u django -p
Enter password: 
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection id is 2
Server version: 5.7.12 MySQL Community Server (GPL)

Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved.

Oracle is a registered trademark of Oracle Corporation and/or its
affiliates. Other names may be trademarks of their respective
owners.

Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.

mysql> SHOW DATABASES;
+--------------------+
| Database           |
+--------------------+
| information_schema |
| myAppDB            |
+--------------------+
2 rows in set (0.01 sec)

mysql>
好的。可以登录。真奇怪。。。从容器里面呢

$> docker exec -it c7216f99ca0f /bin/bash
root@c7216f99ca0f:/#
root@c7216f99ca0f:/# mysql -u django -p                                                                                                                                                           
Enter password: 
ERROR 1045 (28000): Access denied for user 'django'@'localhost' (using password: YES)
$> docker exec -it 73071b929e82 /bin/bash
root@73071b929e82:/# mysql -u django -p                                                                                                                                                           
Enter password: 
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection id is 3
Server version: 5.7.12 MySQL Community Server (GPL)

Copyright (c) 2000, 2016, Oracle and/or its affiliates. All rights reserved.

Oracle is a registered trademark of Oracle Corporation and/or its
affiliates. Other names may be trademarks of their respective
owners.

Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.

mysql> SHOW DATABASES;
+--------------------+
| Database           |
+--------------------+
| information_schema |
| myAppDB            |
+--------------------+
2 rows in set (0.00 sec)

mysql> 
好的,当我使用docker run启动时,我可以从容器内外登录,但不能使用docker compose。发生什么事?docker compose在幕后一定做了一些改变数据库初始化方式的事情

如果我也尝试使用root用户,以上所有内容都是完全相同的。因此,这不是django用户的权限问题


有没有办法解决这个问题?

我正在使用docker compose的官方mysql映像,没有问题。撰写文件中唯一的区别是我使用的是字典而不是数组:

environment:
  MYSQL_ROOT_PASSWORD: secret
  MYSQL_USER: django
  MYSQL_PASSWORD: secret
  MYSQL_DATABASE: myAppDB
我注意到撰写文件文档在某些地方仍然停留在V1中,所以如果您使用的是V2,您可以试试这个。否则,为了进行调试,您可以使用
docker compose exec
直接与compose创建的容器交互


docker compose exec db/bin/bash
会给您带来麻烦的容器上的shell,您可以检查
SHOW GRANTS FOR django@%
或端口转发是否正确。我希望这能有所帮助。

我也遇到过类似的问题,这对我有帮助:

自从第一次尝试运行容器以来,您是否更改了密码?docker compose在运行之间做额外的工作来保存卷(从而保存数据库);您可能需要尝试
docker compose rm-v
删除所有内容并重新启动


使用数组定义时,
docker compose.yml
文件中的环境变量不应带有引号:

db:
  image: mysql:5.7
  ports:
    - "3306:3306"
  environment:
    - MYSQL_ROOT_PASSWORD=secret
    - MYSQL_USER=django
    - MYSQL_PASSWORD=secret
    - MYSQL_DATABASE=myAppDB

如果在
docker compose.yml
文件中使用它们:

db:
  image: mysql:5.7
  ports:
    - "3306:3306"
  environment:
    - MYSQL_ROOT_PASSWORD="secret"
    - MYSQL_USER="django"
    - MYSQL_PASSWORD="secret"
    - MYSQL_DATABASE="myAppDB"
并运行:

$ docker-compose up -d
并输入运行容器:

$ docker-compose exec db /bin/bash
您将看到输出:

root@979813643b0c:/# echo $MYSQL_ROOT_PASSWORD                                                                                                                                              
"secret"

看来你的问题解决了。我想我会讨论类似的问题

我正在Synology NAS(DSM 6.0.2)上使用docker compose运行tomcat(web)和mysql(db)。它在我拥有的Ubuntu设备上运行得很好,但在NAS上却不行

问题是NAS上的防火墙-我修改了防火墙规则,允许某些端口打开,但最后拒绝所有端口。当我添加:3306到允许的端口时,它工作了

这不是一个好的解决方案,我不知道DSM为什么需要这样做,因为docker compose运行在桥接网络上。我已经投了一张支持票

此答案可能有助于其他人解决此被阻止的容器问题。

我遇到了相同的错误“用户'admin'@'172.20.0.1(使用密码:YES)的访问被拒绝”。而且很长一段时间都不知道如何解决这个问题。在我的情况下,docker compose从.env文件获取配置

environment:
  MYSQL_DATABASE: ${DB_DATABASE}
  MYSQL_USER: ${DB_USERNAME}
  MYSQL_PASSWORD: ${DB_PASSWORD}
  MYSQL_ROOT_PASSWORD: ${DB_PASSWORD}
我终于发现了问题!问题在于参数中的双引号

DB_PASSWORD="dbpassword"
不起作用

DB_PASSWORD=dbpassword

工作

在我的例子中,我安装了mariadb,并试图启动一个mysql容器。不知何故,启动容器没有失败,运行
docker ps
显示容器正在侦听3306,但实际上,mariad mysqld正在运行,我的访问被拒绝。而不是容器中的数据库。我正在使用Mac,能够通过以下命令阻止mariadb:
launchctl unload~/Library/LaunchAgents/homebew.mxcl.mariadb.plist
编辑的docker-compose.yaml在您已经启动该容器时不起作用

所以我支持这一点:

1:检查已经存在的db容器

docker ps

CONTAINER ID        NAMES               PORTS       STATUS
1cbfe602466a        mysql5.7                        Exited (0) About an hour ago
2:如果容器已启动,则停止并重新启动

docker stop 1cbfe602466a //(mysql5.7)
docker rm 1cbfe602466a
3:现在可以重启mysql容器了

docker-compose.yaml/(注意格式化代码)

4:运行推荐:

docker-compose up -d mysql5.7
5:你成功了!你们可以把它装进集装箱

docker exec -it mysql5.7 /bin/bash

root@1719480b6716:/# mysql -u root -p
Enter password:
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection id is 3
Server version: 5.7.29-log MySQL Community Server (GPL)

Copyright (c) 2000, 2020, Oracle and/or its affiliates. All rights reserved.

Oracle is a registered trademark of Oracle Corporation and/or its
affiliates. Other names may be trademarks of their respective
owners.

Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.

mysql>

我对docker compose中的mysql 5.7也有同样的问题:

$> docker run --name run-mysql -e MYSQL_ROOT_PASSWORD="secret" -e MYSQL_USER="django" -e MYSQL_PASSWORD="secret" -e MYSQL_DATABASE="myAppDB" -p "3306:3306" mysql:5.7
<<LOTS OF OUTPUT SAME AS BEFORE>>
        image: mysql/mysql-server:5.7
        dns: 8.8.8.8
        volumes:
            - mysql-data:/var/lib/mysql
        environment:
            MYSQL_ROOT_PASSWORD: 123456
            MYSQL_DATABASE: mydb
            MYSQL_USER: user
            MYSQL_PASSWORD: 123456           
        ports:
            - 3306:3306
从容器内部,仅使用
localhost
工作(而不是
127.0.0.1
):

要将其更改为允许来自任何地方的连接,请在进入mysql应用程序后执行以下操作:

GRANT ALL PRIVILEGES ON *.* TO 'root'@'%' IDENTIFIED BY '123456';
FLUSH PRIVILEGES;
EXIT;

这正是字典与数组的问题。非常感谢。我不知道为什么会这样。还有静默错误。这是一个很好的观点,一个无效的配置应该抛出一个错误。文档中说你可以使用任何一种——我假设文档中有一个bug。一般来说,我认为yaml不是提供配置选项的最直观的格式。JSON万岁!。我现在对links参数有问题(我想)可能是出于同样的原因。当使用dict时,我得到:
错误:yaml.scanner.ScannerError:这里不允许映射值
@DavyKavanagh问题不是数组与字典,而是在数组定义中,不能有引号,因为它们已成为秘密的一部分。因此:应该是公认的答案,谢谢你提出这样一个结构良好的问题。正是我遇到的问题和解决方案。我有同样的问题,但给出的解决方案都不起作用。对我来说,根本原因是我使用Dockerfile“entrypoint”调用客户端的方式。作为环境变量传递的DB凭据要求我使用entrypoint的shell版本,而不是entrypoint的命令版本:[“/bin/bash”、“-c”、“java-DMYSQL_PASSWORD=${MYSQL_PASSWORD}-jar myapp.war”]这对我也适用。可能是应该
mysql -h localhost -u root -p
GRANT ALL PRIVILEGES ON *.* TO 'root'@'%' IDENTIFIED BY '123456';
FLUSH PRIVILEGES;
EXIT;