Merge branch 'main' into nav-menu-callables

This commit is contained in:
Brian Tiemann 2025-06-12 16:42:50 -04:00
commit 9d6abcf57b
8 changed files with 49 additions and 17 deletions

View File

@ -53,6 +53,11 @@ WIRELESS_IFACE_TYPES = [
InterfaceTypeChoices.TYPE_802151, InterfaceTypeChoices.TYPE_802151,
InterfaceTypeChoices.TYPE_802154, InterfaceTypeChoices.TYPE_802154,
InterfaceTypeChoices.TYPE_OTHER_WIRELESS, InterfaceTypeChoices.TYPE_OTHER_WIRELESS,
InterfaceTypeChoices.TYPE_GSM,
InterfaceTypeChoices.TYPE_CDMA,
InterfaceTypeChoices.TYPE_LTE,
InterfaceTypeChoices.TYPE_4G,
InterfaceTypeChoices.TYPE_5G,
] ]
NONCONNECTABLE_IFACE_TYPES = VIRTUAL_IFACE_TYPES + WIRELESS_IFACE_TYPES NONCONNECTABLE_IFACE_TYPES = VIRTUAL_IFACE_TYPES + WIRELESS_IFACE_TYPES

View File

@ -954,6 +954,19 @@ class CableTestCase(TestCase):
with self.assertRaises(ValidationError): with self.assertRaises(ValidationError):
cable.clean() cable.clean()
@tag('regression')
def test_cable_cannot_terminate_to_a_cellular_interface(self):
"""
A cable cannot terminate to a cellular interface
"""
device1 = Device.objects.get(name='TestDevice1')
interface2 = Interface.objects.get(device__name='TestDevice2', name='eth0')
cellular_interface = Interface(device=device1, name="W1", type=InterfaceTypeChoices.TYPE_LTE)
cable = Cable(a_terminations=[interface2], b_terminations=[cellular_interface])
with self.assertRaises(ValidationError):
cable.clean()
class VirtualDeviceContextTestCase(TestCase): class VirtualDeviceContextTestCase(TestCase):

View File

@ -66,11 +66,11 @@ class ScriptInputSerializer(serializers.Serializer):
interval = serializers.IntegerField(required=False, allow_null=True) interval = serializers.IntegerField(required=False, allow_null=True)
def validate_schedule_at(self, value): def validate_schedule_at(self, value):
if value and not self.context['script'].scheduling_enabled: if value and not self.context['script'].python_class.scheduling_enabled:
raise serializers.ValidationError(_("Scheduling is not enabled for this script.")) raise serializers.ValidationError(_("Scheduling is not enabled for this script."))
return value return value
def validate_interval(self, value): def validate_interval(self, value):
if value and not self.context['script'].scheduling_enabled: if value and not self.context['script'].python_class.scheduling_enabled:
raise serializers.ValidationError(_("Scheduling is not enabled for this script.")) raise serializers.ValidationError(_("Scheduling is not enabled for this script."))
return value return value

View File

@ -270,6 +270,7 @@ class ScriptViewSet(ModelViewSet):
module_name, script_name = pk.split('.', maxsplit=1) module_name, script_name = pk.split('.', maxsplit=1)
except ValueError: except ValueError:
raise Http404 raise Http404
return get_object_or_404(self.queryset, module__file_path=f'{module_name}.py', name=script_name) return get_object_or_404(self.queryset, module__file_path=f'{module_name}.py', name=script_name)
def retrieve(self, request, pk): def retrieve(self, request, pk):

View File

@ -238,10 +238,18 @@ class TagImportForm(CSVModelForm):
label=_('Weight'), label=_('Weight'),
required=False required=False
) )
object_types = CSVMultipleContentTypeField(
label=_('Object types'),
queryset=ObjectType.objects.with_feature('tags'),
help_text=_("One or more assigned object types"),
required=False,
)
class Meta: class Meta:
model = Tag model = Tag
fields = ('name', 'slug', 'color', 'weight', 'description') fields = (
'name', 'slug', 'color', 'weight', 'description', 'object_types',
)
class JournalEntryImportForm(NetBoxModelImportForm): class JournalEntryImportForm(NetBoxModelImportForm):

View File

@ -444,6 +444,8 @@ class TagTestCase(ViewTestCases.OrganizationalObjectViewTestCase):
@classmethod @classmethod
def setUpTestData(cls): def setUpTestData(cls):
site_ct = ContentType.objects.get_for_model(Site)
tags = ( tags = (
Tag(name='Tag 1', slug='tag-1'), Tag(name='Tag 1', slug='tag-1'),
Tag(name='Tag 2', slug='tag-2', weight=1), Tag(name='Tag 2', slug='tag-2', weight=1),
@ -456,14 +458,15 @@ class TagTestCase(ViewTestCases.OrganizationalObjectViewTestCase):
'slug': 'tag-x', 'slug': 'tag-x',
'color': 'c0c0c0', 'color': 'c0c0c0',
'comments': 'Some comments', 'comments': 'Some comments',
'object_types': [site_ct.pk],
'weight': 11, 'weight': 11,
} }
cls.csv_data = ( cls.csv_data = (
"name,slug,color,description,weight", "name,slug,color,description,object_types,weight",
"Tag 4,tag-4,ff0000,Fourth tag,0", "Tag 4,tag-4,ff0000,Fourth tag,dcim.interface,0",
"Tag 5,tag-5,00ff00,Fifth tag,1111", "Tag 5,tag-5,00ff00,Fifth tag,'dcim.device,dcim.site',1111",
"Tag 6,tag-6,0000ff,Sixth tag,0", "Tag 6,tag-6,0000ff,Sixth tag,dcim.site,0",
) )
cls.csv_update_data = ( cls.csv_update_data = (

View File

@ -8,7 +8,7 @@ msgid ""
msgstr "" msgstr ""
"Project-Id-Version: PACKAGE VERSION\n" "Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n" "Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2025-06-10 05:02+0000\n" "POT-Creation-Date: 2025-06-11 05:02+0000\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n" "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n" "Language-Team: LANGUAGE <LL@li.org>\n"
@ -5278,7 +5278,7 @@ msgid "Connection"
msgstr "" msgstr ""
#: netbox/dcim/forms/filtersets.py:1426 netbox/extras/forms/bulk_edit.py:382 #: netbox/dcim/forms/filtersets.py:1426 netbox/extras/forms/bulk_edit.py:382
#: netbox/extras/forms/bulk_import.py:253 netbox/extras/forms/filtersets.py:527 #: netbox/extras/forms/bulk_import.py:261 netbox/extras/forms/filtersets.py:527
#: netbox/extras/forms/model_forms.py:759 netbox/extras/tables/tables.py:640 #: netbox/extras/forms/model_forms.py:759 netbox/extras/tables/tables.py:640
#: netbox/templates/extras/journalentry.html:30 #: netbox/templates/extras/journalentry.html:30
msgid "Kind" msgid "Kind"
@ -8192,7 +8192,8 @@ msgstr ""
#: netbox/extras/forms/bulk_import.py:37 netbox/extras/forms/bulk_import.py:118 #: netbox/extras/forms/bulk_import.py:37 netbox/extras/forms/bulk_import.py:118
#: netbox/extras/forms/bulk_import.py:139 #: netbox/extras/forms/bulk_import.py:139
#: netbox/extras/forms/bulk_import.py:164 #: netbox/extras/forms/bulk_import.py:164
#: netbox/extras/forms/bulk_import.py:188 netbox/extras/forms/filtersets.py:141 #: netbox/extras/forms/bulk_import.py:188
#: netbox/extras/forms/bulk_import.py:242 netbox/extras/forms/filtersets.py:141
#: netbox/extras/forms/filtersets.py:235 netbox/extras/forms/filtersets.py:265 #: netbox/extras/forms/filtersets.py:235 netbox/extras/forms/filtersets.py:265
#: netbox/extras/forms/model_forms.py:50 netbox/extras/forms/model_forms.py:222 #: netbox/extras/forms/model_forms.py:50 netbox/extras/forms/model_forms.py:222
#: netbox/extras/forms/model_forms.py:254 #: netbox/extras/forms/model_forms.py:254
@ -8206,6 +8207,7 @@ msgstr ""
#: netbox/extras/forms/bulk_import.py:141 #: netbox/extras/forms/bulk_import.py:141
#: netbox/extras/forms/bulk_import.py:166 #: netbox/extras/forms/bulk_import.py:166
#: netbox/extras/forms/bulk_import.py:190 #: netbox/extras/forms/bulk_import.py:190
#: netbox/extras/forms/bulk_import.py:244
#: netbox/tenancy/forms/bulk_import.py:95 #: netbox/tenancy/forms/bulk_import.py:95
msgid "One or more assigned object types" msgid "One or more assigned object types"
msgstr "" msgstr ""
@ -8282,15 +8284,15 @@ msgstr ""
msgid "Script {name} not found" msgid "Script {name} not found"
msgstr "" msgstr ""
#: netbox/extras/forms/bulk_import.py:250 #: netbox/extras/forms/bulk_import.py:258
msgid "Assigned object type" msgid "Assigned object type"
msgstr "" msgstr ""
#: netbox/extras/forms/bulk_import.py:255 #: netbox/extras/forms/bulk_import.py:263
msgid "The classification of entry" msgid "The classification of entry"
msgstr "" msgstr ""
#: netbox/extras/forms/bulk_import.py:267 #: netbox/extras/forms/bulk_import.py:275
#: netbox/extras/forms/model_forms.py:398 netbox/netbox/navigation/menu.py:413 #: netbox/extras/forms/model_forms.py:398 netbox/netbox/navigation/menu.py:413
#: netbox/templates/extras/notificationgroup.html:41 #: netbox/templates/extras/notificationgroup.html:41
#: netbox/templates/users/group.html:29 netbox/users/forms/model_forms.py:236 #: netbox/templates/users/group.html:29 netbox/users/forms/model_forms.py:236
@ -8299,11 +8301,11 @@ msgstr ""
msgid "Users" msgid "Users"
msgstr "" msgstr ""
#: netbox/extras/forms/bulk_import.py:271 #: netbox/extras/forms/bulk_import.py:279
msgid "User names separated by commas, encased with double quotes" msgid "User names separated by commas, encased with double quotes"
msgstr "" msgstr ""
#: netbox/extras/forms/bulk_import.py:274 #: netbox/extras/forms/bulk_import.py:282
#: netbox/extras/forms/model_forms.py:393 netbox/netbox/navigation/menu.py:295 #: netbox/extras/forms/model_forms.py:393 netbox/netbox/navigation/menu.py:295
#: netbox/netbox/navigation/menu.py:433 #: netbox/netbox/navigation/menu.py:433
#: netbox/templates/extras/notificationgroup.html:31 #: netbox/templates/extras/notificationgroup.html:31
@ -8316,7 +8318,7 @@ msgstr ""
msgid "Groups" msgid "Groups"
msgstr "" msgstr ""
#: netbox/extras/forms/bulk_import.py:278 #: netbox/extras/forms/bulk_import.py:286
msgid "Group names separated by commas, encased with double quotes" msgid "Group names separated by commas, encased with double quotes"
msgstr "" msgstr ""

View File

@ -3,7 +3,7 @@
[project] [project]
name = "netbox" name = "netbox"
version = "4.3.1" version = "4.3.2"
requires-python = ">=3.10" requires-python = ">=3.10"
authors = [ authors = [
{ name = "NetBox Community" } { name = "NetBox Community" }