4

我正在使用 django-nose 在 django (1.4) 中运行我的单元测试。

TEST_RUNNER = 'django_nose.NoseTestSuiteRunner'

创建数据库需要很长时间。

所以我发现把它放在settings.py中:

os.environ['REUSE_DB'] = "1"

应该做的伎俩。

实际上 django itsellve 给出了这个建议:

To reuse old database "<path not very interesting>/var/sqlite/unittest.db" for speed, set env var REUSE_DB=1.

当然,您需要使用此标志 =0 运行一次(或在每次数据库更改后)

但是,当您将标志设置为 0 时,我的测试以以下备注结束:

Destroying test database for alias 'default'...

所以当我想重用运行它时......没有什么可以重用......我会收到错误说该表不存在

DatabaseError: no such table: <and than a table name>

将reuse_db设置为0时测试运行完美

我在我的开发设置中使用测试数据库别名:

DATABASES = {
    'default': {
        'NAME': os.path.join(BUILDOUT_DIR, 'var', 'sqlite', 'development.db'),
        'TEST_NAME': os.path.join(BUILDOUT_DIR, 'var', 'sqlite', 'unittest.db'),
        'ENGINE': 'django.db.backends.sqlite3', 
        'USER': '',
        'PASSWORD': '',
        'HOST': '', 
        'PORT': '', 
        }
    }

我没有使用内存中的 sqllite 数据库进行测试,因为我在某处读到这不适用于 django-nose。

那么,当它最终破坏数据库时,我该如何重用数据库......

根据这个https://docs.djangoproject.com/en/1.4/topics/testing/#the-test-database django 正在这样做,但它没有显示如何防止这种情况(如果可以的话),或者如何使用reuse_db 选项。我应该使用其他设置吗?

4

3 回答 3

9

如果我理解正确,您不知道如何第一次创建测试数据库(以便以后重用它)。

即使您设置 REUSE_DB = 0,如果 DB 不存在,NoseTestSuiteRunner 也应该自动创建它。如果您想手动创建测试数据库,您可以创建以下文件:

test_db_settings.py

您在其中指定:

from settings import *

DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.postgresql_psycopg2',
        # TestRunner uses a database with name that consists
        # of prefix test_ and your database name if your database
        # name is db then the test database name has to be test_db
        'NAME': 'test_db', 
        'USER': 'postgres_user',
        'PASSWORD': 'postgres_user',
        'HOST': 'localhost',
        'PORT': '5432',
        }
}

之后创建 test_db:

createdb -U postgres_user -h localhost test_db # if you use postgres

python manage.py syncdb --settings test_db_settings.py
python manage.py migrate --settings test_db_settings.py (only if you use South)

现在我们有了 TestRunner 使用的数据库。我们可以运行测试:

REUSE_DB=1 python manage.py test

更新

你确定你使用的是 NoseTestSuiteRunner 吗?这是来自 django_nose.NoseTestSuiteRunner 的一些代码。我们可以看到,如果选项 REUSE_DB 被设置,则 teardown_database 被禁用。如果你愿意,你可以调试它,例如在这里设置一个断点来检查你是否真的使用了它的 Runner 等。

def teardown_databases(self, *args, **kwargs):
    """Leave those poor, reusable databases alone if REUSE_DB is true."""
    if not _reusing_db():
        return super(NoseTestSuiteRunner, self).teardown_databases(
                *args, **kwargs)
    # else skip tearing down the DB so we can reuse it next time
于 2013-06-19T09:12:41.247 回答
2

我接受了 Andrey Kaygorodov 的回答,因为他引导我找到了解决方案......阅读他的回答我想(多么容易,我多么愚蠢......)

无论如何,将这个 settings_test_db.py 放在具有此内容的设置旁边:(填写您的项目名称)

from <myproject>.settings import *

DATABASES = {
    'default': {
        'NAME': os.path.join(BUILDOUT_DIR, 'var', 'sqlite', 'unittest.db'),
        'ENGINE': 'django.db.backends.sqlite3', 
        'USER': '',
        'PASSWORD': '',
        'HOST': '',
        'PORT': '',
        }
}

对于 sqlite,您不必创建数据库。赶紧跑

python manage.py syncdb --settings <myproject>.settings_test_db  

(注意:使用项目名称,不带 .py)

并运行迁移

python manage.py migrate --settings <myproject>.settings_test_db

(仅当您使用 South 时)

并在您的 settings.py 中设置:

os.environ['REUSE_DB'] = "1" 

所以你可以使用

python manage.py test
于 2013-06-19T11:36:56.180 回答
1

顺便说一句,您可以在相同的设置中定义一个测试动画,而不是使用单独的测试设置文件:

DATABASES = {
    'default': {
        'NAME': os.path.join(BUILDOUT_DIR, 'var', 'sqlite', 'test.db'),
        'TEST_NAME': os.path.join(BUILDOUT_DIR, 'var', 'sqlite', 'unittest.db'),
        'ENGINE': 'django.db.backends.sqlite3', 
        'USER': '',
        'PASSWORD': '',
        'HOST': '',  # empty string for localhost.
        'PORT': '',  # empty string for default.
        }
    }
于 2015-09-18T12:29:25.380 回答