diff options
author | django-bot <ops@djangoproject.com> | 2022-02-03 20:24:19 +0100 |
---|---|---|
committer | Mariusz Felisiak <felisiak.mariusz@gmail.com> | 2022-02-07 20:37:05 +0100 |
commit | 9c19aff7c7561e3a82978a272ecdaad40dda5c00 (patch) | |
tree | f0506b668a013d0063e5fba3dbf4863b466713ba /tests/modeladmin | |
parent | f68fa8b45dfac545cfc4111d4e52804c86db68d3 (diff) | |
download | django-9c19aff7c7561e3a82978a272ecdaad40dda5c00.tar.gz |
Refs #33476 -- Reformatted code with Black.
Diffstat (limited to 'tests/modeladmin')
-rw-r--r-- | tests/modeladmin/models.py | 28 | ||||
-rw-r--r-- | tests/modeladmin/test_actions.py | 75 | ||||
-rw-r--r-- | tests/modeladmin/test_checks.py | 724 | ||||
-rw-r--r-- | tests/modeladmin/tests.py | 411 |
4 files changed, 701 insertions, 537 deletions
diff --git a/tests/modeladmin/models.py b/tests/modeladmin/models.py index c0d3c772c9..51ebca768c 100644 --- a/tests/modeladmin/models.py +++ b/tests/modeladmin/models.py @@ -8,7 +8,7 @@ class Band(models.Model): sign_date = models.DateField() class Meta: - ordering = ('name',) + ordering = ("name",) def __str__(self): return self.name @@ -17,37 +17,39 @@ class Band(models.Model): class Song(models.Model): name = models.CharField(max_length=100) band = models.ForeignKey(Band, models.CASCADE) - featuring = models.ManyToManyField(Band, related_name='featured') + featuring = models.ManyToManyField(Band, related_name="featured") def __str__(self): return self.name class Concert(models.Model): - main_band = models.ForeignKey(Band, models.CASCADE, related_name='main_concerts') - opening_band = models.ForeignKey(Band, models.CASCADE, related_name='opening_concerts', blank=True) - day = models.CharField(max_length=3, choices=((1, 'Fri'), (2, 'Sat'))) - transport = models.CharField(max_length=100, choices=( - (1, 'Plane'), - (2, 'Train'), - (3, 'Bus') - ), blank=True) + main_band = models.ForeignKey(Band, models.CASCADE, related_name="main_concerts") + opening_band = models.ForeignKey( + Band, models.CASCADE, related_name="opening_concerts", blank=True + ) + day = models.CharField(max_length=3, choices=((1, "Fri"), (2, "Sat"))) + transport = models.CharField( + max_length=100, choices=((1, "Plane"), (2, "Train"), (3, "Bus")), blank=True + ) class ValidationTestModel(models.Model): name = models.CharField(max_length=100) slug = models.SlugField() users = models.ManyToManyField(User) - state = models.CharField(max_length=2, choices=(("CO", "Colorado"), ("WA", "Washington"))) + state = models.CharField( + max_length=2, choices=(("CO", "Colorado"), ("WA", "Washington")) + ) is_active = models.BooleanField(default=False) pub_date = models.DateTimeField() band = models.ForeignKey(Band, models.CASCADE) - best_friend = models.OneToOneField(User, models.CASCADE, related_name='best_friend') + best_friend = models.OneToOneField(User, models.CASCADE, related_name="best_friend") # This field is intentionally 2 characters long (#16080). no = models.IntegerField(verbose_name="Number", blank=True, null=True) def decade_published_in(self): - return self.pub_date.strftime('%Y')[:3] + "0's" + return self.pub_date.strftime("%Y")[:3] + "0's" class ValidationTestInlineModel(models.Model): diff --git a/tests/modeladmin/test_actions.py b/tests/modeladmin/test_actions.py index b61641c0c9..fa3108ce08 100644 --- a/tests/modeladmin/test_actions.py +++ b/tests/modeladmin/test_actions.py @@ -7,16 +7,23 @@ from .models import Band class AdminActionsTests(TestCase): - @classmethod def setUpTestData(cls): - cls.superuser = User.objects.create_superuser(username='super', password='secret', email='super@example.com') + cls.superuser = User.objects.create_superuser( + username="super", password="secret", email="super@example.com" + ) content_type = ContentType.objects.get_for_model(Band) - Permission.objects.create(name='custom', codename='custom_band', content_type=content_type) - for user_type in ('view', 'add', 'change', 'delete', 'custom'): - username = '%suser' % user_type - user = User.objects.create_user(username=username, password='secret', is_staff=True) - permission = Permission.objects.get(codename='%s_band' % user_type, content_type=content_type) + Permission.objects.create( + name="custom", codename="custom_band", content_type=content_type + ) + for user_type in ("view", "add", "change", "delete", "custom"): + username = "%suser" % user_type + user = User.objects.create_user( + username=username, password="secret", is_staff=True + ) + permission = Permission.objects.get( + codename="%s_band" % user_type, content_type=content_type + ) user.user_permissions.add(permission) setattr(cls, username, user) @@ -25,31 +32,31 @@ class AdminActionsTests(TestCase): pass class BandAdmin(admin.ModelAdmin): - actions = ['custom_action'] + actions = ["custom_action"] @admin.action def custom_action(modeladmin, request, queryset): pass def has_custom_permission(self, request): - return request.user.has_perm('%s.custom_band' % self.opts.app_label) + return request.user.has_perm("%s.custom_band" % self.opts.app_label) ma = BandAdmin(Band, admin.AdminSite()) mock_request = MockRequest() mock_request.GET = {} cases = [ - (None, self.viewuser, ['custom_action']), - ('view', self.superuser, ['delete_selected', 'custom_action']), - ('view', self.viewuser, ['custom_action']), - ('add', self.adduser, ['custom_action']), - ('change', self.changeuser, ['custom_action']), - ('delete', self.deleteuser, ['delete_selected', 'custom_action']), - ('custom', self.customuser, ['custom_action']), + (None, self.viewuser, ["custom_action"]), + ("view", self.superuser, ["delete_selected", "custom_action"]), + ("view", self.viewuser, ["custom_action"]), + ("add", self.adduser, ["custom_action"]), + ("change", self.changeuser, ["custom_action"]), + ("delete", self.deleteuser, ["delete_selected", "custom_action"]), + ("custom", self.customuser, ["custom_action"]), ] for permission, user, expected in cases: with self.subTest(permission=permission, user=user): if permission is None: - if hasattr(BandAdmin.custom_action, 'allowed_permissions'): + if hasattr(BandAdmin.custom_action, "allowed_permissions"): del BandAdmin.custom_action.allowed_permissions else: BandAdmin.custom_action.allowed_permissions = (permission,) @@ -59,7 +66,7 @@ class AdminActionsTests(TestCase): def test_actions_inheritance(self): class AdminBase(admin.ModelAdmin): - actions = ['custom_action'] + actions = ["custom_action"] @admin.action def custom_action(modeladmin, request, queryset): @@ -73,14 +80,14 @@ class AdminActionsTests(TestCase): ma1 = AdminA(Band, admin.AdminSite()) action_names = [name for _, name, _ in ma1._get_base_actions()] - self.assertEqual(action_names, ['delete_selected', 'custom_action']) + self.assertEqual(action_names, ["delete_selected", "custom_action"]) # `actions = None` removes actions from superclasses. ma2 = AdminB(Band, admin.AdminSite()) action_names = [name for _, name, _ in ma2._get_base_actions()] - self.assertEqual(action_names, ['delete_selected']) + self.assertEqual(action_names, ["delete_selected"]) def test_global_actions_description(self): - @admin.action(description='Site-wide admin action 1.') + @admin.action(description="Site-wide admin action 1.") def global_action_1(modeladmin, request, queryset): pass @@ -99,32 +106,32 @@ class AdminActionsTests(TestCase): self.assertEqual( [description for _, _, description in ma._get_base_actions()], [ - 'Delete selected %(verbose_name_plural)s', - 'Site-wide admin action 1.', - 'Global action 2', + "Delete selected %(verbose_name_plural)s", + "Site-wide admin action 1.", + "Global action 2", ], ) def test_actions_replace_global_action(self): - @admin.action(description='Site-wide admin action 1.') + @admin.action(description="Site-wide admin action 1.") def global_action_1(modeladmin, request, queryset): pass - @admin.action(description='Site-wide admin action 2.') + @admin.action(description="Site-wide admin action 2.") def global_action_2(modeladmin, request, queryset): pass - admin.site.add_action(global_action_1, name='custom_action_1') - admin.site.add_action(global_action_2, name='custom_action_2') + admin.site.add_action(global_action_1, name="custom_action_1") + admin.site.add_action(global_action_2, name="custom_action_2") - @admin.action(description='Local admin action 1.') + @admin.action(description="Local admin action 1.") def custom_action_1(modeladmin, request, queryset): pass class BandAdmin(admin.ModelAdmin): - actions = [custom_action_1, 'custom_action_2'] + actions = [custom_action_1, "custom_action_2"] - @admin.action(description='Local admin action 2.') + @admin.action(description="Local admin action 2.") def custom_action_2(self, request, queryset): pass @@ -134,10 +141,10 @@ class AdminActionsTests(TestCase): [ desc for _, name, desc in ma._get_base_actions() - if name.startswith('custom_action') + if name.startswith("custom_action") ], [ - 'Local admin action 1.', - 'Local admin action 2.', + "Local admin action 1.", + "Local admin action 2.", ], ) diff --git a/tests/modeladmin/test_checks.py b/tests/modeladmin/test_checks.py index b08d52e6dd..c74c35f76f 100644 --- a/tests/modeladmin/test_checks.py +++ b/tests/modeladmin/test_checks.py @@ -9,21 +9,31 @@ from django.db.models.functions import Upper from django.forms.models import BaseModelFormSet from django.test import SimpleTestCase -from .models import ( - Band, Song, User, ValidationTestInlineModel, ValidationTestModel, -) +from .models import Band, Song, User, ValidationTestInlineModel, ValidationTestModel class CheckTestCase(SimpleTestCase): - - def assertIsInvalid(self, model_admin, model, msg, id=None, hint=None, invalid_obj=None, admin_site=None): + def assertIsInvalid( + self, + model_admin, + model, + msg, + id=None, + hint=None, + invalid_obj=None, + admin_site=None, + ): if admin_site is None: admin_site = AdminSite() invalid_obj = invalid_obj or model_admin admin_obj = model_admin(model, admin_site) - self.assertEqual(admin_obj.check(), [Error(msg, hint=hint, obj=invalid_obj, id=id)]) + self.assertEqual( + admin_obj.check(), [Error(msg, hint=hint, obj=invalid_obj, id=id)] + ) - def assertIsInvalidRegexp(self, model_admin, model, msg, id=None, hint=None, invalid_obj=None): + def assertIsInvalidRegexp( + self, model_admin, model, msg, id=None, hint=None, invalid_obj=None + ): """ Same as assertIsInvalid but treats the given msg as a regexp. """ @@ -45,63 +55,64 @@ class CheckTestCase(SimpleTestCase): class RawIdCheckTests(CheckTestCase): - def test_not_iterable(self): class TestModelAdmin(ModelAdmin): raw_id_fields = 10 self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'raw_id_fields' must be a list or tuple.", - 'admin.E001' + "admin.E001", ) def test_missing_field(self): class TestModelAdmin(ModelAdmin): - raw_id_fields = ('non_existent_field',) + raw_id_fields = ("non_existent_field",) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'raw_id_fields[0]' refers to 'non_existent_field', " "which is not a field of 'modeladmin.ValidationTestModel'.", - 'admin.E002' + "admin.E002", ) def test_invalid_field_type(self): class TestModelAdmin(ModelAdmin): - raw_id_fields = ('name',) + raw_id_fields = ("name",) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'raw_id_fields[0]' must be a foreign key or a " "many-to-many field.", - 'admin.E003' + "admin.E003", ) def test_valid_case(self): class TestModelAdmin(ModelAdmin): - raw_id_fields = ('users',) + raw_id_fields = ("users",) self.assertIsValid(TestModelAdmin, ValidationTestModel) def test_field_attname(self): class TestModelAdmin(ModelAdmin): - raw_id_fields = ['band_id'] + raw_id_fields = ["band_id"] self.assertIsInvalid( TestModelAdmin, ValidationTestModel, "The value of 'raw_id_fields[0]' refers to 'band_id', which is " "not a field of 'modeladmin.ValidationTestModel'.", - 'admin.E002', + "admin.E002", ) class FieldsetsCheckTests(CheckTestCase): - def test_valid_case(self): class TestModelAdmin(ModelAdmin): - fieldsets = (('General', {'fields': ('name',)}),) + fieldsets = (("General", {"fields": ("name",)}),) self.assertIsValid(TestModelAdmin, ValidationTestModel) @@ -110,9 +121,10 @@ class FieldsetsCheckTests(CheckTestCase): fieldsets = 10 self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'fieldsets' must be a list or tuple.", - 'admin.E007' + "admin.E007", ) def test_non_iterable_item(self): @@ -120,9 +132,10 @@ class FieldsetsCheckTests(CheckTestCase): fieldsets = ({},) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'fieldsets[0]' must be a list or tuple.", - 'admin.E008' + "admin.E008", ) def test_item_not_a_pair(self): @@ -130,87 +143,93 @@ class FieldsetsCheckTests(CheckTestCase): fieldsets = ((),) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'fieldsets[0]' must be of length 2.", - 'admin.E009' + "admin.E009", ) def test_second_element_of_item_not_a_dict(self): class TestModelAdmin(ModelAdmin): - fieldsets = (('General', ()),) + fieldsets = (("General", ()),) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'fieldsets[0][1]' must be a dictionary.", - 'admin.E010' + "admin.E010", ) def test_missing_fields_key(self): class TestModelAdmin(ModelAdmin): - fieldsets = (('General', {}),) + fieldsets = (("General", {}),) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'fieldsets[0][1]' must contain the key 'fields'.", - 'admin.E011' + "admin.E011", ) class TestModelAdmin(ModelAdmin): - fieldsets = (('General', {'fields': ('name',)}),) + fieldsets = (("General", {"fields": ("name",)}),) self.assertIsValid(TestModelAdmin, ValidationTestModel) def test_specified_both_fields_and_fieldsets(self): class TestModelAdmin(ModelAdmin): - fieldsets = (('General', {'fields': ('name',)}),) - fields = ['name'] + fieldsets = (("General", {"fields": ("name",)}),) + fields = ["name"] self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "Both 'fieldsets' and 'fields' are specified.", - 'admin.E005' + "admin.E005", ) def test_duplicate_fields(self): class TestModelAdmin(ModelAdmin): - fieldsets = [(None, {'fields': ['name', 'name']})] + fieldsets = [(None, {"fields": ["name", "name"]})] self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "There are duplicate field(s) in 'fieldsets[0][1]'.", - 'admin.E012' + "admin.E012", ) def test_duplicate_fields_in_fieldsets(self): class TestModelAdmin(ModelAdmin): fieldsets = [ - (None, {'fields': ['name']}), - (None, {'fields': ['name']}), + (None, {"fields": ["name"]}), + (None, {"fields": ["name"]}), ] self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "There are duplicate field(s) in 'fieldsets[1][1]'.", - 'admin.E012' + "admin.E012", ) def test_fieldsets_with_custom_form_validation(self): class BandAdmin(ModelAdmin): - fieldsets = (('Band', {'fields': ('name',)}),) + fieldsets = (("Band", {"fields": ("name",)}),) self.assertIsValid(BandAdmin, Band) class FieldsCheckTests(CheckTestCase): - def test_duplicate_fields_in_fields(self): class TestModelAdmin(ModelAdmin): - fields = ['name', 'name'] + fields = ["name", "name"] self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'fields' contains duplicate field(s).", - 'admin.E006' + "admin.E006", ) def test_inline(self): @@ -222,15 +241,15 @@ class FieldsCheckTests(CheckTestCase): inlines = [ValidationTestInline] self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'fields' must be a list or tuple.", - 'admin.E004', - invalid_obj=ValidationTestInline + "admin.E004", + invalid_obj=ValidationTestInline, ) class FormCheckTests(CheckTestCase): - def test_invalid_type(self): class FakeForm: pass @@ -239,20 +258,20 @@ class FormCheckTests(CheckTestCase): form = FakeForm class TestModelAdminWithNoForm(ModelAdmin): - form = 'not a form' + form = "not a form" for model_admin in (TestModelAdmin, TestModelAdminWithNoForm): with self.subTest(model_admin): self.assertIsInvalid( - model_admin, ValidationTestModel, + model_admin, + ValidationTestModel, "The value of 'form' must inherit from 'BaseModelForm'.", - 'admin.E016' + "admin.E016", ) def test_fieldsets_with_custom_form_validation(self): - class BandAdmin(ModelAdmin): - fieldsets = (('Band', {'fields': ('name',)}),) + fieldsets = (("Band", {"fields": ("name",)}),) self.assertIsValid(BandAdmin, Band) @@ -262,157 +281,159 @@ class FormCheckTests(CheckTestCase): class BandAdmin(ModelAdmin): form = AdminBandForm - fieldsets = ( - ('Band', { - 'fields': ('name', 'bio', 'sign_date', 'delete') - }), - ) + fieldsets = (("Band", {"fields": ("name", "bio", "sign_date", "delete")}),) self.assertIsValid(BandAdmin, Band) class FilterVerticalCheckTests(CheckTestCase): - def test_not_iterable(self): class TestModelAdmin(ModelAdmin): filter_vertical = 10 self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'filter_vertical' must be a list or tuple.", - 'admin.E017' + "admin.E017", ) def test_missing_field(self): class TestModelAdmin(ModelAdmin): - filter_vertical = ('non_existent_field',) + filter_vertical = ("non_existent_field",) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'filter_vertical[0]' refers to 'non_existent_field', " "which is not a field of 'modeladmin.ValidationTestModel'.", - 'admin.E019' + "admin.E019", ) def test_invalid_field_type(self): class TestModelAdmin(ModelAdmin): - filter_vertical = ('name',) + filter_vertical = ("name",) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'filter_vertical[0]' must be a many-to-many field.", - 'admin.E020' + "admin.E020", ) def test_valid_case(self): class TestModelAdmin(ModelAdmin): - filter_vertical = ('users',) + filter_vertical = ("users",) self.assertIsValid(TestModelAdmin, ValidationTestModel) class FilterHorizontalCheckTests(CheckTestCase): - def test_not_iterable(self): class TestModelAdmin(ModelAdmin): filter_horizontal = 10 self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'filter_horizontal' must be a list or tuple.", - 'admin.E018' + "admin.E018", ) def test_missing_field(self): class TestModelAdmin(ModelAdmin): - filter_horizontal = ('non_existent_field',) + filter_horizontal = ("non_existent_field",) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'filter_horizontal[0]' refers to 'non_existent_field', " "which is not a field of 'modeladmin.ValidationTestModel'.", - 'admin.E019' + "admin.E019", ) def test_invalid_field_type(self): class TestModelAdmin(ModelAdmin): - filter_horizontal = ('name',) + filter_horizontal = ("name",) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'filter_horizontal[0]' must be a many-to-many field.", - 'admin.E020' + "admin.E020", ) def test_valid_case(self): class TestModelAdmin(ModelAdmin): - filter_horizontal = ('users',) + filter_horizontal = ("users",) self.assertIsValid(TestModelAdmin, ValidationTestModel) class RadioFieldsCheckTests(CheckTestCase): - def test_not_dictionary(self): - class TestModelAdmin(ModelAdmin): radio_fields = () self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'radio_fields' must be a dictionary.", - 'admin.E021' + "admin.E021", ) def test_missing_field(self): class TestModelAdmin(ModelAdmin): - radio_fields = {'non_existent_field': VERTICAL} + radio_fields = {"non_existent_field": VERTICAL} self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'radio_fields' refers to 'non_existent_field', " "which is not a field of 'modeladmin.ValidationTestModel'.", - 'admin.E022' + "admin.E022", ) def test_invalid_field_type(self): class TestModelAdmin(ModelAdmin): - radio_fields = {'name': VERTICAL} + radio_fields = {"name": VERTICAL} self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'radio_fields' refers to 'name', which is not an instance " "of ForeignKey, and does not have a 'choices' definition.", - 'admin.E023' + "admin.E023", ) def test_invalid_value(self): class TestModelAdmin(ModelAdmin): - radio_fields = {'state': None} + radio_fields = {"state": None} self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'radio_fields[\"state\"]' must be either admin.HORIZONTAL or admin.VERTICAL.", - 'admin.E024' + "admin.E024", ) def test_valid_case(self): class TestModelAdmin(ModelAdmin): - radio_fields = {'state': VERTICAL} + radio_fields = {"state": VERTICAL} self.assertIsValid(TestModelAdmin, ValidationTestModel) class PrepopulatedFieldsCheckTests(CheckTestCase): - def test_not_list_or_tuple(self): class TestModelAdmin(ModelAdmin): - prepopulated_fields = {'slug': 'test'} + prepopulated_fields = {"slug": "test"} self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, - 'The value of \'prepopulated_fields["slug"]\' must be a list or tuple.', - 'admin.E029' + TestModelAdmin, + ValidationTestModel, + "The value of 'prepopulated_fields[\"slug\"]' must be a list or tuple.", + "admin.E029", ) def test_not_dictionary(self): @@ -420,94 +441,101 @@ class PrepopulatedFieldsCheckTests(CheckTestCase): prepopulated_fields = () self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'prepopulated_fields' must be a dictionary.", - 'admin.E026' + "admin.E026", ) def test_missing_field(self): class TestModelAdmin(ModelAdmin): - prepopulated_fields = {'non_existent_field': ('slug',)} + prepopulated_fields = {"non_existent_field": ("slug",)} self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'prepopulated_fields' refers to 'non_existent_field', " "which is not a field of 'modeladmin.ValidationTestModel'.", - 'admin.E027' + "admin.E027", ) def test_missing_field_again(self): class TestModelAdmin(ModelAdmin): - prepopulated_fields = {'slug': ('non_existent_field',)} + prepopulated_fields = {"slug": ("non_existent_field",)} self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'prepopulated_fields[\"slug\"][0]' refers to 'non_existent_field', " "which is not a field of 'modeladmin.ValidationTestModel'.", - 'admin.E030' + "admin.E030", ) def test_invalid_field_type(self): class TestModelAdmin(ModelAdmin): - prepopulated_fields = {'users': ('name',)} + prepopulated_fields = {"users": ("name",)} self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'prepopulated_fields' refers to 'users', which must not be " "a DateTimeField, a ForeignKey, a OneToOneField, or a ManyToManyField.", - 'admin.E028' + "admin.E028", ) def test_valid_case(self): class TestModelAdmin(ModelAdmin): - prepopulated_fields = {'slug': ('name',)} + prepopulated_fields = {"slug": ("name",)} self.assertIsValid(TestModelAdmin, ValidationTestModel) def test_one_to_one_field(self): class TestModelAdmin(ModelAdmin): - prepopulated_fields = {'best_friend': ('name',)} + prepopulated_fields = {"best_friend": ("name",)} self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'prepopulated_fields' refers to 'best_friend', which must not be " "a DateTimeField, a ForeignKey, a OneToOneField, or a ManyToManyField.", - 'admin.E028' + "admin.E028", ) class ListDisplayTests(CheckTestCase): - def test_not_iterable(self): class TestModelAdmin(ModelAdmin): list_display = 10 self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_display' must be a list or tuple.", - 'admin.E107' + "admin.E107", ) def test_missing_field(self): class TestModelAdmin(ModelAdmin): - list_display = ('non_existent_field',) + list_display = ("non_existent_field",) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_display[0]' refers to 'non_existent_field', " "which is not a callable, an attribute of 'TestModelAdmin', " "or an attribute or method on 'modeladmin.ValidationTestModel'.", - 'admin.E108' + "admin.E108", ) def test_invalid_field_type(self): class TestModelAdmin(ModelAdmin): - list_display = ('users',) + list_display = ("users",) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_display[0]' must not be a ManyToManyField.", - 'admin.E109' + "admin.E109", ) def test_valid_case(self): @@ -519,13 +547,15 @@ class ListDisplayTests(CheckTestCase): @admin.display def a_method(self, obj): pass - list_display = ('name', 'decade_published_in', 'a_method', a_callable) + + list_display = ("name", "decade_published_in", "a_method", a_callable) self.assertIsValid(TestModelAdmin, ValidationTestModel) def test_valid_field_accessible_via_instance(self): class PositionField(Field): """Custom field accessible only via instance.""" + def contribute_to_class(self, cls, name): super().contribute_to_class(cls, name) setattr(cls, self.name, self) @@ -538,42 +568,46 @@ class ListDisplayTests(CheckTestCase): field = PositionField() class TestModelAdmin(ModelAdmin): - list_display = ('field',) + list_display = ("field",) self.assertIsValid(TestModelAdmin, TestModel) class ListDisplayLinksCheckTests(CheckTestCase): - def test_not_iterable(self): class TestModelAdmin(ModelAdmin): list_display_links = 10 self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_display_links' must be a list, a tuple, or None.", - 'admin.E110' + "admin.E110", ) def test_missing_field(self): class TestModelAdmin(ModelAdmin): - list_display_links = ('non_existent_field',) + list_display_links = ("non_existent_field",) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, ( + TestModelAdmin, + ValidationTestModel, + ( "The value of 'list_display_links[0]' refers to " "'non_existent_field', which is not defined in 'list_display'." - ), 'admin.E111' + ), + "admin.E111", ) def test_missing_in_list_display(self): class TestModelAdmin(ModelAdmin): - list_display_links = ('name',) + list_display_links = ("name",) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_display_links[0]' refers to 'name', which is not defined in 'list_display'.", - 'admin.E111' + "admin.E111", ) def test_valid_case(self): @@ -585,8 +619,9 @@ class ListDisplayLinksCheckTests(CheckTestCase): @admin.display def a_method(self, obj): pass - list_display = ('name', 'decade_published_in', 'a_method', a_callable) - list_display_links = ('name', 'decade_published_in', 'a_method', a_callable) + + list_display = ("name", "decade_published_in", "a_method", a_callable) + list_display_links = ("name", "decade_published_in", "a_method", a_callable) self.assertIsValid(TestModelAdmin, ValidationTestModel) @@ -600,53 +635,59 @@ class ListDisplayLinksCheckTests(CheckTestCase): """ list_display_links check is skipped if get_list_display() is overridden. """ + class TestModelAdmin(ModelAdmin): - list_display_links = ['name', 'subtitle'] + list_display_links = ["name", "subtitle"] def get_list_display(self, request): pass self.assertIsValid(TestModelAdmin, ValidationTestModel) - def test_list_display_link_checked_for_list_tuple_if_get_list_display_overridden(self): + def test_list_display_link_checked_for_list_tuple_if_get_list_display_overridden( + self, + ): """ list_display_links is checked for list/tuple/None even if get_list_display() is overridden. """ + class TestModelAdmin(ModelAdmin): - list_display_links = 'non-list/tuple' + list_display_links = "non-list/tuple" def get_list_display(self, request): pass self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_display_links' must be a list, a tuple, or None.", - 'admin.E110' + "admin.E110", ) class ListFilterTests(CheckTestCase): - def test_list_filter_validation(self): class TestModelAdmin(ModelAdmin): list_filter = 10 self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_filter' must be a list or tuple.", - 'admin.E112' + "admin.E112", ) def test_not_list_filter_class(self): class TestModelAdmin(ModelAdmin): - list_filter = ['RandomClass'] + list_filter = ["RandomClass"] self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_filter[0]' refers to 'RandomClass', which " "does not refer to a Field.", - 'admin.E116' + "admin.E116", ) def test_callable(self): @@ -657,9 +698,10 @@ class ListFilterTests(CheckTestCase): list_filter = [random_callable] self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_filter[0]' must inherit from 'ListFilter'.", - 'admin.E113' + "admin.E113", ) def test_not_callable(self): @@ -667,20 +709,22 @@ class ListFilterTests(CheckTestCase): list_filter = [[42, 42]] self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_filter[0][1]' must inherit from 'FieldListFilter'.", - 'admin.E115' + "admin.E115", ) def test_missing_field(self): class TestModelAdmin(ModelAdmin): - list_filter = ('non_existent_field',) + list_filter = ("non_existent_field",) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_filter[0]' refers to 'non_existent_field', " "which does not refer to a Field.", - 'admin.E116' + "admin.E116", ) def test_not_filter(self): @@ -691,9 +735,10 @@ class ListFilterTests(CheckTestCase): list_filter = (RandomClass,) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_filter[0]' must inherit from 'ListFilter'.", - 'admin.E113' + "admin.E113", ) def test_not_filter_again(self): @@ -701,32 +746,34 @@ class ListFilterTests(CheckTestCase): pass class TestModelAdmin(ModelAdmin): - list_filter = (('is_active', RandomClass),) + list_filter = (("is_active", RandomClass),) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_filter[0][1]' must inherit from 'FieldListFilter'.", - 'admin.E115' + "admin.E115", ) def test_not_filter_again_again(self): class AwesomeFilter(SimpleListFilter): def get_title(self): - return 'awesomeness' + return "awesomeness" def get_choices(self, request): - return (('bit', 'A bit awesome'), ('very', 'Very awesome')) + return (("bit", "A bit awesome"), ("very", "Very awesome")) def get_queryset(self, cl, qs): return qs class TestModelAdmin(ModelAdmin): - list_filter = (('is_active', AwesomeFilter),) + list_filter = (("is_active", AwesomeFilter),) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_filter[0][1]' must inherit from 'FieldListFilter'.", - 'admin.E115' + "admin.E115", ) def test_list_filter_is_func(self): @@ -737,9 +784,10 @@ class ListFilterTests(CheckTestCase): list_filter = [get_filter] self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_filter[0]' must inherit from 'ListFilter'.", - 'admin.E113' + "admin.E113", ) def test_not_associated_with_field_name(self): @@ -747,38 +795,44 @@ class ListFilterTests(CheckTestCase): list_filter = (BooleanFieldListFilter,) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_filter[0]' must not inherit from 'FieldListFilter'.", - 'admin.E114' + "admin.E114", ) def test_valid_case(self): class AwesomeFilter(SimpleListFilter): def get_title(self): - return 'awesomeness' + return "awesomeness" def get_choices(self, request): - return (('bit', 'A bit awesome'), ('very', 'Very awesome')) + return (("bit", "A bit awesome"), ("very", "Very awesome")) def get_queryset(self, cl, qs): return qs class TestModelAdmin(ModelAdmin): - list_filter = ('is_active', AwesomeFilter, ('is_active', BooleanFieldListFilter), 'no') + list_filter = ( + "is_active", + AwesomeFilter, + ("is_active", BooleanFieldListFilter), + "no", + ) self.assertIsValid(TestModelAdmin, ValidationTestModel) class ListPerPageCheckTests(CheckTestCase): - def test_not_integer(self): class TestModelAdmin(ModelAdmin): - list_per_page = 'hello' + list_per_page = "hello" self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_per_page' must be an integer.", - 'admin.E118' + "admin.E118", ) def test_valid_case(self): @@ -789,15 +843,15 @@ class ListPerPageCheckTests(CheckTestCase): class ListMaxShowAllCheckTests(CheckTestCase): - def test_not_integer(self): class TestModelAdmin(ModelAdmin): - list_max_show_all = 'hello' + list_max_show_all = "hello" self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_max_show_all' must be an integer.", - 'admin.E119' + "admin.E119", ) def test_valid_case(self): @@ -808,144 +862,149 @@ class ListMaxShowAllCheckTests(CheckTestCase): class SearchFieldsCheckTests(CheckTestCase): - def test_not_iterable(self): class TestModelAdmin(ModelAdmin): search_fields = 10 self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'search_fields' must be a list or tuple.", - 'admin.E126' + "admin.E126", ) class DateHierarchyCheckTests(CheckTestCase): - def test_missing_field(self): class TestModelAdmin(ModelAdmin): - date_hierarchy = 'non_existent_field' + date_hierarchy = "non_existent_field" self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'date_hierarchy' refers to 'non_existent_field', " "which does not refer to a Field.", - 'admin.E127' + "admin.E127", ) def test_invalid_field_type(self): class TestModelAdmin(ModelAdmin): - date_hierarchy = 'name' + date_hierarchy = "name" self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'date_hierarchy' must be a DateField or DateTimeField.", - 'admin.E128' + "admin.E128", ) def test_valid_case(self): class TestModelAdmin(ModelAdmin): - date_hierarchy = 'pub_date' + date_hierarchy = "pub_date" self.assertIsValid(TestModelAdmin, ValidationTestModel) def test_related_valid_case(self): class TestModelAdmin(ModelAdmin): - date_hierarchy = 'band__sign_date' + date_hierarchy = "band__sign_date" self.assertIsValid(TestModelAdmin, ValidationTestModel) def test_related_invalid_field_type(self): class TestModelAdmin(ModelAdmin): - date_hierarchy = 'band__name' + date_hierarchy = "band__name" self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'date_hierarchy' must be a DateField or DateTimeField.", - 'admin.E128' + "admin.E128", ) class OrderingCheckTests(CheckTestCase): - def test_not_iterable(self): class TestModelAdmin(ModelAdmin): ordering = 10 self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'ordering' must be a list or tuple.", - 'admin.E031' + "admin.E031", ) class TestModelAdmin(ModelAdmin): - ordering = ('non_existent_field',) + ordering = ("non_existent_field",) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'ordering[0]' refers to 'non_existent_field', " "which is not a field of 'modeladmin.ValidationTestModel'.", - 'admin.E033' + "admin.E033", ) def test_random_marker_not_alone(self): class TestModelAdmin(ModelAdmin): - ordering = ('?', 'name') + ordering = ("?", "name") self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'ordering' has the random ordering marker '?', but contains " "other fields as well.", - 'admin.E032', - hint='Either remove the "?", or remove the other fields.' + "admin.E032", + hint='Either remove the "?", or remove the other fields.', ) def test_valid_random_marker_case(self): class TestModelAdmin(ModelAdmin): - ordering = ('?',) + ordering = ("?",) self.assertIsValid(TestModelAdmin, ValidationTestModel) def test_valid_complex_case(self): class TestModelAdmin(ModelAdmin): - ordering = ('band__name',) + ordering = ("band__name",) self.assertIsValid(TestModelAdmin, ValidationTestModel) def test_valid_case(self): class TestModelAdmin(ModelAdmin): - ordering = ('name', 'pk') + ordering = ("name", "pk") self.assertIsValid(TestModelAdmin, ValidationTestModel) def test_invalid_expression(self): class TestModelAdmin(ModelAdmin): - ordering = (F('nonexistent'), ) + ordering = (F("nonexistent"),) self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'ordering[0]' refers to 'nonexistent', which is not " "a field of 'modeladmin.ValidationTestModel'.", - 'admin.E033' + "admin.E033", ) def test_valid_expression(self): class TestModelAdmin(ModelAdmin): - ordering = (Upper('name'), Upper('band__name').desc()) + ordering = (Upper("name"), Upper("band__name").desc()) self.assertIsValid(TestModelAdmin, ValidationTestModel) class ListSelectRelatedCheckTests(CheckTestCase): - def test_invalid_type(self): class TestModelAdmin(ModelAdmin): list_select_related = 1 self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'list_select_related' must be a boolean, tuple or list.", - 'admin.E117' + "admin.E117", ) def test_valid_case(self): @@ -956,15 +1015,15 @@ class ListSelectRelatedCheckTests(CheckTestCase): class SaveAsCheckTests(CheckTestCase): - def test_not_boolean(self): class TestModelAdmin(ModelAdmin): save_as = 1 self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'save_as' must be a boolean.", - 'admin.E101' + "admin.E101", ) def test_valid_case(self): @@ -975,15 +1034,15 @@ class SaveAsCheckTests(CheckTestCase): class SaveOnTopCheckTests(CheckTestCase): - def test_not_boolean(self): class TestModelAdmin(ModelAdmin): save_on_top = 1 self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'save_on_top' must be a boolean.", - 'admin.E102' + "admin.E102", ) def test_valid_case(self): @@ -994,15 +1053,15 @@ class SaveOnTopCheckTests(CheckTestCase): class InlinesCheckTests(CheckTestCase): - def test_not_iterable(self): class TestModelAdmin(ModelAdmin): inlines = 10 self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'inlines' must be a list or tuple.", - 'admin.E103' + "admin.E103", ) def test_not_correct_inline_field(self): @@ -1010,9 +1069,10 @@ class InlinesCheckTests(CheckTestCase): inlines = [42] self.assertIsInvalidRegexp( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, r"'.*\.TestModelAdmin' must inherit from 'InlineModelAdmin'\.", - 'admin.E104' + "admin.E104", ) def test_not_model_admin(self): @@ -1023,9 +1083,10 @@ class InlinesCheckTests(CheckTestCase): inlines = [ValidationTestInline] self.assertIsInvalidRegexp( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, r"'.*\.ValidationTestInline' must inherit from 'InlineModelAdmin'\.", - 'admin.E104' + "admin.E104", ) def test_missing_model_field(self): @@ -1036,9 +1097,10 @@ class InlinesCheckTests(CheckTestCase): inlines = [ValidationTestInline] self.assertIsInvalidRegexp( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, r"'.*\.ValidationTestInline' must have a 'model' attribute\.", - 'admin.E105' + "admin.E105", ) def test_invalid_model_type(self): @@ -1052,22 +1114,24 @@ class InlinesCheckTests(CheckTestCase): inlines = [ValidationTestInline] self.assertIsInvalidRegexp( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, r"The value of '.*\.ValidationTestInline.model' must be a Model\.", - 'admin.E106' + "admin.E106", ) def test_invalid_model(self): class ValidationTestInline(TabularInline): - model = 'Not a class' + model = "Not a class" class TestModelAdmin(ModelAdmin): inlines = [ValidationTestInline] self.assertIsInvalidRegexp( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, r"The value of '.*\.ValidationTestInline.model' must be a Model\.", - 'admin.E106' + "admin.E106", ) def test_invalid_callable(self): @@ -1078,9 +1142,10 @@ class InlinesCheckTests(CheckTestCase): inlines = [random_obj] self.assertIsInvalidRegexp( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, r"'.*\.random_obj' must inherit from 'InlineModelAdmin'\.", - 'admin.E104' + "admin.E104", ) def test_valid_case(self): @@ -1094,26 +1159,26 @@ class InlinesCheckTests(CheckTestCase): class FkNameCheckTests(CheckTestCase): - def test_missing_field(self): class ValidationTestInline(TabularInline): model = ValidationTestInlineModel - fk_name = 'non_existent_field' + fk_name = "non_existent_field" class TestModelAdmin(ModelAdmin): inlines = [ValidationTestInline] self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "'modeladmin.ValidationTestInlineModel' has no field named 'non_existent_field'.", - 'admin.E202', - invalid_obj=ValidationTestInline + "admin.E202", + invalid_obj=ValidationTestInline, ) def test_valid_case(self): class ValidationTestInline(TabularInline): model = ValidationTestInlineModel - fk_name = 'parent' + fk_name = "parent" class TestModelAdmin(ModelAdmin): inlines = [ValidationTestInline] @@ -1137,7 +1202,7 @@ class FkNameCheckTests(CheckTestCase): class InlineFkName(admin.TabularInline): model = Related - fk_name = 'proxy_child' + fk_name = "proxy_child" class InlineNoFkName(admin.TabularInline): model = Related @@ -1149,20 +1214,20 @@ class FkNameCheckTests(CheckTestCase): class ExtraCheckTests(CheckTestCase): - def test_not_integer(self): class ValidationTestInline(TabularInline): model = ValidationTestInlineModel - extra = 'hello' + extra = "hello" class TestModelAdmin(ModelAdmin): inlines = [ValidationTestInline] self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'extra' must be an integer.", - 'admin.E203', - invalid_obj=ValidationTestInline + "admin.E203", + invalid_obj=ValidationTestInline, ) def test_valid_case(self): @@ -1177,20 +1242,20 @@ class ExtraCheckTests(CheckTestCase): class MaxNumCheckTests(CheckTestCase): - def test_not_integer(self): class ValidationTestInline(TabularInline): model = ValidationTestInlineModel - max_num = 'hello' + max_num = "hello" class TestModelAdmin(ModelAdmin): inlines = [ValidationTestInline] self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'max_num' must be an integer.", - 'admin.E204', - invalid_obj=ValidationTestInline + "admin.E204", + invalid_obj=ValidationTestInline, ) def test_valid_case(self): @@ -1205,20 +1270,20 @@ class MaxNumCheckTests(CheckTestCase): class MinNumCheckTests(CheckTestCase): - def test_not_integer(self): class ValidationTestInline(TabularInline): model = ValidationTestInlineModel - min_num = 'hello' + min_num = "hello" class TestModelAdmin(ModelAdmin): inlines = [ValidationTestInline] self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'min_num' must be an integer.", - 'admin.E205', - invalid_obj=ValidationTestInline + "admin.E205", + invalid_obj=ValidationTestInline, ) def test_valid_case(self): @@ -1233,7 +1298,6 @@ class MinNumCheckTests(CheckTestCase): class FormsetCheckTests(CheckTestCase): - def test_invalid_type(self): class FakeFormSet: pass @@ -1246,25 +1310,27 @@ class FormsetCheckTests(CheckTestCase): inlines = [ValidationTestInline] self.assertIsInvalid( - TestModelAdmin, ValidationTestModel, + TestModelAdmin, + ValidationTestModel, "The value of 'formset' must inherit from 'BaseModelFormSet'.", - 'admin.E206', - invalid_obj=ValidationTestInline + "admin.E206", + invalid_obj=ValidationTestInline, ) def test_inline_without_formset_class(self): class ValidationTestInlineWithoutFormsetClass(TabularInline): model = ValidationTestInlineModel - formset = 'Not a FormSet Class' + formset = "Not a FormSet Class" class TestModelAdminWithoutFormsetClass(ModelAdmin): inlines = [ValidationTestInlineWithoutFormsetClass] self.assertIsInvalid( - TestModelAdminWithoutFormsetClass, ValidationTestModel, + TestModelAdminWithoutFormsetClass, + ValidationTestModel, "The value of 'formset' must inherit from 'BaseModelFormSet'.", - 'admin.E206', - invalid_obj=ValidationTestInlineWithoutFormsetClass + "admin.E206", + invalid_obj=ValidationTestInlineWithoutFormsetClass, ) def test_valid_case(self): @@ -1287,10 +1353,12 @@ class ListDisplayEditableTests(CheckTestCase): list_display and list_editable can contain the same values when list_display_links is None """ + class ProductAdmin(ModelAdmin): - list_display = ['name', 'slug', 'pub_date'] + list_display = ["name", "slug", "pub_date"] list_editable = list_display list_display_links = None + self.assertIsValid(ProductAdmin, ValidationTestModel) def test_list_display_first_item_same_as_list_editable_first_item(self): @@ -1298,10 +1366,12 @@ class ListDisplayEditableTests(CheckTestCase): The first item in list_display can be the same as the first in list_editable. """ + class ProductAdmin(ModelAdmin): - list_display = ['name', 'slug', 'pub_date'] - list_editable = ['name', 'slug'] - list_display_links = ['pub_date'] + list_display = ["name", "slug", "pub_date"] + list_editable = ["name", "slug"] + list_display_links = ["pub_date"] + self.assertIsValid(ProductAdmin, ValidationTestModel) def test_list_display_first_item_in_list_editable(self): @@ -1309,10 +1379,12 @@ class ListDisplayEditableTests(CheckTestCase): The first item in list_display can be in list_editable as long as list_display_links is defined. """ + class ProductAdmin(ModelAdmin): - list_display = ['name', 'slug', 'pub_date'] - list_editable = ['slug', 'name'] - list_display_links = ['pub_date'] + list_display = ["name", "slug", "pub_date"] + list_editable = ["slug", "name"] + list_display_links = ["pub_date"] + self.assertIsValid(ProductAdmin, ValidationTestModel) def test_list_display_first_item_same_as_list_editable_no_list_display_links(self): @@ -1320,15 +1392,18 @@ class ListDisplayEditableTests(CheckTestCase): The first item in list_display cannot be the same as the first item in list_editable if list_display_links is not defined. """ + class ProductAdmin(ModelAdmin): - list_display = ['name'] - list_editable = ['name'] + list_display = ["name"] + list_editable = ["name"] + self.assertIsInvalid( - ProductAdmin, ValidationTestModel, + ProductAdmin, + ValidationTestModel, "The value of 'list_editable[0]' refers to the first field " "in 'list_display' ('name'), which cannot be used unless " "'list_display_links' is set.", - id='admin.E124', + id="admin.E124", ) def test_list_display_first_item_in_list_editable_no_list_display_links(self): @@ -1336,81 +1411,90 @@ class ListDisplayEditableTests(CheckTestCase): The first item in list_display cannot be in list_editable if list_display_links isn't defined. """ + class ProductAdmin(ModelAdmin): - list_display = ['name', 'slug', 'pub_date'] - list_editable = ['slug', 'name'] + list_display = ["name", "slug", "pub_date"] + list_editable = ["slug", "name"] + self.assertIsInvalid( - ProductAdmin, ValidationTestModel, + ProductAdmin, + ValidationTestModel, "The value of 'list_editable[1]' refers to the first field " "in 'list_display' ('name'), which cannot be used unless " "'list_display_links' is set.", - id='admin.E124', + id="admin.E124", ) def test_both_list_editable_and_list_display_links(self): class ProductAdmin(ModelAdmin): - list_editable = ('name',) - list_display = ('name',) - list_display_links = ('name',) + list_editable = ("name",) + list_display = ("name",) + list_display_links = ("name",) + self.assertIsInvalid( - ProductAdmin, ValidationTestModel, + ProductAdmin, + ValidationTestModel, "The value of 'name' cannot be in both 'list_editable' and " "'list_display_links'.", - id='admin.E123', + id="admin.E123", ) class AutocompleteFieldsTests(CheckTestCase): def test_autocomplete_e036(self): class Admin(ModelAdmin): - autocomplete_fields = 'name' + autocomplete_fields = "name" self.assertIsInvalid( - Admin, Band, + Admin, + Band, msg="The value of 'autocomplete_fields' must be a list or tuple.", - id='admin.E036', + id="admin.E036", invalid_obj=Admin, ) def test_autocomplete_e037(self): class Admin(ModelAdmin): - autocomplete_fields = ('nonexistent',) + autocomplete_fields = ("nonexistent",) self.assertIsInvalid( - Admin, ValidationTestModel, + Admin, + ValidationTestModel, msg=( "The value of 'autocomplete_fields[0]' refers to 'nonexistent', " "which is not a field of 'modeladmin.ValidationTestModel'." ), - id='admin.E037', + id="admin.E037", invalid_obj=Admin, ) def test_autocomplete_e38(self): class Admin(ModelAdmin): - autocomplete_fields = ('name',) + autocomplete_fields = ("name",) self.assertIsInvalid( - Admin, ValidationTestModel, + Admin, + ValidationTestModel, msg=( "The value of 'autocomplete_fields[0]' must be a foreign " "key or a many-to-many field." ), - id='admin.E038', + id="admin.E038", invalid_obj=Admin, ) def test_autocomplete_e039(self): class Admin(ModelAdmin): - autocomplete_fields = ('band',) + autocomplete_fields = ("band",) self.assertIsInvalid( - Admin, Song, + Admin, + Song, msg=( 'An admin for model "Band" has to be registered ' - 'to be referenced by Admin.autocomplete_fields.' + "to be referenced by Admin.autocomplete_fields." ), - id='admin.E039', + id="admin.E039", invalid_obj=Admin, ) @@ -1419,27 +1503,28 @@ class AutocompleteFieldsTests(CheckTestCase): pass class AutocompleteAdmin(ModelAdmin): - autocomplete_fields = ('featuring',) + autocomplete_fields = ("featuring",) site = AdminSite() site.register(Band, NoSearchFieldsAdmin) self.assertIsInvalid( - AutocompleteAdmin, Song, + AutocompleteAdmin, + Song, msg=( 'NoSearchFieldsAdmin must define "search_fields", because ' - 'it\'s referenced by AutocompleteAdmin.autocomplete_fields.' + "it's referenced by AutocompleteAdmin.autocomplete_fields." ), - id='admin.E040', + id="admin.E040", invalid_obj=AutocompleteAdmin, admin_site=site, ) def test_autocomplete_is_valid(self): class SearchFieldsAdmin(ModelAdmin): - search_fields = 'name' + search_fields = "name" class AutocompleteAdmin(ModelAdmin): - autocomplete_fields = ('featuring',) + autocomplete_fields = ("featuring",) site = AdminSite() site.register(Band, SearchFieldsAdmin) @@ -1447,10 +1532,10 @@ class AutocompleteFieldsTests(CheckTestCase): def test_autocomplete_is_onetoone(self): class UserAdmin(ModelAdmin): - search_fields = ('name',) + search_fields = ("name",) class Admin(ModelAdmin): - autocomplete_fields = ('best_friend',) + autocomplete_fields = ("best_friend",) site = AdminSite() site.register(User, UserAdmin) @@ -1458,9 +1543,8 @@ class AutocompleteFieldsTests(CheckTestCase): class ActionsCheckTests(CheckTestCase): - def test_custom_permissions_require_matching_has_method(self): - @admin.action(permissions=['custom']) + @admin.action(permissions=["custom"]) def custom_permission_action(modeladmin, request, queryset): pass @@ -1468,10 +1552,11 @@ class ActionsCheckTests(CheckTestCase): actions = (custom_permission_action,) self.assertIsInvalid( - BandAdmin, Band, - 'BandAdmin must define a has_custom_permission() method for the ' - 'custom_permission_action action.', - id='admin.E129', + BandAdmin, + Band, + "BandAdmin must define a has_custom_permission() method for the " + "custom_permission_action action.", + id="admin.E129", ) def test_actions_not_unique(self): @@ -1483,10 +1568,11 @@ class ActionsCheckTests(CheckTestCase): actions = (action, action) self.assertIsInvalid( - BandAdmin, Band, + BandAdmin, + Band, "__name__ attributes of actions defined in BandAdmin must be " "unique. Name 'action' is not unique.", - id='admin.E130', + id="admin.E130", ) def test_actions_unique(self): diff --git a/tests/modeladmin/tests.py b/tests/modeladmin/tests.py index 6432679735..ede1a09212 100644 --- a/tests/modeladmin/tests.py +++ b/tests/modeladmin/tests.py @@ -3,12 +3,17 @@ from datetime import date from django import forms from django.contrib.admin.models import ADDITION, CHANGE, DELETION, LogEntry from django.contrib.admin.options import ( - HORIZONTAL, VERTICAL, ModelAdmin, TabularInline, + HORIZONTAL, + VERTICAL, + ModelAdmin, + TabularInline, get_content_type_for_model, ) from django.contrib.admin.sites import AdminSite from django.contrib.admin.widgets import ( - AdminDateWidget, AdminRadioSelect, AutocompleteSelect, + AdminDateWidget, + AdminRadioSelect, + AutocompleteSelect, AutocompleteSelectMultiple, ) from django.contrib.auth.models import User @@ -34,12 +39,11 @@ request.user = MockSuperUser() class ModelAdminTests(TestCase): - @classmethod def setUpTestData(cls): cls.band = Band.objects.create( - name='The Doors', - bio='', + name="The Doors", + bio="", sign_date=date(1965, 1, 1), ) @@ -48,7 +52,7 @@ class ModelAdminTests(TestCase): def test_modeladmin_str(self): ma = ModelAdmin(Band, self.site) - self.assertEqual(str(ma), 'modeladmin.ModelAdmin') + self.assertEqual(str(ma), "modeladmin.ModelAdmin") def test_default_attributes(self): ma = ModelAdmin(Band, self.site) @@ -59,9 +63,13 @@ class ModelAdminTests(TestCase): def test_default_fields(self): ma = ModelAdmin(Band, self.site) - self.assertEqual(list(ma.get_form(request).base_fields), ['name', 'bio', 'sign_date']) - self.assertEqual(list(ma.get_fields(request)), ['name', 'bio', 'sign_date']) - self.assertEqual(list(ma.get_fields(request, self.band)), ['name', 'bio', 'sign_date']) + self.assertEqual( + list(ma.get_form(request).base_fields), ["name", "bio", "sign_date"] + ) + self.assertEqual(list(ma.get_fields(request)), ["name", "bio", "sign_date"]) + self.assertEqual( + list(ma.get_fields(request, self.band)), ["name", "bio", "sign_date"] + ) self.assertIsNone(ma.get_exclude(request, self.band)) def test_default_fieldsets(self): @@ -72,43 +80,50 @@ class ModelAdminTests(TestCase): # Here's the default case. There are no custom form_add/form_change methods, # no fields argument, and no fieldsets argument. ma = ModelAdmin(Band, self.site) - self.assertEqual(ma.get_fieldsets(request), [(None, {'fields': ['name', 'bio', 'sign_date']})]) - self.assertEqual(ma.get_fieldsets(request, self.band), [(None, {'fields': ['name', 'bio', 'sign_date']})]) + self.assertEqual( + ma.get_fieldsets(request), + [(None, {"fields": ["name", "bio", "sign_date"]})], + ) + self.assertEqual( + ma.get_fieldsets(request, self.band), + [(None, {"fields": ["name", "bio", "sign_date"]})], + ) def test_get_fieldsets(self): # get_fieldsets() is called when figuring out form fields (#18681). class BandAdmin(ModelAdmin): def get_fieldsets(self, request, obj=None): - return [(None, {'fields': ['name', 'bio']})] + return [(None, {"fields": ["name", "bio"]})] ma = BandAdmin(Band, self.site) form = ma.get_form(None) - self.assertEqual(form._meta.fields, ['name', 'bio']) + self.assertEqual(form._meta.fields, ["name", "bio"]) class InlineBandAdmin(TabularInline): model = Concert - fk_name = 'main_band' + fk_name = "main_band" can_delete = False def get_fieldsets(self, request, obj=None): - return [(None, {'fields': ['day', 'transport']})] + return [(None, {"fields": ["day", "transport"]})] ma = InlineBandAdmin(Band, self.site) form = ma.get_formset(None).form - self.assertEqual(form._meta.fields, ['day', 'transport']) + self.assertEqual(form._meta.fields, ["day", "transport"]) def test_lookup_allowed_allows_nonexistent_lookup(self): """ A lookup_allowed allows a parameter whose field lookup doesn't exist. (#21129). """ + class BandAdmin(ModelAdmin): - fields = ['name'] + fields = ["name"] ma = BandAdmin(Band, self.site) - self.assertTrue(ma.lookup_allowed('name__nonexistent', 'test_value')) + self.assertTrue(ma.lookup_allowed("name__nonexistent", "test_value")) - @isolate_apps('modeladmin') + @isolate_apps("modeladmin") def test_lookup_allowed_onetoone(self): class Department(models.Model): code = models.CharField(max_length=4, unique=True) @@ -125,28 +140,34 @@ class ModelAdminTests(TestCase): class EmployeeProfileAdmin(ModelAdmin): list_filter = [ - 'employee__employeeinfo__description', - 'employee__department__code', + "employee__employeeinfo__description", + "employee__department__code", ] ma = EmployeeProfileAdmin(EmployeeProfile, self.site) # Reverse OneToOneField - self.assertIs(ma.lookup_allowed('employee__employeeinfo__description', 'test_value'), True) + self.assertIs( + ma.lookup_allowed("employee__employeeinfo__description", "test_value"), True + ) # OneToOneField and ForeignKey - self.assertIs(ma.lookup_allowed('employee__department__code', 'test_value'), True) + self.assertIs( + ma.lookup_allowed("employee__department__code", "test_value"), True + ) def test_field_arguments(self): # If fields is specified, fieldsets_add and fieldsets_change should # just stick the fields into a formsets structure and return it. class BandAdmin(ModelAdmin): - fields = ['name'] + fields = ["name"] ma = BandAdmin(Band, self.site) - self.assertEqual(list(ma.get_fields(request)), ['name']) - self.assertEqual(list(ma.get_fields(request, self.band)), ['name']) - self.assertEqual(ma.get_fieldsets(request), [(None, {'fields': ['name']})]) - self.assertEqual(ma.get_fieldsets(request, self.band), [(None, {'fields': ['name']})]) + self.assertEqual(list(ma.get_fields(request)), ["name"]) + self.assertEqual(list(ma.get_fields(request, self.band)), ["name"]) + self.assertEqual(ma.get_fieldsets(request), [(None, {"fields": ["name"]})]) + self.assertEqual( + ma.get_fieldsets(request, self.band), [(None, {"fields": ["name"]})] + ) def test_field_arguments_restricted_on_form(self): # If fields or fieldsets is specified, it should exclude fields on the @@ -157,41 +178,41 @@ class ModelAdminTests(TestCase): # Using `fields`. class BandAdmin(ModelAdmin): - fields = ['name'] + fields = ["name"] ma = BandAdmin(Band, self.site) - self.assertEqual(list(ma.get_form(request).base_fields), ['name']) - self.assertEqual(list(ma.get_form(request, self.band).base_fields), ['name']) + self.assertEqual(list(ma.get_form(request).base_fields), ["name"]) + self.assertEqual(list(ma.get_form(request, self.band).base_fields), ["name"]) # Using `fieldsets`. class BandAdmin(ModelAdmin): - fieldsets = [(None, {'fields': ['name']})] + fieldsets = [(None, {"fields": ["name"]})] ma = BandAdmin(Band, self.site) - self.assertEqual(list(ma.get_form(request).base_fields), ['name']) - self.assertEqual(list(ma.get_form(request, self.band).base_fields), ['name']) + self.assertEqual(list(ma.get_form(request).base_fields), ["name"]) + self.assertEqual(list(ma.get_form(request, self.band).base_fields), ["name"]) # Using `exclude`. class BandAdmin(ModelAdmin): - exclude = ['bio'] + exclude = ["bio"] ma = BandAdmin(Band, self.site) - self.assertEqual(list(ma.get_form(request).base_fields), ['name', 'sign_date']) + self.assertEqual(list(ma.get_form(request).base_fields), ["name", "sign_date"]) # You can also pass a tuple to `exclude`. class BandAdmin(ModelAdmin): - exclude = ('bio',) + exclude = ("bio",) ma = BandAdmin(Band, self.site) - self.assertEqual(list(ma.get_form(request).base_fields), ['name', 'sign_date']) + self.assertEqual(list(ma.get_form(request).base_fields), ["name", "sign_date"]) # Using `fields` and `exclude`. class BandAdmin(ModelAdmin): - fields = ['name', 'bio'] - exclude = ['bio'] + fields = ["name", "bio"] + exclude = ["bio"] ma = BandAdmin(Band, self.site) - self.assertEqual(list(ma.get_form(request).base_fields), ['name']) + self.assertEqual(list(ma.get_form(request).base_fields), ["name"]) def test_custom_form_meta_exclude_with_readonly(self): """ @@ -203,25 +224,25 @@ class ModelAdminTests(TestCase): class AdminBandForm(forms.ModelForm): class Meta: model = Band - exclude = ['bio'] + exclude = ["bio"] class BandAdmin(ModelAdmin): - readonly_fields = ['name'] + readonly_fields = ["name"] form = AdminBandForm ma = BandAdmin(Band, self.site) - self.assertEqual(list(ma.get_form(request).base_fields), ['sign_date']) + self.assertEqual(list(ma.get_form(request).base_fields), ["sign_date"]) # With InlineModelAdmin class AdminConcertForm(forms.ModelForm): class Meta: model = Concert - exclude = ['day'] + exclude = ["day"] class ConcertInline(TabularInline): - readonly_fields = ['transport'] + readonly_fields = ["transport"] form = AdminConcertForm - fk_name = 'main_band' + fk_name = "main_band" model = Concert class BandAdmin(ModelAdmin): @@ -230,7 +251,8 @@ class ModelAdminTests(TestCase): ma = BandAdmin(Band, self.site) self.assertEqual( list(list(ma.get_formsets_with_inlines(request))[0][0]().forms[0].fields), - ['main_band', 'opening_band', 'id', 'DELETE']) + ["main_band", "opening_band", "id", "DELETE"], + ) def test_custom_formfield_override_readonly(self): class AdminBandForm(forms.ModelForm): @@ -242,25 +264,19 @@ class ModelAdminTests(TestCase): class BandAdmin(ModelAdmin): form = AdminBandForm - readonly_fields = ['name'] + readonly_fields = ["name"] ma = BandAdmin(Band, self.site) # `name` shouldn't appear in base_fields because it's part of # readonly_fields. - self.assertEqual( - list(ma.get_form(request).base_fields), - ['bio', 'sign_date'] - ) + self.assertEqual(list(ma.get_form(request).base_fields), ["bio", "sign_date"]) # But it should appear in get_fields()/fieldsets() so it can be # displayed as read-only. - self.assertEqual( - list(ma.get_fields(request)), - ['bio', 'sign_date', 'name'] - ) + self.assertEqual(list(ma.get_fields(request)), ["bio", "sign_date", "name"]) self.assertEqual( list(ma.get_fieldsets(request)), - [(None, {'fields': ['bio', 'sign_date', 'name']})] + [(None, {"fields": ["bio", "sign_date", "name"]})], ) def test_custom_form_meta_exclude(self): @@ -272,25 +288,25 @@ class ModelAdminTests(TestCase): class AdminBandForm(forms.ModelForm): class Meta: model = Band - exclude = ['bio'] + exclude = ["bio"] class BandAdmin(ModelAdmin): - exclude = ['name'] + exclude = ["name"] form = AdminBandForm ma = BandAdmin(Band, self.site) - self.assertEqual(list(ma.get_form(request).base_fields), ['bio', 'sign_date']) + self.assertEqual(list(ma.get_form(request).base_fields), ["bio", "sign_date"]) # With InlineModelAdmin class AdminConcertForm(forms.ModelForm): class Meta: model = Concert - exclude = ['day'] + exclude = ["day"] class ConcertInline(TabularInline): - exclude = ['transport'] + exclude = ["transport"] form = AdminConcertForm - fk_name = 'main_band' + fk_name = "main_band" model = Concert class BandAdmin(ModelAdmin): @@ -299,41 +315,41 @@ class ModelAdminTests(TestCase): ma = BandAdmin(Band, self.site) self.assertEqual( list(list(ma.get_formsets_with_inlines(request))[0][0]().forms[0].fields), - ['main_band', 'opening_band', 'day', 'id', 'DELETE'] + ["main_band", "opening_band", "day", "id", "DELETE"], ) def test_overriding_get_exclude(self): class BandAdmin(ModelAdmin): def get_exclude(self, request, obj=None): - return ['name'] + return ["name"] self.assertEqual( list(BandAdmin(Band, self.site).get_form(request).base_fields), - ['bio', 'sign_date'] + ["bio", "sign_date"], ) def test_get_exclude_overrides_exclude(self): class BandAdmin(ModelAdmin): - exclude = ['bio'] + exclude = ["bio"] def get_exclude(self, request, obj=None): - return ['name'] + return ["name"] self.assertEqual( list(BandAdmin(Band, self.site).get_form(request).base_fields), - ['bio', 'sign_date'] + ["bio", "sign_date"], ) def test_get_exclude_takes_obj(self): class BandAdmin(ModelAdmin): def get_exclude(self, request, obj=None): if obj: - return ['sign_date'] - return ['name'] + return ["sign_date"] + return ["name"] self.assertEqual( list(BandAdmin(Band, self.site).get_form(request, self.band).base_fields), - ['name', 'bio'] + ["name", "bio"], ) def test_custom_form_validation(self): @@ -346,48 +362,55 @@ class ModelAdminTests(TestCase): form = AdminBandForm ma = BandAdmin(Band, self.site) - self.assertEqual(list(ma.get_form(request).base_fields), ['name', 'bio', 'sign_date', 'delete']) - self.assertEqual(type(ma.get_form(request).base_fields['sign_date'].widget), AdminDateWidget) + self.assertEqual( + list(ma.get_form(request).base_fields), + ["name", "bio", "sign_date", "delete"], + ) + self.assertEqual( + type(ma.get_form(request).base_fields["sign_date"].widget), AdminDateWidget + ) def test_form_exclude_kwarg_override(self): """ The `exclude` kwarg passed to `ModelAdmin.get_form()` overrides all other declarations (#8999). """ + class AdminBandForm(forms.ModelForm): class Meta: model = Band - exclude = ['name'] + exclude = ["name"] class BandAdmin(ModelAdmin): - exclude = ['sign_date'] + exclude = ["sign_date"] form = AdminBandForm def get_form(self, request, obj=None, **kwargs): - kwargs['exclude'] = ['bio'] + kwargs["exclude"] = ["bio"] return super().get_form(request, obj, **kwargs) ma = BandAdmin(Band, self.site) - self.assertEqual(list(ma.get_form(request).base_fields), ['name', 'sign_date']) + self.assertEqual(list(ma.get_form(request).base_fields), ["name", "sign_date"]) def test_formset_exclude_kwarg_override(self): """ The `exclude` kwarg passed to `InlineModelAdmin.get_formset()` overrides all other declarations (#8999). """ + class AdminConcertForm(forms.ModelForm): class Meta: model = Concert - exclude = ['day'] + exclude = ["day"] class ConcertInline(TabularInline): - exclude = ['transport'] + exclude = ["transport"] form = AdminConcertForm - fk_name = 'main_band' + fk_name = "main_band" model = Concert def get_formset(self, request, obj=None, **kwargs): - kwargs['exclude'] = ['opening_band'] + kwargs["exclude"] = ["opening_band"] return super().get_formset(request, obj, **kwargs) class BandAdmin(ModelAdmin): @@ -396,22 +419,22 @@ class ModelAdminTests(TestCase): ma = BandAdmin(Band, self.site) self.assertEqual( list(list(ma.get_formsets_with_inlines(request))[0][0]().forms[0].fields), - ['main_band', 'day', 'transport', 'id', 'DELETE'] + ["main_band", "day", "transport", "id", "DELETE"], ) def test_formset_overriding_get_exclude_with_form_fields(self): class AdminConcertForm(forms.ModelForm): class Meta: model = Concert - fields = ['main_band', 'opening_band', 'day', 'transport'] + fields = ["main_band", "opening_band", "day", "transport"] class ConcertInline(TabularInline): form = AdminConcertForm - fk_name = 'main_band' + fk_name = "main_band" model = Concert def get_exclude(self, request, obj=None): - return ['opening_band'] + return ["opening_band"] class BandAdmin(ModelAdmin): inlines = [ConcertInline] @@ -419,22 +442,22 @@ class ModelAdminTests(TestCase): ma = BandAdmin(Band, self.site) self.assertEqual( list(list(ma.get_formsets_with_inlines(request))[0][0]().forms[0].fields), - ['main_band', 'day', 'transport', 'id', 'DELETE'] + ["main_band", "day", "transport", "id", "DELETE"], ) def test_formset_overriding_get_exclude_with_form_exclude(self): class AdminConcertForm(forms.ModelForm): class Meta: model = Concert - exclude = ['day'] + exclude = ["day"] class ConcertInline(TabularInline): form = AdminConcertForm - fk_name = 'main_band' + fk_name = "main_band" model = Concert def get_exclude(self, request, obj=None): - return ['opening_band'] + return ["opening_band"] class BandAdmin(ModelAdmin): inlines = [ConcertInline] @@ -442,7 +465,7 @@ class ModelAdminTests(TestCase): ma = BandAdmin(Band, self.site) self.assertEqual( list(list(ma.get_formsets_with_inlines(request))[0][0]().forms[0].fields), - ['main_band', 'day', 'transport', 'id', 'DELETE'] + ["main_band", "day", "transport", "id", "DELETE"], ) def test_raw_id_fields_widget_override(self): @@ -450,27 +473,35 @@ class ModelAdminTests(TestCase): The autocomplete_fields, raw_id_fields, and radio_fields widgets may overridden by specifying a widget in get_formset(). """ + class ConcertInline(TabularInline): model = Concert - fk_name = 'main_band' - raw_id_fields = ('opening_band',) + fk_name = "main_band" + raw_id_fields = ("opening_band",) def get_formset(self, request, obj=None, **kwargs): - kwargs['widgets'] = {'opening_band': Select} + kwargs["widgets"] = {"opening_band": Select} return super().get_formset(request, obj, **kwargs) class BandAdmin(ModelAdmin): inlines = [ConcertInline] ma = BandAdmin(Band, self.site) - band_widget = list(ma.get_formsets_with_inlines(request))[0][0]().forms[0].fields['opening_band'].widget + band_widget = ( + list(ma.get_formsets_with_inlines(request))[0][0]() + .forms[0] + .fields["opening_band"] + .widget + ) # Without the override this would be ForeignKeyRawIdWidget. self.assertIsInstance(band_widget, Select) def test_queryset_override(self): # If the queryset of a ModelChoiceField in a custom form is overridden, # RelatedFieldWidgetWrapper doesn't mess that up. - band2 = Band.objects.create(name='The Beatles', bio='', sign_date=date(1962, 1, 1)) + band2 = Band.objects.create( + name="The Beatles", bio="", sign_date=date(1962, 1, 1) + ) ma = ModelAdmin(Concert, self.site) form = ma.get_form(request)() @@ -482,13 +513,15 @@ class ModelAdminTests(TestCase): '<option value="" selected>---------</option>' '<option value="%d">The Beatles</option>' '<option value="%d">The Doors</option>' - '</select></div>' % (band2.id, self.band.id) + "</select></div>" % (band2.id, self.band.id), ) class AdminConcertForm(forms.ModelForm): def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) - self.fields["main_band"].queryset = Band.objects.filter(name='The Doors') + self.fields["main_band"].queryset = Band.objects.filter( + name="The Doors" + ) class ConcertAdminWithForm(ModelAdmin): form = AdminConcertForm @@ -502,7 +535,7 @@ class ModelAdminTests(TestCase): '<select name="main_band" id="id_main_band" required>' '<option value="" selected>---------</option>' '<option value="%d">The Doors</option>' - '</select></div>' % self.band.id + "</select></div>" % self.band.id, ) def test_regression_for_ticket_15820(self): @@ -510,18 +543,19 @@ class ModelAdminTests(TestCase): `obj` is passed from `InlineModelAdmin.get_fieldsets()` to `InlineModelAdmin.get_formset()`. """ + class CustomConcertForm(forms.ModelForm): class Meta: model = Concert - fields = ['day'] + fields = ["day"] class ConcertInline(TabularInline): model = Concert - fk_name = 'main_band' + fk_name = "main_band" def get_formset(self, request, obj=None, **kwargs): if obj: - kwargs['form'] = CustomConcertForm + kwargs["form"] = CustomConcertForm return super().get_formset(request, obj, **kwargs) class BandAdmin(ModelAdmin): @@ -531,9 +565,13 @@ class ModelAdminTests(TestCase): ma = BandAdmin(Band, self.site) inline_instances = ma.get_inline_instances(request) fieldsets = list(inline_instances[0].get_fieldsets(request)) - self.assertEqual(fieldsets[0][1]['fields'], ['main_band', 'opening_band', 'day', 'transport']) - fieldsets = list(inline_instances[0].get_fieldsets(request, inline_instances[0].model)) - self.assertEqual(fieldsets[0][1]['fields'], ['day']) + self.assertEqual( + fieldsets[0][1]["fields"], ["main_band", "opening_band", "day", "transport"] + ) + fieldsets = list( + inline_instances[0].get_fieldsets(request, inline_instances[0].model) + ) + self.assertEqual(fieldsets[0][1]["fields"], ["day"]) # radio_fields behavior ########################################### @@ -546,25 +584,27 @@ class ModelAdminTests(TestCase): cma = ModelAdmin(Concert, self.site) cmafa = cma.get_form(request) - self.assertEqual(type(cmafa.base_fields['main_band'].widget.widget), Select) + self.assertEqual(type(cmafa.base_fields["main_band"].widget.widget), Select) self.assertEqual( - list(cmafa.base_fields['main_band'].widget.choices), - [('', '---------'), (self.band.id, 'The Doors')]) + list(cmafa.base_fields["main_band"].widget.choices), + [("", "---------"), (self.band.id, "The Doors")], + ) - self.assertEqual(type(cmafa.base_fields['opening_band'].widget.widget), Select) + self.assertEqual(type(cmafa.base_fields["opening_band"].widget.widget), Select) self.assertEqual( - list(cmafa.base_fields['opening_band'].widget.choices), - [('', '---------'), (self.band.id, 'The Doors')] + list(cmafa.base_fields["opening_band"].widget.choices), + [("", "---------"), (self.band.id, "The Doors")], ) - self.assertEqual(type(cmafa.base_fields['day'].widget), Select) + self.assertEqual(type(cmafa.base_fields["day"].widget), Select) self.assertEqual( - list(cmafa.base_fields['day'].widget.choices), - [('', '---------'), (1, 'Fri'), (2, 'Sat')] + list(cmafa.base_fields["day"].widget.choices), + [("", "---------"), (1, "Fri"), (2, "Sat")], ) - self.assertEqual(type(cmafa.base_fields['transport'].widget), Select) + self.assertEqual(type(cmafa.base_fields["transport"].widget), Select) self.assertEqual( - list(cmafa.base_fields['transport'].widget.choices), - [('', '---------'), (1, 'Plane'), (2, 'Train'), (3, 'Bus')]) + list(cmafa.base_fields["transport"].widget.choices), + [("", "---------"), (1, "Plane"), (2, "Train"), (3, "Bus")], + ) def test_foreign_key_as_radio_field(self): # Now specify all the fields as radio_fields. Widgets should now be @@ -573,67 +613,81 @@ class ModelAdminTests(TestCase): # 'radiolist' attr, and 'inline' as well if the field is specified HORIZONTAL. class ConcertAdmin(ModelAdmin): radio_fields = { - 'main_band': HORIZONTAL, - 'opening_band': VERTICAL, - 'day': VERTICAL, - 'transport': HORIZONTAL, + "main_band": HORIZONTAL, + "opening_band": VERTICAL, + "day": VERTICAL, + "transport": HORIZONTAL, } cma = ConcertAdmin(Concert, self.site) cmafa = cma.get_form(request) - self.assertEqual(type(cmafa.base_fields['main_band'].widget.widget), AdminRadioSelect) - self.assertEqual(cmafa.base_fields['main_band'].widget.attrs, {'class': 'radiolist inline'}) self.assertEqual( - list(cmafa.base_fields['main_band'].widget.choices), - [(self.band.id, 'The Doors')] + type(cmafa.base_fields["main_band"].widget.widget), AdminRadioSelect + ) + self.assertEqual( + cmafa.base_fields["main_band"].widget.attrs, {"class": "radiolist inline"} + ) + self.assertEqual( + list(cmafa.base_fields["main_band"].widget.choices), + [(self.band.id, "The Doors")], ) - self.assertEqual(type(cmafa.base_fields['opening_band'].widget.widget), AdminRadioSelect) - self.assertEqual(cmafa.base_fields['opening_band'].widget.attrs, {'class': 'radiolist'}) self.assertEqual( - list(cmafa.base_fields['opening_band'].widget.choices), - [('', 'None'), (self.band.id, 'The Doors')] + type(cmafa.base_fields["opening_band"].widget.widget), AdminRadioSelect + ) + self.assertEqual( + cmafa.base_fields["opening_band"].widget.attrs, {"class": "radiolist"} + ) + self.assertEqual( + list(cmafa.base_fields["opening_band"].widget.choices), + [("", "None"), (self.band.id, "The Doors")], + ) + self.assertEqual(type(cmafa.base_fields["day"].widget), AdminRadioSelect) + self.assertEqual(cmafa.base_fields["day"].widget.attrs, {"class": "radiolist"}) + self.assertEqual( + list(cmafa.base_fields["day"].widget.choices), [(1, "Fri"), (2, "Sat")] ) - self.assertEqual(type(cmafa.base_fields['day'].widget), AdminRadioSelect) - self.assertEqual(cmafa.base_fields['day'].widget.attrs, {'class': 'radiolist'}) - self.assertEqual(list(cmafa.base_fields['day'].widget.choices), [(1, 'Fri'), (2, 'Sat')]) - self.assertEqual(type(cmafa.base_fields['transport'].widget), AdminRadioSelect) - self.assertEqual(cmafa.base_fields['transport'].widget.attrs, {'class': 'radiolist inline'}) + self.assertEqual(type(cmafa.base_fields["transport"].widget), AdminRadioSelect) self.assertEqual( - list(cmafa.base_fields['transport'].widget.choices), - [('', 'None'), (1, 'Plane'), (2, 'Train'), (3, 'Bus')] + cmafa.base_fields["transport"].widget.attrs, {"class": "radiolist inline"} + ) + self.assertEqual( + list(cmafa.base_fields["transport"].widget.choices), + [("", "None"), (1, "Plane"), (2, "Train"), (3, "Bus")], ) class AdminConcertForm(forms.ModelForm): class Meta: model = Concert - exclude = ('transport',) + exclude = ("transport",) class ConcertAdmin(ModelAdmin): form = AdminConcertForm ma = ConcertAdmin(Concert, self.site) - self.assertEqual(list(ma.get_form(request).base_fields), ['main_band', 'opening_band', 'day']) + self.assertEqual( + list(ma.get_form(request).base_fields), ["main_band", "opening_band", "day"] + ) class AdminConcertForm(forms.ModelForm): extra = forms.CharField() class Meta: model = Concert - fields = ['extra', 'transport'] + fields = ["extra", "transport"] class ConcertAdmin(ModelAdmin): form = AdminConcertForm ma = ConcertAdmin(Concert, self.site) - self.assertEqual(list(ma.get_form(request).base_fields), ['extra', 'transport']) + self.assertEqual(list(ma.get_form(request).base_fields), ["extra", "transport"]) class ConcertInline(TabularInline): form = AdminConcertForm model = Concert - fk_name = 'main_band' + fk_name = "main_band" can_delete = True class BandAdmin(ModelAdmin): @@ -642,30 +696,30 @@ class ModelAdminTests(TestCase): ma = BandAdmin(Band, self.site) self.assertEqual( list(list(ma.get_formsets_with_inlines(request))[0][0]().forms[0].fields), - ['extra', 'transport', 'id', 'DELETE', 'main_band'] + ["extra", "transport", "id", "DELETE", "main_band"], ) def test_log_actions(self): ma = ModelAdmin(Band, self.site) mock_request = MockRequest() - mock_request.user = User.objects.create(username='bill') + mock_request.user = User.objects.create(username="bill") content_type = get_content_type_for_model(self.band) tests = ( - (ma.log_addition, ADDITION, {'added': {}}), - (ma.log_change, CHANGE, {'changed': {'fields': ['name', 'bio']}}), + (ma.log_addition, ADDITION, {"added": {}}), + (ma.log_change, CHANGE, {"changed": {"fields": ["name", "bio"]}}), (ma.log_deletion, DELETION, str(self.band)), ) for method, flag, message in tests: with self.subTest(name=method.__name__): created = method(mock_request, self.band, message) - fetched = LogEntry.objects.filter(action_flag=flag).latest('id') + fetched = LogEntry.objects.filter(action_flag=flag).latest("id") self.assertEqual(created, fetched) self.assertEqual(fetched.action_flag, flag) self.assertEqual(fetched.content_type, content_type) self.assertEqual(fetched.object_id, str(self.band.pk)) self.assertEqual(fetched.user, mock_request.user) if flag == DELETION: - self.assertEqual(fetched.change_message, '') + self.assertEqual(fetched.change_message, "") self.assertEqual(fetched.object_repr, message) else: self.assertEqual(fetched.change_message, str(message)) @@ -673,37 +727,46 @@ class ModelAdminTests(TestCase): def test_get_autocomplete_fields(self): class NameAdmin(ModelAdmin): - search_fields = ['name'] + search_fields = ["name"] class SongAdmin(ModelAdmin): - autocomplete_fields = ['featuring'] - fields = ['featuring', 'band'] + autocomplete_fields = ["featuring"] + fields = ["featuring", "band"] class OtherSongAdmin(SongAdmin): def get_autocomplete_fields(self, request): - return ['band'] + return ["band"] self.site.register(Band, NameAdmin) try: # Uses autocomplete_fields if not overridden. model_admin = SongAdmin(Song, self.site) form = model_admin.get_form(request)() - self.assertIsInstance(form.fields['featuring'].widget.widget, AutocompleteSelectMultiple) + self.assertIsInstance( + form.fields["featuring"].widget.widget, AutocompleteSelectMultiple + ) # Uses overridden get_autocomplete_fields model_admin = OtherSongAdmin(Song, self.site) form = model_admin.get_form(request)() - self.assertIsInstance(form.fields['band'].widget.widget, AutocompleteSelect) + self.assertIsInstance(form.fields["band"].widget.widget, AutocompleteSelect) finally: self.site.unregister(Band) def test_get_deleted_objects(self): mock_request = MockRequest() - mock_request.user = User.objects.create_superuser(username='bob', email='bob@test.com', password='test') + mock_request.user = User.objects.create_superuser( + username="bob", email="bob@test.com", password="test" + ) self.site.register(Band, ModelAdmin) ma = self.site._registry[Band] - deletable_objects, model_count, perms_needed, protected = ma.get_deleted_objects([self.band], request) - self.assertEqual(deletable_objects, ['Band: The Doors']) - self.assertEqual(model_count, {'bands': 1}) + ( + deletable_objects, + model_count, + perms_needed, + protected, + ) = ma.get_deleted_objects([self.band], request) + self.assertEqual(deletable_objects, ["Band: The Doors"]) + self.assertEqual(model_count, {"bands": 1}) self.assertEqual(perms_needed, set()) self.assertEqual(protected, []) @@ -713,7 +776,9 @@ class ModelAdminTests(TestCase): for permissions checking. """ mock_request = MockRequest() - mock_request.user = User.objects.create_superuser(username='bob', email='bob@test.com', password='test') + mock_request.user = User.objects.create_superuser( + username="bob", email="bob@test.com", password="test" + ) class TestModelAdmin(ModelAdmin): def has_delete_permission(self, request, obj=None): @@ -721,10 +786,15 @@ class ModelAdminTests(TestCase): self.site.register(Band, TestModelAdmin) ma = self.site._registry[Band] - deletable_objects, model_count, perms_needed, protected = ma.get_deleted_objects([self.band], request) - self.assertEqual(deletable_objects, ['Band: The Doors']) - self.assertEqual(model_count, {'bands': 1}) - self.assertEqual(perms_needed, {'band'}) + ( + deletable_objects, + model_count, + perms_needed, + protected, + ) = ma.get_deleted_objects([self.band], request) + self.assertEqual(deletable_objects, ["Band: The Doors"]) + self.assertEqual(model_count, {"bands": 1}) + self.assertEqual(perms_needed, {"band"}) self.assertEqual(protected, []) def test_modeladmin_repr(self): @@ -736,26 +806,25 @@ class ModelAdminTests(TestCase): class ModelAdminPermissionTests(SimpleTestCase): - class MockUser: def has_module_perms(self, app_label): - return app_label == 'modeladmin' + return app_label == "modeladmin" class MockViewUser(MockUser): def has_perm(self, perm, obj=None): - return perm == 'modeladmin.view_band' + return perm == "modeladmin.view_band" class MockAddUser(MockUser): def has_perm(self, perm, obj=None): - return perm == 'modeladmin.add_band' + return perm == "modeladmin.add_band" class MockChangeUser(MockUser): def has_perm(self, perm, obj=None): - return perm == 'modeladmin.change_band' + return perm == "modeladmin.change_band" class MockDeleteUser(MockUser): def has_perm(self, perm, obj=None): - return perm == 'modeladmin.delete_band' + return perm == "modeladmin.delete_band" def test_has_view_permission(self): """ @@ -803,7 +872,7 @@ class ModelAdminPermissionTests(SimpleTestCase): request = MockRequest() request.user = self.MockAddUser() self.assertEqual(ma.get_inline_instances(request), []) - band = Band(name='The Doors', bio='', sign_date=date(1965, 1, 1)) + band = Band(name="The Doors", bio="", sign_date=date(1965, 1, 1)) inline_instances = ma.get_inline_instances(request, band) self.assertEqual(len(inline_instances), 1) self.assertIsInstance(inline_instances[0], ConcertInline) @@ -857,7 +926,7 @@ class ModelAdminPermissionTests(SimpleTestCase): self.assertTrue(ma.has_module_permission(request)) original_app_label = ma.opts.app_label - ma.opts.app_label = 'anotherapp' + ma.opts.app_label = "anotherapp" try: request.user = self.MockViewUser() self.assertIs(ma.has_module_permission(request), False) |