Django无法连接到数据库。

时间:2017-05-23 17:17:07

标签: mysql django docker environment-variables

我正在尝试使用docker为我公司的应用创建开发环境。出于某种原因,如果我使用docker run web "bash"然后从shell运行mysql,我就可以连接到数据库,但是Django不会连接。 Web / worker节点的Dockerfile如下所示:

FROM python:2.7
ENV PYTHONUNBUFFERED 1
ENV DOCKER 1
ENV REDIS_HOST "redis"
ENV CASSANDRA_HOST "cassandra"
RUN mkdir /code
WORKDIR /code
ADD . /code/
RUN pip install --default-timeout=100 numpy==1.9.1
RUN pip install --default-timeout=100 scipy==0.15.1
RUN pip install --default-timeout=100 -r requirements_docker.txt
#RUN python /code/app/manage.py migrate

docker-compose文件如下所示:

version: "2"

services:
  cassandra:
    image:
      cassandra:latest
  redis:
    image: 
      redis:latest
  db:
    image: mysql
    environment:
      MYSQL_DATABASE: appdb
      MYSQL_USER: dbuser
      MYSQL_PASSWORD: dbpass

  web:
    build: .
    command: python app/manage.py runserver 0.0.0.0:8000
    environment:
      DOCKER: 1
      DATABASE_HOST: db
      DATABASE_NAME: appdb
      DATABASE_USER: dbuser
      DATABASE_PASSWORD: dbpass
      REDIS_HOST: redis
      CASSANDRA_HOST: cassandra
    volumes:
      - .:/code
    ports:
      - "8000:8000"
    depends_on:
      - db
      - redis
      - cassandra
  worker:
    build: .
    environment:
      DOCKER: 1
      DATABASE_HOST: db
      DATABASE_NAME: appdb
      DATABASE_USER: dbuser
      DATABASE_PASSWORD: dbpass
      REDIS_HOST: redis
      CASSANDRA_HOST: cassandra
    command: python /code/app/manage.py celery worker -Q celery,offline,periodic --broker=redis://redis:6379/4
    depends_on:
      - db
      - redis
      - cassandra

最后,数据库设置是(从多个设置文件合并):

if not os.environ.has_key('DOCKER'):
    DATABASES = {
        "default": {
            'ENGINE': 'django.db.backends.mysql',
            'OPTIONS': {
                'read_default_file': os.path.join(PROJECT_ROOT, 'mysql.cnf'),
                "init_command": "SET foreign_key_checks = 0;",
            },
        }
    }
else:  # Using Docker
    DATABASES = {
        'default': {
            'ENGINE': 'django.db.backends.mysql',
            'NAME': os.environ['DATABASE_NAME'],
            'USER': os.environ['DATABASE_USER'],
            'PASSWORD': os.environ['DATABASE_PASSWORD'],
            'HOST': os.environ["DATABASE_HOST"],
            'PORT': '5432',
            'OPTIONS': {
                'init_command': "SET foreign_key_checks = 0;"
            }
        }
    }

if 'test' in sys.argv:
    SLAVE_DATABASES = []
elif os.environ.has_key('DOCKER'):
    DATABASES['replica_1'] = {
        'ENGINE': 'django.db.backends.mysql',
        'NAME': os.environ['DATABASE_NAME'],
        'USER': os.environ['DATABASE_USER'],
        'PASSWORD': os.environ['DATABASE_PASSWORD'],
        'HOST': os.environ["DATABASE_HOST"],
        'PORT': '5432',
        'OPTIONS': {
            "init_command": "SET foreign_key_checks = 0;"
        }
    }
    SLAVE_DATABASES = ['replica_1', ]
    DATABASE_ROUTERS = ('multidb.PinningMasterSlaveRouter',)
    MIDDLEWARE_CLASSES = ['multidb.middleware.PinningRouterMiddleware', ] + settings.MIDDLEWARE_CLASSES
else:
    DATABASES["replica_1"] = {
        'ENGINE': 'django.db.backends.mysql',
        'OPTIONS': {
            'read_default_file': os.path.join(settings.PROJECT_ROOT, 'mysql.cnf'),
            "init_command": "SET foreign_key_checks = 0;",
        },
        'TEST': {
            'MIRROR': 'default',
        },
    }

    SLAVE_DATABASES = ['replica_1', ]
    DATABASE_ROUTERS = ('multidb.PinningMasterSlaveRouter',)
    MIDDLEWARE_CLASSES = ['multidb.middleware.PinningRouterMiddleware', ] + settings.MIDDLEWARE_CLASSES


if os.environ.has_key("DOCKER"):
    from cassandra import ConsistencyLevel
    DATABASES['cassandra'] = {
        'ENGINE': 'django_cassandra_engine',
        'NAME': 'verificient_local',
        'TEST_NAME': 'test_verificient_local',
        'HOST': os.environ['CASSANDRA_HOST'],
        'OPTIONS': {
            'replication': {
                'strategy_class': 'SimpleStrategy',
                'replication_factor': 1
            },
            'connection': {
                'consistency': ConsistencyLevel.LOCAL_ONE,
                'retry_connect': True
            },
            'session': {
                'default_timeout': 30,
                'default_fetch_size': 10000
            }
        }
    }

奇怪的是,尽管运行python manage.py migrate会返回错误(django.db.utils.OperationalError: (2003, "Can't connect to MySQL server on 'db' (111)")),但我可以使用命令mysql -h$DATABASE_HOST -u$DATABASE_USER -p$DATABASE_PASSWORD $DATABASE_NAME

连接到数据库而没有任何问题

我的django设置可能出现什么问题?

1 个答案:

答案 0 :(得分:2)

MySQL默认端口为3306,因此请更改:

'PORT': '5432',

'PORT': '3306',

它可以使用mysql命令手动工作,因为该命令默认使用正确的端口