django无法在docker-compose中连接mysql
我对docker非常陌生,现在我想通过docker-compose在Docker中运行django,但是我总是得到这个错误:
我使用Docker version 17.09.1-ce, build 19e2cf6
, Docker version 17.09.1-ce, build 19e2cf6
docker-compose version 1.18.0, build 8dd22a9
django.db.utils.OperationalError:(2003,'无法连接到'mariadb55'(111“连接被拒绝)”)上的MySQL服务器
运行后,我可以正确地连接数据库docker-compose up db
在本地或远程docker-compose up db
,我甚至可以在anaconda虚拟环境中正确运行python manage.py runserver 0.0.0.0:6001
,通过设置参数settings.py在docker中连接db
服务文件如下:
DATABASES = { 'default': { 'ENGINE': 'django.db.backends.mysql', 'NAME': 'test', 'USER': 'belter', # 'HOST': 'mariadb55', 'HOST': '127.0.0.1', 'PORT': '3302', 'PASSWORD': 'belter_2017', 'default-character-set': 'utf8', 'OPTIONS': { 'sql_mode': 'traditional', } } }
这是我的docker-compose.yml文件
version: '3' services: db: image: mariadb:5.5 restart: always environment: - MYSQL_HOST=localhost - MYSQL_PORT=3306 - MYSQL_ROOT_HOST=% - MYSQL_DATABASE=test - MYSQL_USER=belter - MYSQL_PASSWORD=belter_2017 - MYSQL_ROOT_PASSWORD=123456_abc volumes: - /home/belter/mdbdata/mdb55:/var/lib/mysql ports: - "3302:3306" web: image: onlybelter/django_py35 command: python3 manage.py runserver 0.0.0.0:6001 volumes: - /mnt/data/www/mysite:/djcode ports: - "6001:6001" depends_on: - db links: - db:mariadb55
我几乎试过了我能find的所有东西,但仍然无法弄清楚,任何帮助都会很好!
我曾经尝试过:
Docker撰写mysql连接失败
使用docker-compose链接django和mysql容器
由docker-compose连接到postgres的Django连接
您应该在settings.py
文件中使用容器名称而不是localhost(或127.0.0.1)。 尝试使用container_name
属性docker-compose.yml
文件中的db
服务提供容器名称,并使用container_name
的值replacesettings.py
的主机名。 (请确保它们位于Docker组合为您创build的同一networking中。)
最后,我明白了! 关键是,就像@SangminKim所说的,我需要在settings.py
使用3306
而不是3302
,并使用db
作为HOST
而不是127.0.0.1
。
所以这是我的docker-compose.yml文件:
version: '3' services: db: image: mariadb:5.5 restart: always environment: - MYSQL_HOST=localhost - MYSQL_PORT=3306 # cannot change this port to other number - MYSQL_ROOT_HOST=% - MYSQL_DATABASE=test - MYSQL_USER=belter - MYSQL_PASSWORD=belter_2017 - MYSQL_ROOT_PASSWORD=123456_abc volumes: - /home/belter/mdbdata/mdb55:/var/lib/mysql ports: - "3302:3306" web: image: onlybelter/django_py35 command: python3 manage.py runserver 0.0.0.0:6001 volumes: - .:/djcode ports: - "6001:6001" depends_on: - db
所以现在我们可以直接通过mysql -h 127.0.0.1 -P 3302 -u root -p
连接这个docker-mysql ,但是我们必须在django settings.py
文件中使用db
和3306
:
DATABASES = { 'default': { 'ENGINE': 'django.db.backends.mysql', 'NAME': 'test', 'USER': 'belter', # 'HOST': 'mariadb55', 'HOST': 'db', #<--- 'PORT': '3306', #<--- 'PASSWORD': 'belter_2017', 'default-character-set': 'utf8', 'OPTIONS': { 'sql_mode': 'traditional', } } }
我们仍然可以通过在docker-compose.yml
文件中运行额外的命令来检查这个端口是否打开:
... web: image: onlybelter/django_py35 command: /bin/sh -c "python check_db.py --service-name mysql --ip db --port 3306" volumes: - .:/djcode ...
这里是check_db.py文件:
# check_db.py import socket import time import argparse """ Check if port is open, avoid docker-compose race condition """ parser = argparse.ArgumentParser(description='Check if port is open, avoid\ docker-compose race condition') parser.add_argument('--service-name', required=True) parser.add_argument('--ip', required=True) parser.add_argument('--port', required=True) args = parser.parse_args() # Get arguments service_name = str(args.service_name) port = int(args.port) ip = str(args.ip) # Infinite loop while True: sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM) result = sock.connect_ex((ip, port)) if result == 0: print("{0} port is open! Bye!".format(service_name)) break else: print("{0} port is not open! I'll check it soon!".format(service_name)) time.sleep(3)
顺便说一句,这是我的Dockerfile构builddjango-py35
:
FROM python:3.5-alpine MAINTAINER Xin Xiong "xiongxin20008@126.com" ENV PYTHONUNBUFFERED 1 RUN set -e; \ apk add --no-cache --virtual .build-deps \ gcc \ libc-dev \ linux-headers \ mariadb-dev \ python3-dev \ postgresql-dev \ freetype-dev \ libpng-dev \ g++ \ ; RUN mkdir /djcode WORKDIR /djcode ENV REFRESHED_AT 2017-12-25 ADD requirements.txt /djcode/ RUN pip install --no-cache-dir -r /djcode/requirements.txt RUN pip install uwsgi ADD . /djcode/ # copy . to /djcode/ EXPOSE 6001
从这里查看更多细节: https : //github.com/OnlyBelter/django-compose