在Fabric任务中使用依赖于环境的django设置

时间:2014-01-07 16:17:33

标签: python django fabric

我正在尝试使用设置文件上的数据库配置集来使用fabric进行数据库转储。

有多个设置文件,所以我希望能够根据我选择的环境这样做。

到现在为止,我的任务就像这样

def dump_database():
    with cd('~/project_folder'), prefix(WORKON_VIRTUALENV):

        django.settings_module(env.settings)
        from django.conf import settings

        dbname = settings.DATABASES['default']['NAME']
        dbuser = settings.DATABASES['default']['USER']
        dbpassword = settings.DATABASES['default']['PASSWORD']

        fname = '/tmp/{0}-backup-{1}.sql.gz'.format(
            dbname,
            time.strftime('%Y%m%d%H%M%S')
        )

        run('mysqldump -u %s -p=%s %s | gzip -9 /tmp/backup-%s.sql.gz' % (
            dbuser,
            dbpassword,
            dbname,
            fname))

但是我得到了一个ImportError:

ImportError: Could not import settings 'project.settings.production'

我尝试使用shell_env()设置DJANGO_SETTINGS_MODULE而不是django.settings_module(env.settings),结果相同。

我使用任务来根据环境字典改变环境:

def environment(name):
    env.update(environments[name])
    env.environment = name

这样,我希望能够从多个主机创建转储,如:

fab environment:live dump_database
fab environment:otherhost dump_database

无需从fabfile上的所有主机重现数据库设置。

2 个答案:

答案 0 :(得分:1)

此处说明在结构中导入Django设置文件。 http://fabric.readthedocs.org/en/1.3.3/api/contrib/django.html

从以上链接引用:

from fabric.api import run
from fabric.contrib import django

django.settings_module('myproject.settings')
from django.conf import settings

def dump_production_database():
    run('mysqldump -u %s -p=%s %s > /tmp/prod-db.sql' % (
        settings.DATABASE_USER,
        settings.DATABASE_PASSWORD,
        settings.DATABASE_NAME
    ))

答案 1 :(得分:1)

注意:我不回答问题,但提供不同的解决方案

我遇到了同样的问题..所以我做了这样的自定义.py脚本:

我创建了一个名为dump_db.py的文件(例如放在fabfile.py旁边,位于远程计算机上)

import os
import sys
from datetime import datetime
from django.conf import settings


def dump_mysql():
    os.environ.setdefault("DJANGO_SETTINGS_MODULE", SETTINGS_MODULE)
    DB_NAME = settings.DATABASES['default']['NAME']
    DB_USER = settings.DATABASES['default']['USER']
    DB_PASSWORD = settings.DATABASES['default']['PASSWORD']

    dump_file_name = '{time}_{db_name}.sql'.format(
        time=datetime.now().strftime('%Y_%m_%d'),
        db_name=DB_NAME,
    )

    os.system('mysqldump -u {db_user} -p{db_password} {db_name} > {to_file}'.format(
        db_user=DB_USER,
        db_password=DB_PASSWORD,
        db_name=DB_NAME,
        to_file=dump_file_name,
    ))

    return dump_file_name


if __name__ == '__main__':
    try:
        SETTINGS_MODULE = sys.argv[1:].pop()
    except IndexError:
        SETTINGS_MODULE = 'project_name.settings'

    print dump_mysql()

如您所见sys.argv [1:]。pop()尝试获取可选参数(在本例中为设置模块)。

所以在我的fabfile中:     import os

from fabric.api import env, local, run, prefix, cd

.....

def dump():
    current_dir = os.getcwd()
    with prefix('source {}bin/activate'.format(env.venv)), cd('{}'.format(env.home)):
        dumped_file = run('python dump_db.py {}'.format(env.environment)) # the optional argument given

    file_path = os.path.join(env.home, dumped_file)
    copy_to = os.path.join(current_dir, dumped_file)
    scp(file_path, copy_to)


def scp(file_path, copy_to):
    local('scp {}:{} {}'.format(env.host, file_path, copy_to))

其中env.environment ='project_name.settings。 env_module '

这就是我转储数据库并将其复制回给我的方式。

希望它对某人有用! :)