首页 > 解决方案 > 为什么使用 docker-compose 时 TeamCity 无法连接到 MySQL?

问题描述

我正在尝试让 TeamCity 服务器使用docker-compose. 这是我的撰写文件:

version: '3'

services:
  db:
    image: mysql
    container_name: teamcity-db
    restart: unless-stopped
    env_file: .env
    environment:
      - MYSQL_DATABASE=teamcity
    volumes: 
      - mysql:/var/lib/mysql
    command: '--default-authentication-plugin=mysql_native_password'

  teamcity:
    depends_on: 
      - db
    image: jetbrains/teamcity-server
    container_name: teamcity
    restart: unless-stopped
    volumes: 
      - datadir:/data/teamcity_server/datadir
      - logs:/opt/teamcity/logs
    ports:
      - "8111:8111"

volumes:
  mysql:
  datadir:
  logs:

我已经成功地使用非常相似的技术设置了 wordpress,我可以运行 phpMyAdmin 并将其链接到 MySQL 容器并查看数据库,所以它就在那里。

当我浏览到 teamcity 网址时,它会按预期显示初始设置屏幕。我告诉它使用 MySQL,然后输入“root”作为用户名和我的 MySQL root 密码。Teamcity 然后显示:

在此处输入图像描述

我确定这很简单,但我看不出有什么问题。有任何想法吗?

标签: mysqldocker-composeteamcity

解决方案


解决了!这是我的解决方案和其他一些学习。

问题是我告诉 TeamCity 使用“localhost”作为数据库服务器 URL。这看起来很直观,因为所有服务都在同一台机器上,但不正确。就好像每个容器都是它自己的主机,因此“localhost”特定于每个容器。容器内的“localhost”指的是容器本身,而不是主机或任何其他容器。所以 teamcity 服务上的 'localhost' 指的是 teamcity 服务器,而不是数据库服务器,这就是它无法连接的原因。

根据我的docker-compose.yml文件正确的数据库服务器地址是db(数据库容器的服务名称)。服务名称成为该容器的主机名,并且 docker 在组合组中将它们正确解析为 DNS 名称。

另请注意:default虚拟网络是由组合组中的所有容器隐式创建的,docker-compose并允许组合组中的所有容器相互通信。该网络的名称源自文件所在的文件夹docker-compose.yml(在我的情况下~/projects/teamcity),因此我得到了一个名为teamcity_default. 此专用虚拟网络上的所有服务器彼此可见,无需进一步配置。

teamcity服务器容器显式暴露主机网络接口上的8111端口,因此它是唯一对外可见的容器。如果您只需要服务器相互通信,则不需要(并且可能不应该)公开端口。例如,数据库服务器不需要有ports条目,因为它会自动暴露在私有容器间网络上。这对安全性非常有用,因为所有后端服务都对物理 LAN 和 Internet 隐藏。


推荐阅读