mirror of
https://github.com/netbox-community/netbox.git
synced 2024-05-10 07:54:54 +00:00
* Fixes #14847: Relax requirement for IKE policy * Docs tweak --------- Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
258 lines
6.6 KiB
Python
258 lines
6.6 KiB
Python
from django.core.exceptions import ValidationError
|
|
from django.db import models
|
|
from django.urls import reverse
|
|
from django.utils.translation import gettext_lazy as _
|
|
|
|
from netbox.models import PrimaryModel
|
|
from vpn.choices import *
|
|
|
|
__all__ = (
|
|
'IKEPolicy',
|
|
'IKEProposal',
|
|
'IPSecPolicy',
|
|
'IPSecProfile',
|
|
'IPSecProposal',
|
|
)
|
|
|
|
|
|
#
|
|
# IKE
|
|
#
|
|
|
|
class IKEProposal(PrimaryModel):
|
|
name = models.CharField(
|
|
verbose_name=_('name'),
|
|
max_length=100,
|
|
unique=True
|
|
)
|
|
authentication_method = models.CharField(
|
|
verbose_name=('authentication method'),
|
|
choices=AuthenticationMethodChoices
|
|
)
|
|
encryption_algorithm = models.CharField(
|
|
verbose_name=_('encryption algorithm'),
|
|
choices=EncryptionAlgorithmChoices
|
|
)
|
|
authentication_algorithm = models.CharField(
|
|
verbose_name=_('authentication algorithm'),
|
|
choices=AuthenticationAlgorithmChoices,
|
|
blank=True
|
|
)
|
|
group = models.PositiveSmallIntegerField(
|
|
verbose_name=_('group'),
|
|
choices=DHGroupChoices,
|
|
help_text=_('Diffie-Hellman group ID')
|
|
)
|
|
sa_lifetime = models.PositiveIntegerField(
|
|
verbose_name=_('SA lifetime'),
|
|
blank=True,
|
|
null=True,
|
|
help_text=_('Security association lifetime (in seconds)')
|
|
)
|
|
|
|
clone_fields = (
|
|
'authentication_method', 'encryption_algorithm', 'authentication_algorithm', 'group', 'sa_lifetime',
|
|
)
|
|
|
|
class Meta:
|
|
ordering = ('name',)
|
|
verbose_name = _('IKE proposal')
|
|
verbose_name_plural = _('IKE proposals')
|
|
|
|
def __str__(self):
|
|
return self.name
|
|
|
|
def get_absolute_url(self):
|
|
return reverse('vpn:ikeproposal', args=[self.pk])
|
|
|
|
|
|
class IKEPolicy(PrimaryModel):
|
|
name = models.CharField(
|
|
verbose_name=_('name'),
|
|
max_length=100,
|
|
unique=True
|
|
)
|
|
version = models.PositiveSmallIntegerField(
|
|
verbose_name=_('version'),
|
|
choices=IKEVersionChoices,
|
|
default=IKEVersionChoices.VERSION_2
|
|
)
|
|
mode = models.CharField(
|
|
verbose_name=_('mode'),
|
|
choices=IKEModeChoices,
|
|
blank=True
|
|
)
|
|
proposals = models.ManyToManyField(
|
|
to='vpn.IKEProposal',
|
|
related_name='ike_policies',
|
|
verbose_name=_('proposals')
|
|
)
|
|
preshared_key = models.TextField(
|
|
verbose_name=_('pre-shared key'),
|
|
blank=True
|
|
)
|
|
|
|
clone_fields = (
|
|
'version', 'mode', 'proposals',
|
|
)
|
|
prerequisite_models = (
|
|
'vpn.IKEProposal',
|
|
)
|
|
|
|
class Meta:
|
|
ordering = ('name',)
|
|
verbose_name = _('IKE policy')
|
|
verbose_name_plural = _('IKE policies')
|
|
|
|
def __str__(self):
|
|
return self.name
|
|
|
|
def get_absolute_url(self):
|
|
return reverse('vpn:ikepolicy', args=[self.pk])
|
|
|
|
def clean(self):
|
|
super().clean()
|
|
|
|
# Mode is required
|
|
if self.version == IKEVersionChoices.VERSION_1 and not self.mode:
|
|
raise ValidationError(_("Mode is required for selected IKE version"))
|
|
|
|
# Mode cannot be used
|
|
if self.version == IKEVersionChoices.VERSION_2 and self.mode:
|
|
raise ValidationError(_("Mode cannot be used for selected IKE version"))
|
|
|
|
|
|
#
|
|
# IPSec
|
|
#
|
|
|
|
class IPSecProposal(PrimaryModel):
|
|
name = models.CharField(
|
|
verbose_name=_('name'),
|
|
max_length=100,
|
|
unique=True
|
|
)
|
|
encryption_algorithm = models.CharField(
|
|
verbose_name=_('encryption'),
|
|
choices=EncryptionAlgorithmChoices,
|
|
blank=True
|
|
)
|
|
authentication_algorithm = models.CharField(
|
|
verbose_name=_('authentication'),
|
|
choices=AuthenticationAlgorithmChoices,
|
|
blank=True
|
|
)
|
|
sa_lifetime_seconds = models.PositiveIntegerField(
|
|
verbose_name=_('SA lifetime (seconds)'),
|
|
blank=True,
|
|
null=True,
|
|
help_text=_('Security association lifetime (seconds)')
|
|
)
|
|
sa_lifetime_data = models.PositiveIntegerField(
|
|
verbose_name=_('SA lifetime (KB)'),
|
|
blank=True,
|
|
null=True,
|
|
help_text=_('Security association lifetime (in kilobytes)')
|
|
)
|
|
|
|
clone_fields = (
|
|
'encryption_algorithm', 'authentication_algorithm', 'sa_lifetime_seconds', 'sa_lifetime_data',
|
|
)
|
|
|
|
class Meta:
|
|
ordering = ('name',)
|
|
verbose_name = _('IPSec proposal')
|
|
verbose_name_plural = _('IPSec proposals')
|
|
|
|
def __str__(self):
|
|
return self.name
|
|
|
|
def get_absolute_url(self):
|
|
return reverse('vpn:ipsecproposal', args=[self.pk])
|
|
|
|
def clean(self):
|
|
super().clean()
|
|
|
|
# Encryption and/or authentication algorithm must be defined
|
|
if not self.encryption_algorithm and not self.authentication_algorithm:
|
|
raise ValidationError(_("Encryption and/or authentication algorithm must be defined"))
|
|
|
|
|
|
class IPSecPolicy(PrimaryModel):
|
|
name = models.CharField(
|
|
verbose_name=_('name'),
|
|
max_length=100,
|
|
unique=True
|
|
)
|
|
proposals = models.ManyToManyField(
|
|
to='vpn.IPSecProposal',
|
|
related_name='ipsec_policies',
|
|
verbose_name=_('proposals')
|
|
)
|
|
pfs_group = models.PositiveSmallIntegerField(
|
|
verbose_name=_('PFS group'),
|
|
choices=DHGroupChoices,
|
|
blank=True,
|
|
null=True,
|
|
help_text=_('Diffie-Hellman group for Perfect Forward Secrecy')
|
|
)
|
|
|
|
clone_fields = (
|
|
'proposals', 'pfs_group',
|
|
)
|
|
prerequisite_models = (
|
|
'vpn.IPSecProposal',
|
|
)
|
|
|
|
class Meta:
|
|
ordering = ('name',)
|
|
verbose_name = _('IPSec policy')
|
|
verbose_name_plural = _('IPSec policies')
|
|
|
|
def __str__(self):
|
|
return self.name
|
|
|
|
def get_absolute_url(self):
|
|
return reverse('vpn:ipsecpolicy', args=[self.pk])
|
|
|
|
|
|
class IPSecProfile(PrimaryModel):
|
|
name = models.CharField(
|
|
verbose_name=_('name'),
|
|
max_length=100,
|
|
unique=True
|
|
)
|
|
mode = models.CharField(
|
|
verbose_name=_('mode'),
|
|
choices=IPSecModeChoices
|
|
)
|
|
ike_policy = models.ForeignKey(
|
|
to='vpn.IKEPolicy',
|
|
on_delete=models.PROTECT,
|
|
related_name='ipsec_profiles'
|
|
)
|
|
ipsec_policy = models.ForeignKey(
|
|
to='vpn.IPSecPolicy',
|
|
on_delete=models.PROTECT,
|
|
related_name='ipsec_profiles'
|
|
)
|
|
|
|
clone_fields = (
|
|
'mode', 'ike_policy', 'ipsec_policy',
|
|
)
|
|
prerequisite_models = (
|
|
'vpn.IKEPolicy',
|
|
'vpn.IPSecPolicy',
|
|
)
|
|
|
|
class Meta:
|
|
ordering = ('name',)
|
|
verbose_name = _('IPSec profile')
|
|
verbose_name_plural = _('IPSec profiles')
|
|
|
|
def __str__(self):
|
|
return self.name
|
|
|
|
def get_absolute_url(self):
|
|
return reverse('vpn:ipsecprofile', args=[self.pk])
|