Skip to content

Commit

Permalink
Fixes #2994: Prevent modifying termination points of existing cable t…
Browse files Browse the repository at this point in the history
…o ensure end-to-end path integrity
  • Loading branch information
jeremystretch committed Apr 21, 2020
1 parent 5eef6bc commit b362c6a
Show file tree
Hide file tree
Showing 2 changed files with 33 additions and 0 deletions.
1 change: 1 addition & 0 deletions docs/release-notes/version-2.8.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@

### Bug Fixes

* [#2994](https://github.com/netbox-community/netbox/issues/2994) - Prevent modifying termination points of existing cable to ensure end-to-end path integrity
* [#4361](https://github.com/netbox-community/netbox/issues/4361) - Fix Type of `connection_state` in Swagger schema
* [#4388](https://github.com/netbox-community/netbox/issues/4388) - Fix detection of connected endpoints when connecting rear ports
* [#4489](https://github.com/netbox-community/netbox/issues/4489) - Fix display of parent/child role on device type view
Expand Down
32 changes: 32 additions & 0 deletions netbox/dcim/models/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -2070,6 +2070,20 @@ def __init__(self, *args, **kwargs):
# A copy of the PK to be used by __str__ in case the object is deleted
self._pk = self.pk

@classmethod
def from_db(cls, db, field_names, values):
"""
Cache the original A and B terminations of existing Cable instances for later reference inside clean().
"""
instance = super().from_db(db, field_names, values)

instance._orig_termination_a_type = instance.termination_a_type
instance._orig_termination_a_id = instance.termination_a_id
instance._orig_termination_b_type = instance.termination_b_type
instance._orig_termination_b_id = instance.termination_b_id

return instance

def __str__(self):
return self.label or '#{}'.format(self._pk)

Expand Down Expand Up @@ -2098,6 +2112,24 @@ def clean(self):
'termination_b': 'Invalid ID for type {}'.format(self.termination_b_type)
})

# If editing an existing Cable instance, check that neither termination has been modified.
if self.pk:
err_msg = 'Cable termination points may not be modified. Delete and recreate the cable instead.'
if (
self.termination_a_type != self._orig_termination_a_type or
self.termination_a_id != self._orig_termination_a_id
):
raise ValidationError({
'termination_a': err_msg
})
if (
self.termination_b_type != self._orig_termination_b_type or
self.termination_b_id != self._orig_termination_b_id
):
raise ValidationError({
'termination_b': err_msg
})

type_a = self.termination_a_type.model
type_b = self.termination_b_type.model

Expand Down

0 comments on commit b362c6a

Please sign in to comment.