Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fixes #10950 - Add filtering and validation to primary_ip4/primary_ip6 VirtualDeviceContext model #10954

Closed
wants to merge 2 commits into from

Conversation

DanSheps
Copy link
Member

Fixes: #10950

  • Adds filtering to VirtualDeviceContext model_form
  • Adds validation to VirtualDeviceContext model
  • Adds validation to IPAddress model

@DanSheps DanSheps self-assigned this Nov 17, 2022
@DanSheps DanSheps changed the base branch from develop to feature November 17, 2022 14:53
@DanSheps DanSheps added the beta Concerns a bug/feature in a beta release label Nov 17, 2022
@@ -1705,6 +1705,22 @@ class VirtualDeviceContextForm(TenancyForm, NetBoxModelForm):
'rack_id': '$rack',
}
)
primary_ip4 = DynamicModelChoiceField(
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Need to set labels on the form fields to ensure their proper display.


def clean(self):
super().clean()
vc_interfaces = self.device.vc_interfaces(if_master=False)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shouldn't we limit this to interfaces assigned to the VDC?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, I have went ahead and made this change.

@@ -866,7 +866,7 @@ def clean(self):

# Check for primary IP assignment that doesn't match the assigned device/VM
if self.pk:
for cls, attr in ((Device, 'device'), (VirtualMachine, 'virtual_machine')):
for cls, attr in ((Device, 'device'), (VirtualMachine, 'virtual_machine'), (VirtualDeviceContext, 'device')):
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
for cls, attr in ((Device, 'device'), (VirtualMachine, 'virtual_machine'), (VirtualDeviceContext, 'device')):
for cls, attr in ((Device, 'device'), (VirtualMachine, 'virtual_machine'), (VirtualDeviceContext, 'vdc')):

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The reverse attribute is vdcs and is a manytomany manager field. I had to do some thing different but perhaps you can take a look and maybe make a suggestion to clean this up better.

@@ -866,9 +866,16 @@ def clean(self):

# Check for primary IP assignment that doesn't match the assigned device/VM
if self.pk:
for cls, attr in ((Device, 'device'), (VirtualMachine, 'virtual_machine')):
for cls, attr in ((Device, 'device'), (VirtualMachine, 'virtual_machine'), (VirtualDeviceContext, 'vdcs')):
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This might be a bit cleaner - I think line 872 comparison of .all() != parent might be wrong, should be first()? I'm assuming the m2m check only needs to be done if 'vdcs', device and virtual_machine attrs aren't m2m.

        if self.pk:
            for cls, attr in ((Device, 'device'), (VirtualMachine, 'virtual_machine'), (VirtualDeviceContext, 'vdcs')):
                parent = cls.objects.filter(Q(primary_ip4=self) | Q(primary_ip6=self)).first()
                if parent and hasattr(self.assigned_object, attr):
                    if attr == 'vdcs'and getattr(self.assigned_object, attr).first() != parent:
                        raise ValidationError({
                            'interface': f"IP address is primary for {cls._meta.model_name} {parent} but "
                                         f"not assigned to it!"
                        })
                    elif getattr(self.assigned_object, attr, None) != parent:
                        # Check for a NAT relationship
                        if not self.nat_inside or getattr(self.nat_inside.assigned_object, attr, None) != parent:
                            raise ValidationError({
                                'interface': f"IP address is primary for {cls._meta.model_name} {parent} but "
                                             f"not assigned to it!"
                            })

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

also, move the parent = cls.objects outside the loop:

        if self.pk:
            parent = cls.objects.filter(Q(primary_ip4=self) | Q(primary_ip6=self)).first()
            for cls, attr in ((Device, 'device'), (VirtualMachine, 'virtual_machine'), (VirtualDeviceContext, 'vdcs')):

@jeremystretch
Copy link
Member

Shouldn't we limit this to interfaces assigned to the VDC?

Considering this further, we probably don't want to force this limitation. I can see a case where the primary IP address via which a VDC is managed does not belong to the VDC itself (e.g. an out-of-band or otherwise "special" IP). It does need to be validated against the parent device though.

Additionally, we've moved away from statically rendering choice fields; selection options should always be populated via the REST API. And the primary IP validation under the IPAddress model has since been removed as part of unrelated work.

I've committed b2f34ce which I believe fully resolves #10950 and supersedes this PR. Open to further discussion re: validation, but that should occur outside the context of this particular bug.

@jeremystretch jeremystretch deleted the 100950-vdc-fix-primary_ip4_primary_ip6 branch December 9, 2022 14:57
@github-actions github-actions bot locked as resolved and limited conversation to collaborators Jan 9, 2023
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
beta Concerns a bug/feature in a beta release
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Primary IPv6 for VDC filters IPv4
3 participants