在测试之间自动删除MEDIA_ROOT

时间:2014-09-11 16:32:58

标签: python django unit-testing

我想知道在每次测试之间使用Django DiscoverRunner来删除我的媒体目录是否可能,最好不是太困难,包括一次开始和最后一次。我对Django 1.7中引入的新属性“test_suite”和“test_runner”特别感兴趣,并且想知道它们是否会使这项任务变得更容易。

我还想知道如何将测试特定MEDIA_ROOT作为临时文件,目前我有一个名为“media”的常规MEDIA_ROOT和一个名为“media_test”的测试MEDIA_ROOT,我在每个测试类的setup和tearDown中使用rmtree涉及媒体目录。我指定使用哪个MEDIA_ROOT的方式在我的test.py设置文件中,当前我只有:

MEDIA_ROOT = normpath(join(DJANGO_ROOT, 'media_test'))

有没有办法可以将MEDIA_ROOT设置为名为“media”的临时目录?

3 个答案:

答案 0 :(得分:2)

我发现一个解决方案就是简单地在setUp / tearDown中删除它,我宁愿找到一些方法让它自动应用于所有测试,而不是必须将逻辑放在涉及媒体的每个测试文件中,但是我还没想出怎么做。

我使用的代码是:

from shutil import rmtree
from django.conf import settings
from django.test import TestCase

class MyTests(TestCase):
    def setUp(self):
        rmtree(settings.MEDIA_ROOT, ignore_errors=True)

    def tearDown(self):
        rmtree(settings.MEDIA_ROOT, ignore_errors=True)

我在setUp和tearDown中执行此操作的原因是因为如果我只在setUp中使用它,我可能最终会使用一个延迟的media_test目录,即使它不会被意外地检入GitHub(它& #39;在.gitignore中)它仍然占用了我的项目浏览器中不必要的空间,我只是不喜欢它坐在那里占用空间。如果我只在tearDown中使用它,那么如果我从测试中退出并且尝试运行涉及媒体的测试而我终止会导致问题,而来自终止测试的媒体仍然存在。

答案 1 :(得分:0)

那样的东西?

TESTING_MODE = True
...
MEDIA_ROOT = os.path.join(DJANGO_ROOT, 'media_test' if TESTING_MODE else 'media')

答案 2 :(得分:0)

The answer by Richard Cooke可以工作,但至少在Python 3.7和Django 2.2上会在文件系统中留下临时目录。可以通过结合使用setUpClass,tearUpClass和覆盖测试方法中的设置来避免这种情况。例如:

import tempfile
class ExampleTestCase(TestCase):
    temporary_dir = None

    @classmethod
    def setUpClass(cls):
        cls.temporary_dir = tempfile.TemporaryDirectory()
        super(ExampleTestCase, cls).setUpClass()

    @classmethod
    def tearDownClass(cls):
        cls.temporary_dir = None
        super(ExampleTestCase, cls).tearDownClass()

    def test_example(self):
        with self.settings(MEDIA_ROOT=self.temporary_dir.name):
            # perform a test
            pass

通过这种方式可以立即删除临时文件,您也不必担心临时目录的名称。 (当然,如果需要,您仍然可以在调用tempfile.TemporaryDirectory时使用prefix参数)