Skip to content

Commit

Permalink
[1.3.X] Fixed #16681 -- Refactored the invalid_models unit test so th…
Browse files Browse the repository at this point in the history
…at it can be invoked manually. Thanks to Anthony Briggs for the report and patch.

Backport of r16661 from trunk.

git-svn-id: http://code.djangoproject.com/svn/django/branches/releases/1.3.X@16674 bcc190cf-cafb-0310-a4f2-bffc1f526a37
  • Loading branch information
freakboy3742 committed Aug 23, 2011
1 parent 3e7d79b commit 3853070
Show file tree
Hide file tree
Showing 6 changed files with 372 additions and 390 deletions.
1 change: 1 addition & 0 deletions AUTHORS
Expand Up @@ -92,6 +92,7 @@ answer newbie questions, and generally made Django that much better:
Sean Brant Sean Brant
Andrew Brehaut <http://brehaut.net/blog> Andrew Brehaut <http://brehaut.net/blog>
David Brenneman <http://davidbrenneman.com> David Brenneman <http://davidbrenneman.com>
Anthony Briggs <anthony.briggs@gmail.com>
brut.alll@gmail.com brut.alll@gmail.com
bthomas bthomas
btoll@bestweb.net btoll@bestweb.net
Expand Down
Empty file.
330 changes: 330 additions & 0 deletions tests/modeltests/invalid_models/invalid_models/models.py

Large diffs are not rendered by default.

330 changes: 0 additions & 330 deletions tests/modeltests/invalid_models/models.py

Large diffs are not rendered by default.

37 changes: 37 additions & 0 deletions tests/modeltests/invalid_models/tests.py
@@ -0,0 +1,37 @@
import sys

from django.utils import unittest


class InvalidModelTestCase(unittest.TestCase):
"""Import an appliation with invalid models and test the exceptions."""

def test_invalid_models(self):
from django.core.management.validation import get_validation_errors
from django.db.models.loading import load_app
from cStringIO import StringIO

try:
module = load_app("modeltests.invalid_models.invalid_models")
except Exception, e:
self.fail('Unable to load invalid model module')

# Make sure sys.stdout is not a tty so that we get errors without
# coloring attached (makes matching the results easier). We restore
# sys.stderr afterwards.
orig_stdout = sys.stdout
s = StringIO()
sys.stdout = s
count = get_validation_errors(s, module)
sys.stdout = orig_stdout
s.seek(0)
error_log = s.read()
actual = error_log.split('\n')
expected = module.model_errors.split('\n')

unexpected = [err for err in actual if err not in expected]
missing = [err for err in expected if err not in actual]
self.assertFalse(unexpected, "Unexpected Errors: " + '\n'.join(unexpected))
self.assertFalse(missing, "Missing Errors: " + '\n'.join(missing))


64 changes: 4 additions & 60 deletions tests/runtests.py
Expand Up @@ -2,7 +2,6 @@
import os, subprocess, sys import os, subprocess, sys


import django.contrib as contrib import django.contrib as contrib
from django.utils import unittest


CONTRIB_DIR_NAME = 'django.contrib' CONTRIB_DIR_NAME = 'django.contrib'
MODEL_TESTS_DIR_NAME = 'modeltests' MODEL_TESTS_DIR_NAME = 'modeltests'
Expand Down Expand Up @@ -40,57 +39,14 @@ def get_test_modules():
modules = [] modules = []
for loc, dirpath in (MODEL_TESTS_DIR_NAME, MODEL_TEST_DIR), (REGRESSION_TESTS_DIR_NAME, REGRESSION_TEST_DIR), (CONTRIB_DIR_NAME, CONTRIB_DIR): for loc, dirpath in (MODEL_TESTS_DIR_NAME, MODEL_TEST_DIR), (REGRESSION_TESTS_DIR_NAME, REGRESSION_TEST_DIR), (CONTRIB_DIR_NAME, CONTRIB_DIR):
for f in os.listdir(dirpath): for f in os.listdir(dirpath):
if f.startswith('__init__') or f.startswith('.') or \ if (f.startswith('__init__') or
f.startswith('sql') or f.startswith('invalid') or \ f.startswith('.') or
os.path.basename(f) in REGRESSION_SUBDIRS_TO_SKIP: f.startswith('sql') or
os.path.basename(f) in REGRESSION_SUBDIRS_TO_SKIP):
continue continue
modules.append((loc, f)) modules.append((loc, f))
return modules return modules


def get_invalid_modules():
modules = []
for loc, dirpath in (MODEL_TESTS_DIR_NAME, MODEL_TEST_DIR), (REGRESSION_TESTS_DIR_NAME, REGRESSION_TEST_DIR), (CONTRIB_DIR_NAME, CONTRIB_DIR):
for f in os.listdir(dirpath):
if f.startswith('__init__') or f.startswith('.') or f.startswith('sql'):
continue
if f.startswith('invalid'):
modules.append((loc, f))
return modules

class InvalidModelTestCase(unittest.TestCase):
def __init__(self, module_label):
unittest.TestCase.__init__(self)
self.module_label = module_label

def runTest(self):
from django.core.management.validation import get_validation_errors
from django.db.models.loading import load_app
from cStringIO import StringIO

try:
module = load_app(self.module_label)
except Exception, e:
self.fail('Unable to load invalid model module')

# Make sure sys.stdout is not a tty so that we get errors without
# coloring attached (makes matching the results easier). We restore
# sys.stderr afterwards.
orig_stdout = sys.stdout
s = StringIO()
sys.stdout = s
count = get_validation_errors(s, module)
sys.stdout = orig_stdout
s.seek(0)
error_log = s.read()
actual = error_log.split('\n')
expected = module.model_errors.split('\n')

unexpected = [err for err in actual if err not in expected]
missing = [err for err in expected if err not in actual]

self.assertTrue(not unexpected, "Unexpected Errors: " + '\n'.join(unexpected))
self.assertTrue(not missing, "Missing Errors: " + '\n'.join(missing))

def setup(verbosity, test_labels): def setup(verbosity, test_labels):
from django.conf import settings from django.conf import settings
state = { state = {
Expand Down Expand Up @@ -162,19 +118,7 @@ def teardown(state):
def django_tests(verbosity, interactive, failfast, test_labels): def django_tests(verbosity, interactive, failfast, test_labels):
from django.conf import settings from django.conf import settings
state = setup(verbosity, test_labels) state = setup(verbosity, test_labels)

# Add tests for invalid models apps.
extra_tests = [] extra_tests = []
for module_dir, module_name in get_invalid_modules():
module_label = '.'.join([module_dir, module_name])
if not test_labels or module_name in test_labels:
extra_tests.append(InvalidModelTestCase(module_label))
try:
# Invalid models are not working apps, so we cannot pass them into
# the test runner with the other test_labels
test_labels.remove(module_name)
except ValueError:
pass


# If GeoDjango is used, add it's tests that aren't a part of # If GeoDjango is used, add it's tests that aren't a part of
# an application (e.g., GEOS, GDAL, Distance objects). # an application (e.g., GEOS, GDAL, Distance objects).
Expand Down

0 comments on commit 3853070

Please sign in to comment.