Skip to content

Commit d381914

Browse files
mick88timgraham
authored andcommitted
Fixed #28313 -- Added model name max length check of 100 characters in contrib.contentttypes.
1 parent 44a7b98 commit d381914

File tree

4 files changed

+44
-1
lines changed

4 files changed

+44
-1
lines changed

django/contrib/contenttypes/apps.py

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
from django.apps import AppConfig
2-
from django.contrib.contenttypes.checks import check_generic_foreign_keys
2+
from django.contrib.contenttypes.checks import (
3+
check_generic_foreign_keys, check_model_name_lengths,
4+
)
35
from django.core import checks
46
from django.db.models.signals import post_migrate, pre_migrate
57
from django.utils.translation import gettext_lazy as _
@@ -17,3 +19,4 @@ def ready(self):
1719
pre_migrate.connect(inject_rename_contenttypes_operations, sender=self)
1820
post_migrate.connect(create_contenttypes)
1921
checks.register(check_generic_foreign_keys, checks.Tags.models)
22+
checks.register(check_model_name_lengths, checks.Tags.models)

django/contrib/contenttypes/checks.py

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
from itertools import chain
22

33
from django.apps import apps
4+
from django.core.checks import Error
45

56

67
def check_generic_foreign_keys(app_configs=None, **kwargs):
@@ -18,3 +19,23 @@ def check_generic_foreign_keys(app_configs=None, **kwargs):
1819
for field in fields:
1920
errors.extend(field.check())
2021
return errors
22+
23+
24+
def check_model_name_lengths(app_configs=None, **kwargs):
25+
if app_configs is None:
26+
models = apps.get_models()
27+
else:
28+
models = chain.from_iterable(app_config.get_models() for app_config in app_configs)
29+
errors = []
30+
for model in models:
31+
if len(model._meta.model_name) > 100:
32+
errors.append(
33+
Error(
34+
'Model names must be at most 100 characters (got %d).' % (
35+
len(model._meta.model_name),
36+
),
37+
obj=model,
38+
id='contenttypes.E005',
39+
)
40+
)
41+
return errors

docs/ref/checks.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -668,6 +668,7 @@ The following checks are performed when a model contains a
668668
* **contenttypes.E003**: ``<field>`` is not a ``ForeignKey``.
669669
* **contenttypes.E004**: ``<field>`` is not a ``ForeignKey`` to
670670
``contenttypes.ContentType``.
671+
* **contenttypes.E005**: Model names must be at most 100 characters.
671672

672673
``sites``
673674
---------

tests/contenttypes_tests/test_checks.py

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
from unittest import mock
22

3+
from django.contrib.contenttypes.checks import check_model_name_lengths
34
from django.contrib.contenttypes.fields import (
45
GenericForeignKey, GenericRelation,
56
)
@@ -216,3 +217,20 @@ class InvalidBookmark(models.Model):
216217
id='fields.E001',
217218
)
218219
])
220+
221+
222+
@isolate_apps('contenttypes_tests', attr_name='apps')
223+
class ModelCheckTests(SimpleTestCase):
224+
def test_model_name_too_long(self):
225+
model = type('A' * 101, (models.Model,), {'__module__': self.__module__})
226+
self.assertEqual(check_model_name_lengths(self.apps.get_app_configs()), [
227+
checks.Error(
228+
'Model names must be at most 100 characters (got 101).',
229+
obj=model,
230+
id='contenttypes.E005',
231+
)
232+
])
233+
234+
def test_model_name_max_length(self):
235+
type('A' * 100, (models.Model,), {'__module__': self.__module__})
236+
self.assertEqual(check_model_name_lengths(self.apps.get_app_configs()), [])

0 commit comments

Comments
 (0)