Răsfoiți Sursa

fix(extras): Handle None ordering in TableConfig validation

Prevent TypeError when TableConfig.ordering is None by adding explicit
null check in clean(). Add regression test covering unset ordering
field.

Fixes #22206
Martin Hauser 6 zile în urmă
părinte
comite
90c371dee2
2 a modificat fișierele cu 22 adăugiri și 1 ștergeri
  1. 1 1
      netbox/extras/models/models.py
  2. 21 0
      netbox/extras/tests/test_models.py

+ 1 - 1
netbox/extras/models/models.py

@@ -658,7 +658,7 @@ class TableConfig(CloningMixin, ChangeLoggedModel):
         table = self.table_class([])
 
         # Validate ordering columns
-        for name in self.ordering:
+        for name in self.ordering or []:
             if name.startswith('-'):
                 name = name[1:]  # Strip leading hyphen
             if name not in table.columns:

+ 21 - 0
netbox/extras/tests/test_models.py

@@ -24,6 +24,7 @@ from extras.models import (
     EventRule,
     ExportTemplate,
     ImageAttachment,
+    TableConfig,
     Tag,
     TaggedItem,
 )
@@ -31,6 +32,7 @@ from extras.models.mixins import RenderTemplateMixin
 from tenancy.models import Tenant, TenantGroup
 from utilities.exceptions import AbortRequest
 from utilities.jinja2 import render_jinja2
+from utilities.tables import get_table_for_model
 from virtualization.models import Cluster, ClusterGroup, ClusterType, VirtualMachine
 
 
@@ -190,6 +192,25 @@ class ImageAttachmentTestCase(TestCase):
         self.assertCountEqual(storage.files.keys(), {base_name, suffixed_name})
 
 
+class TableConfigTestCase(TestCase):
+    @classmethod
+    def setUpTestData(cls):
+        cls.site_ct = ContentType.objects.get_for_model(Site)
+        cls.table_name = get_table_for_model(Site).__name__
+
+    def test_clean_accepts_ordering_none(self):
+        """clean() must accept ordering=None (field is null=True)."""
+        tc = TableConfig(
+            object_type=self.site_ct,
+            table=self.table_name,
+            name='No ordering',
+            columns=['name'],
+            # ordering left unset (defaults to None)
+        )
+        # Must not raise TypeError: 'NoneType' object is not iterable
+        tc.full_clean()
+
+
 class TagTestCase(TestCase):
 
     def test_default_ordering_weight_then_name_is_set(self):