Opened 3 years ago

Last modified 15 months ago

#32939 assigned Cleanup/optimization

Permit override_settings to work with test class mixins that don't inherit from unittest.TestCase

Reported by: Chris Jerdonek Owned by: Jonathan Wang
Component: Testing framework Version: dev
Severity: Normal Keywords:
Cc: Florian Demmer Triage Stage: Accepted
Has patch: no Needs documentation: no
Needs tests: no Patch needs improvement: no
Easy pickings: no UI/UX: no

Description (last modified by Chris Jerdonek)

Currently, the @override_settings decorator raises a ValueError if it's used to decorate a class that doesn't inherit from SimpleTestCase:
https://github.com/django/django/blob/56f9579105c324ff15250423bf9f8bdf1634cfb4/django/test/utils.py#L519-L521

However, this prevents the decorator from being useable as a test-class mixin for a number of SimpleTestCase subclasses. When creating shared test-class functionality, it's often better to use a mixin rather than a concrete TestCase class. This way the mixin won't have its setUp methods run unnecessarily on a test-case class with no tests, and it won't count towards the parallel test runner's test-case class count, etc.

The check could instead be done lazily, e.g. inside setUpClass(), while still having the same desired effect.

I noticed this when seeing if I could convert AuthViewsTestCase into a mixin. This AuthViewsTestCase change could be done in a nicer way once this ticket is implemented, perhaps even as part of this ticket.

Change History (9)

comment:1 by Chris Jerdonek, 3 years ago

PS - should this be a TypeError instead of ValueError?

comment:2 by Chris Jerdonek, 3 years ago

Description: modified (diff)

comment:3 by Chris Jerdonek, 3 years ago

Owner: changed from nobody to Chris Jerdonek
Status: newassigned
Summary: Change override_settings to do its subclass check lazilyPermit override_settings to work with test class mixins that don't inherit from unittest.TestCase

comment:4 by Chris Jerdonek, 3 years ago

I realize now that the "non-lazy" check could be kept by modifying it to be done only when the class inherits from unittest.TestCase (i.e. when the class is a concrete test class):

--- a/django/test/utils.py
+++ b/django/test/utils.py
@@ -515,7 +515,7 @@ class override_settings(TestContextDecorator):
 
     def decorate_class(self, cls):
         from django.test import SimpleTestCase
-        if not issubclass(cls, SimpleTestCase):
+        if issubclass(cls, TestCase) and not issubclass(cls, SimpleTestCase):
             raise ValueError(
                 "Only subclasses of Django SimpleTestCase can be decorated "
                 "with override_settings")

comment:5 by Claude Paroz, 3 years ago

Triage Stage: UnreviewedAccepted

comment:6 by Chris Jerdonek, 3 years ago

This way the mixin won't have its setUp methods run unnecessarily on a test-case class with no tests, and it won't count towards the parallel test runner's test-case class count, etc.

Investigating further, it turns out neither of these seem to happen in practice, since test classes without tests get filtered out. Nevertheless, being able to apply the decorator to test mixins would still be a useful enhancement.

comment:7 by Chris Jerdonek, 3 years ago

Owner: Chris Jerdonek removed
Status: assignednew

comment:8 by Florian Demmer, 2 years ago

Cc: Florian Demmer added

comment:11 by jwang234, 15 months ago

Owner: set to Jonathan Wang
Status: newassigned
Note: See TracTickets for help on using tickets.
Back to Top