Skip to content

Commit 85ca55e

Browse files
committed
#20875 fix updating of denormalized fields (_site, _location, _rack) for all component models
1 parent 970f2bd commit 85ca55e

File tree

4 files changed

+48
-22
lines changed

4 files changed

+48
-22
lines changed

netbox/dcim/models/devices.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,7 @@
3333
from .device_components import *
3434
from .mixins import RenderConfigMixin
3535
from .modules import Module
36+
from ..utils import update_device_components
3637

3738

3839
__all__ = (
@@ -1012,6 +1013,8 @@ def save(self, *args, **kwargs):
10121013
self._instantiate_components(self.device_type.inventoryitemtemplates.all(), bulk_create=False)
10131014
# Interface bridges have to be set after interface instantiation
10141015
update_interface_bridges(self, self.device_type.interfacetemplates.all())
1016+
# Update denormalized fields for all components
1017+
update_device_components(self)
10151018

10161019
# Update Site and Rack assignment for any child Devices
10171020
devices = Device.objects.filter(parent_bay__device=self)

netbox/dcim/models/modules.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515
from utilities.jsonschema import validate_schema
1616
from utilities.string import title
1717
from .device_components import *
18+
from ..utils import update_device_components
1819

1920
__all__ = (
2021
'Module',
@@ -347,3 +348,5 @@ def save(self, *args, **kwargs):
347348

348349
# Interface bridges have to be set after interface instantiation
349350
update_interface_bridges(self.device, self.module_type.interfacetemplates, self)
351+
# Update denormalized fields for all components
352+
update_device_components(self.device)

netbox/dcim/signals.py

Lines changed: 9 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -6,25 +6,11 @@
66
from dcim.choices import CableEndChoices, LinkStatusChoices
77
from virtualization.models import VMInterface
88
from .models import (
9-
Cable, CablePath, CableTermination, ConsolePort, ConsoleServerPort, Device, DeviceBay, FrontPort, Interface,
10-
InventoryItem, ModuleBay, PathEndpoint, PowerOutlet, PowerPanel, PowerPort, Rack, RearPort, Location,
9+
Cable, CablePath, CableTermination, Device, FrontPort, Interface, PathEndpoint, PowerPanel, Rack, Location,
1110
VirtualChassis,
1211
)
1312
from .models.cables import trace_paths
14-
from .utils import create_cablepath, rebuild_paths
15-
16-
COMPONENT_MODELS = (
17-
ConsolePort,
18-
ConsoleServerPort,
19-
DeviceBay,
20-
FrontPort,
21-
Interface,
22-
InventoryItem,
23-
ModuleBay,
24-
PowerOutlet,
25-
PowerPort,
26-
RearPort,
27-
)
13+
from .utils import create_cablepath, rebuild_paths, update_device_components
2814

2915

3016
#
@@ -44,6 +30,9 @@ def handle_location_site_change(instance, created, **kwargs):
4430
Device.objects.filter(location__in=locations).update(site=instance.site)
4531
PowerPanel.objects.filter(location__in=locations).update(site=instance.site)
4632
CableTermination.objects.filter(_location__in=locations).update(_site=instance.site)
33+
# Update component models for devices in these locations
34+
for device in Device.objects.filter(location__in=locations):
35+
update_device_components(device)
4736

4837

4938
@receiver(post_save, sender=Rack)
@@ -53,6 +42,9 @@ def handle_rack_site_change(instance, created, **kwargs):
5342
"""
5443
if not created:
5544
Device.objects.filter(rack=instance).update(site=instance.site, location=instance.location)
45+
# Update component models for devices in this rack
46+
for device in Device.objects.filter(rack=instance):
47+
update_device_components(device)
5648

5749

5850
@receiver(post_save, sender=Device)
@@ -61,12 +53,7 @@ def handle_device_site_change(instance, created, **kwargs):
6153
Update child components to update the parent Site, Location, and Rack when a Device is saved.
6254
"""
6355
if not created:
64-
for model in COMPONENT_MODELS:
65-
model.objects.filter(device=instance).update(
66-
_site=instance.site,
67-
_location=instance.location,
68-
_rack=instance.rack,
69-
)
56+
update_device_components(instance)
7057

7158

7259
#

netbox/dcim/utils.py

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -76,3 +76,36 @@ def update_interface_bridges(device, interface_templates, module=None):
7676
)
7777
interface.full_clean()
7878
interface.save()
79+
80+
81+
def update_device_components(device):
82+
"""
83+
Update denormalized fields (_site, _location, _rack) for all component models
84+
associated with the specified device.
85+
86+
:param device: Device instance whose components should be updated
87+
"""
88+
from dcim.models import (
89+
ConsolePort, ConsoleServerPort, DeviceBay, FrontPort, Interface,
90+
InventoryItem, ModuleBay, PowerOutlet, PowerPort, RearPort,
91+
)
92+
93+
COMPONENT_MODELS = (
94+
ConsolePort,
95+
ConsoleServerPort,
96+
DeviceBay,
97+
FrontPort,
98+
Interface,
99+
InventoryItem,
100+
ModuleBay,
101+
PowerOutlet,
102+
PowerPort,
103+
RearPort,
104+
)
105+
106+
for model in COMPONENT_MODELS:
107+
model.objects.filter(device=device).update(
108+
_site=device.site,
109+
_location=device.location,
110+
_rack=device.rack,
111+
)

0 commit comments

Comments
 (0)