Jeremy Stretch 6 лет назад
Родитель
Сommit
4ecbfc4e5e

+ 2 - 3
netbox/ipam/api/serializers.py

@@ -9,8 +9,7 @@ from dcim.api.nested_serializers import NestedDeviceSerializer, NestedSiteSerial
 from dcim.models import Interface
 from dcim.models import Interface
 from extras.api.customfields import CustomFieldModelSerializer
 from extras.api.customfields import CustomFieldModelSerializer
 from ipam.choices import *
 from ipam.choices import *
-from ipam.constants import *
-from ipam.models import Aggregate, IPAddress, Prefix, RIR, Role, Service, VLAN, VLANGroup, VRF
+from ipam.models import AF_CHOICES, Aggregate, IPAddress, Prefix, RIR, Role, Service, VLAN, VLANGroup, VRF
 from tenancy.api.nested_serializers import NestedTenantSerializer
 from tenancy.api.nested_serializers import NestedTenantSerializer
 from utilities.api import (
 from utilities.api import (
     ChoiceField, SerializedPKRelatedField, ValidatedModelSerializer, WritableNestedSerializer,
     ChoiceField, SerializedPKRelatedField, ValidatedModelSerializer, WritableNestedSerializer,
@@ -240,7 +239,7 @@ class AvailableIPSerializer(serializers.Serializer):
 class ServiceSerializer(CustomFieldModelSerializer):
 class ServiceSerializer(CustomFieldModelSerializer):
     device = NestedDeviceSerializer(required=False, allow_null=True)
     device = NestedDeviceSerializer(required=False, allow_null=True)
     virtual_machine = NestedVirtualMachineSerializer(required=False, allow_null=True)
     virtual_machine = NestedVirtualMachineSerializer(required=False, allow_null=True)
-    protocol = ChoiceField(choices=IP_PROTOCOL_CHOICES)
+    protocol = ChoiceField(choices=ServiceProtocolChoices)
     ipaddresses = SerializedPKRelatedField(
     ipaddresses = SerializedPKRelatedField(
         queryset=IPAddress.objects.all(),
         queryset=IPAddress.objects.all(),
         serializer=NestedIPAddressSerializer,
         serializer=NestedIPAddressSerializer,

+ 20 - 0
netbox/ipam/choices.py

@@ -108,3 +108,23 @@ class VLANStatusChoices(ChoiceSet):
         STATUS_RESERVED: 2,
         STATUS_RESERVED: 2,
         STATUS_DEPRECATED: 3,
         STATUS_DEPRECATED: 3,
     }
     }
+
+
+#
+# VLANs
+#
+
+class ServiceProtocolChoices(ChoiceSet):
+
+    PROTOCOL_TCP = 'tcp'
+    PROTOCOL_UDP = 'udp'
+
+    CHOICES = (
+        (PROTOCOL_TCP, 'TCP'),
+        (PROTOCOL_UDP, 'UDP'),
+    )
+
+    LEGACY_MAP = {
+        PROTOCOL_TCP: 6,
+        PROTOCOL_UDP: 17,
+    }

+ 0 - 14
netbox/ipam/constants.py

@@ -1,14 +0,0 @@
-# IP address families
-AF_CHOICES = (
-    (4, 'IPv4'),
-    (6, 'IPv6'),
-)
-
-
-# IP protocols (for services)
-IP_PROTOCOL_TCP = 6
-IP_PROTOCOL_UDP = 17
-IP_PROTOCOL_CHOICES = (
-    (IP_PROTOCOL_TCP, 'TCP'),
-    (IP_PROTOCOL_UDP, 'UDP'),
-)

+ 0 - 1
netbox/ipam/filters.py

@@ -10,7 +10,6 @@ from tenancy.filtersets import TenancyFilterSet
 from utilities.filters import NameSlugSearchFilterSet, NumericInFilter, TagFilter
 from utilities.filters import NameSlugSearchFilterSet, NumericInFilter, TagFilter
 from virtualization.models import VirtualMachine
 from virtualization.models import VirtualMachine
 from .choices import *
 from .choices import *
-from .constants import *
 from .models import Aggregate, IPAddress, Prefix, RIR, Role, Service, VLAN, VLANGroup, VRF
 from .models import Aggregate, IPAddress, Prefix, RIR, Role, Service, VLAN, VLANGroup, VRF
 
 
 
 

+ 2 - 3
netbox/ipam/forms.py

@@ -14,7 +14,6 @@ from utilities.forms import (
 )
 )
 from virtualization.models import VirtualMachine
 from virtualization.models import VirtualMachine
 from .choices import *
 from .choices import *
-from .constants import *
 from .models import Aggregate, IPAddress, Prefix, RIR, Role, Service, VLAN, VLANGroup, VRF
 from .models import Aggregate, IPAddress, Prefix, RIR, Role, Service, VLAN, VLANGroup, VRF
 
 
 IP_FAMILY_CHOICES = [
 IP_FAMILY_CHOICES = [
@@ -1293,7 +1292,7 @@ class ServiceFilterForm(BootstrapMixin, CustomFieldFilterForm):
         label='Search'
         label='Search'
     )
     )
     protocol = forms.ChoiceField(
     protocol = forms.ChoiceField(
-        choices=add_blank_choice(IP_PROTOCOL_CHOICES),
+        choices=add_blank_choice(ServiceProtocolChoices),
         required=False,
         required=False,
         widget=StaticSelect2Multiple()
         widget=StaticSelect2Multiple()
     )
     )
@@ -1308,7 +1307,7 @@ class ServiceBulkEditForm(BootstrapMixin, CustomFieldBulkEditForm):
         widget=forms.MultipleHiddenInput()
         widget=forms.MultipleHiddenInput()
     )
     )
     protocol = forms.ChoiceField(
     protocol = forms.ChoiceField(
-        choices=add_blank_choice(IP_PROTOCOL_CHOICES),
+        choices=add_blank_choice(ServiceProtocolChoices),
         required=False,
         required=False,
         widget=StaticSelect2()
         widget=StaticSelect2()
     )
     )

+ 35 - 0
netbox/ipam/migrations/0031_3569_service_fields.py

@@ -0,0 +1,35 @@
+from django.db import migrations, models
+
+
+SERVICE_PROTOCOL_CHOICES = (
+    (6, 'tcp'),
+    (17, 'udp'),
+)
+
+
+def service_protocol_to_slug(apps, schema_editor):
+    Service = apps.get_model('ipam', 'Service')
+    for id, slug in SERVICE_PROTOCOL_CHOICES:
+        Service.objects.filter(protocol=str(id)).update(protocol=slug)
+
+
+class Migration(migrations.Migration):
+    atomic = False
+
+    dependencies = [
+        ('ipam', '0030_3569_vlan_fields'),
+    ]
+
+    operations = [
+
+        # Service.protocol
+        migrations.AlterField(
+            model_name='service',
+            name='protocol',
+            field=models.CharField(max_length=50),
+        ),
+        migrations.RunPython(
+            code=service_protocol_to_slug
+        ),
+
+    ]

+ 9 - 3
netbox/ipam/models.py

@@ -15,12 +15,17 @@ from utilities.models import ChangeLoggedModel
 from utilities.utils import serialize_object
 from utilities.utils import serialize_object
 from virtualization.models import VirtualMachine
 from virtualization.models import VirtualMachine
 from .choices import *
 from .choices import *
-from .constants import *
 from .fields import IPNetworkField, IPAddressField
 from .fields import IPNetworkField, IPAddressField
 from .querysets import PrefixQuerySet
 from .querysets import PrefixQuerySet
 from .validators import DNSValidator
 from .validators import DNSValidator
 
 
 
 
+# IP address families
+AF_CHOICES = (
+    (4, 'IPv4'),
+    (6, 'IPv6'),
+)
+
 IPADDRESS_ROLES_NONUNIQUE = (
 IPADDRESS_ROLES_NONUNIQUE = (
     # IPAddress roles which are exempt from unique address enforcement
     # IPAddress roles which are exempt from unique address enforcement
     IPAddressRoleChoices.ROLE_ANYCAST,
     IPAddressRoleChoices.ROLE_ANYCAST,
@@ -975,8 +980,9 @@ class Service(ChangeLoggedModel, CustomFieldModel):
     name = models.CharField(
     name = models.CharField(
         max_length=30
         max_length=30
     )
     )
-    protocol = models.PositiveSmallIntegerField(
-        choices=IP_PROTOCOL_CHOICES
+    protocol = models.CharField(
+        max_length=50,
+        choices=ServiceProtocolChoices
     )
     )
     port = models.PositiveIntegerField(
     port = models.PositiveIntegerField(
         validators=[MinValueValidator(1), MaxValueValidator(65535)],
         validators=[MinValueValidator(1), MaxValueValidator(65535)],

+ 9 - 9
netbox/ipam/tests/test_api.py

@@ -5,7 +5,7 @@ from netaddr import IPNetwork
 from rest_framework import status
 from rest_framework import status
 
 
 from dcim.models import Device, DeviceRole, DeviceType, Manufacturer, Site
 from dcim.models import Device, DeviceRole, DeviceType, Manufacturer, Site
-from ipam.constants import IP_PROTOCOL_TCP, IP_PROTOCOL_UDP
+from ipam.choices import ServiceProtocolChoices
 from ipam.models import Aggregate, IPAddress, Prefix, RIR, Role, Service, VLAN, VLANGroup, VRF
 from ipam.models import Aggregate, IPAddress, Prefix, RIR, Role, Service, VLAN, VLANGroup, VRF
 from utilities.testing import APITestCase
 from utilities.testing import APITestCase
 
 
@@ -996,13 +996,13 @@ class ServiceTest(APITestCase):
             name='Test Device 2', site=site, device_type=devicetype, device_role=devicerole
             name='Test Device 2', site=site, device_type=devicetype, device_role=devicerole
         )
         )
         self.service1 = Service.objects.create(
         self.service1 = Service.objects.create(
-            device=self.device1, name='Test Service 1', protocol=IP_PROTOCOL_TCP, port=1
+            device=self.device1, name='Test Service 1', protocol=ServiceProtocolChoices.PROTOCOL_TCP, port=1
         )
         )
         self.service1 = Service.objects.create(
         self.service1 = Service.objects.create(
-            device=self.device1, name='Test Service 2', protocol=IP_PROTOCOL_TCP, port=2
+            device=self.device1, name='Test Service 2', protocol=ServiceProtocolChoices.PROTOCOL_TCP, port=2
         )
         )
         self.service1 = Service.objects.create(
         self.service1 = Service.objects.create(
-            device=self.device1, name='Test Service 3', protocol=IP_PROTOCOL_TCP, port=3
+            device=self.device1, name='Test Service 3', protocol=ServiceProtocolChoices.PROTOCOL_TCP, port=3
         )
         )
 
 
     def test_get_service(self):
     def test_get_service(self):
@@ -1024,7 +1024,7 @@ class ServiceTest(APITestCase):
         data = {
         data = {
             'device': self.device1.pk,
             'device': self.device1.pk,
             'name': 'Test Service 4',
             'name': 'Test Service 4',
-            'protocol': IP_PROTOCOL_TCP,
+            'protocol': ServiceProtocolChoices.PROTOCOL_TCP,
             'port': 4,
             'port': 4,
         }
         }
 
 
@@ -1045,19 +1045,19 @@ class ServiceTest(APITestCase):
             {
             {
                 'device': self.device1.pk,
                 'device': self.device1.pk,
                 'name': 'Test Service 4',
                 'name': 'Test Service 4',
-                'protocol': IP_PROTOCOL_TCP,
+                'protocol': ServiceProtocolChoices.PROTOCOL_TCP,
                 'port': 4,
                 'port': 4,
             },
             },
             {
             {
                 'device': self.device1.pk,
                 'device': self.device1.pk,
                 'name': 'Test Service 5',
                 'name': 'Test Service 5',
-                'protocol': IP_PROTOCOL_TCP,
+                'protocol': ServiceProtocolChoices.PROTOCOL_TCP,
                 'port': 5,
                 'port': 5,
             },
             },
             {
             {
                 'device': self.device1.pk,
                 'device': self.device1.pk,
                 'name': 'Test Service 6',
                 'name': 'Test Service 6',
-                'protocol': IP_PROTOCOL_TCP,
+                'protocol': ServiceProtocolChoices.PROTOCOL_TCP,
                 'port': 6,
                 'port': 6,
             },
             },
         ]
         ]
@@ -1076,7 +1076,7 @@ class ServiceTest(APITestCase):
         data = {
         data = {
             'device': self.device2.pk,
             'device': self.device2.pk,
             'name': 'Test Service X',
             'name': 'Test Service X',
-            'protocol': IP_PROTOCOL_UDP,
+            'protocol': ServiceProtocolChoices.PROTOCOL_UDP,
             'port': 99,
             'port': 99,
         }
         }
 
 

+ 4 - 4
netbox/ipam/tests/test_views.py

@@ -5,7 +5,7 @@ from django.test import Client, TestCase
 from django.urls import reverse
 from django.urls import reverse
 
 
 from dcim.models import Device, DeviceRole, DeviceType, Manufacturer, Site
 from dcim.models import Device, DeviceRole, DeviceType, Manufacturer, Site
-from ipam.constants import IP_PROTOCOL_TCP
+from ipam.choices import ServiceProtocolChoices
 from ipam.models import Aggregate, IPAddress, Prefix, RIR, Role, Service, VLAN, VLANGroup, VRF
 from ipam.models import Aggregate, IPAddress, Prefix, RIR, Role, Service, VLAN, VLANGroup, VRF
 from utilities.testing import create_test_user
 from utilities.testing import create_test_user
 
 
@@ -264,9 +264,9 @@ class ServiceTestCase(TestCase):
         device.save()
         device.save()
 
 
         Service.objects.bulk_create([
         Service.objects.bulk_create([
-            Service(device=device, name='Service 1', protocol=IP_PROTOCOL_TCP, port=101),
-            Service(device=device, name='Service 2', protocol=IP_PROTOCOL_TCP, port=102),
-            Service(device=device, name='Service 3', protocol=IP_PROTOCOL_TCP, port=103),
+            Service(device=device, name='Service 1', protocol=ServiceProtocolChoices.PROTOCOL_TCP, port=101),
+            Service(device=device, name='Service 2', protocol=ServiceProtocolChoices.PROTOCOL_TCP, port=102),
+            Service(device=device, name='Service 3', protocol=ServiceProtocolChoices.PROTOCOL_TCP, port=103),
         ])
         ])
 
 
     def test_service_list(self):
     def test_service_list(self):

+ 0 - 1
netbox/ipam/views.py

@@ -15,7 +15,6 @@ from utilities.views import (
 from virtualization.models import VirtualMachine
 from virtualization.models import VirtualMachine
 from . import filters, forms, tables
 from . import filters, forms, tables
 from .choices import *
 from .choices import *
-from .constants import *
 from .models import Aggregate, IPAddress, Prefix, RIR, Role, Service, VLAN, VLANGroup, VRF
 from .models import Aggregate, IPAddress, Prefix, RIR, Role, Service, VLAN, VLANGroup, VRF