diff --git a/netbox/circuits/forms.py b/netbox/circuits/forms.py index 5e5a88080..4731c9adb 100644 --- a/netbox/circuits/forms.py +++ b/netbox/circuits/forms.py @@ -303,14 +303,24 @@ class CircuitFilterForm(BootstrapMixin, TenancyFilterForm, CustomFieldFilterForm # class CircuitTerminationForm(BootstrapMixin, forms.ModelForm): + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + initial_params={ + 'sites': '$site' + } + ) site = DynamicModelChoiceField( - queryset=Site.objects.all() + queryset=Site.objects.all(), + query_params={ + 'region_id': '$region' + } ) class Meta: model = CircuitTermination fields = [ - 'term_side', 'site', 'port_speed', 'upstream_speed', 'xconnect_id', 'pp_info', 'description', + 'term_side', 'region', 'site', 'port_speed', 'upstream_speed', 'xconnect_id', 'pp_info', 'description', ] help_texts = { 'port_speed': "Physical circuit speed", diff --git a/netbox/dcim/forms.py b/netbox/dcim/forms.py index 3b1f24b3a..45be438f2 100644 --- a/netbox/dcim/forms.py +++ b/netbox/dcim/forms.py @@ -352,8 +352,18 @@ class SiteFilterForm(BootstrapMixin, TenancyFilterForm, CustomFieldFilterForm): # class RackGroupForm(BootstrapMixin, forms.ModelForm): + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + initial_params={ + 'sites': '$site' + } + ) site = DynamicModelChoiceField( - queryset=Site.objects.all() + queryset=Site.objects.all(), + query_params={ + 'region_id': '$region' + } ) parent = DynamicModelChoiceField( queryset=RackGroup.objects.all(), @@ -367,7 +377,7 @@ class RackGroupForm(BootstrapMixin, forms.ModelForm): class Meta: model = RackGroup fields = ( - 'site', 'parent', 'name', 'slug', 'description', + 'region', 'site', 'parent', 'name', 'slug', 'description', ) @@ -447,14 +457,17 @@ class RackRoleCSVForm(CSVModelForm): # class RackForm(BootstrapMixin, TenancyForm, CustomFieldModelForm): - site = DynamicModelChoiceField( - queryset=Site.objects.all() - ) - group = DynamicModelChoiceField( - queryset=RackGroup.objects.all(), + region = DynamicModelChoiceField( + queryset=Region.objects.all(), required=False, + initial_params={ + 'sites': '$site' + } + ) + site = DynamicModelChoiceField( + queryset=Site.objects.all(), query_params={ - 'site_id': '$site' + 'region_id': '$region' } ) role = DynamicModelChoiceField( @@ -470,8 +483,9 @@ class RackForm(BootstrapMixin, TenancyForm, CustomFieldModelForm): class Meta: model = Rack fields = [ - 'site', 'group', 'name', 'facility_id', 'tenant_group', 'tenant', 'status', 'role', 'serial', 'asset_tag', - 'type', 'width', 'u_height', 'desc_units', 'outer_width', 'outer_depth', 'outer_unit', 'comments', 'tags', + 'region', 'site', 'group', 'name', 'facility_id', 'tenant_group', 'tenant', 'status', 'role', 'serial', + 'asset_tag', 'type', 'width', 'u_height', 'desc_units', 'outer_width', 'outer_depth', 'outer_unit', + 'comments', 'tags', ] help_texts = { 'site': "The site at which the rack exists", @@ -548,9 +562,19 @@ class RackBulkEditForm(BootstrapMixin, AddRemoveTagsForm, CustomFieldBulkEditFor queryset=Rack.objects.all(), widget=forms.MultipleHiddenInput ) + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + initial_params={ + 'sites': '$site' + } + ) site = DynamicModelChoiceField( queryset=Site.objects.all(), - required=False + required=False, + query_params={ + 'region_id': '$region' + } ) group = DynamicModelChoiceField( queryset=RackGroup.objects.all(), @@ -691,9 +715,19 @@ class RackElevationFilterForm(RackFilterForm): # class RackReservationForm(BootstrapMixin, TenancyForm, forms.ModelForm): + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + initial_params={ + 'sites': '$site' + } + ) site = DynamicModelChoiceField( queryset=Site.objects.all(), - required=False + required=False, + query_params={ + 'region_id': '$region' + } ) rack_group = DynamicModelChoiceField( queryset=RackGroup.objects.all(), @@ -707,7 +741,7 @@ class RackReservationForm(BootstrapMixin, TenancyForm, forms.ModelForm): display_field='display_name', query_params={ 'site_id': '$site', - 'group_id': 'rack', + 'group_id': '$rack', } ) units = NumericArrayField( @@ -809,15 +843,23 @@ class RackReservationBulkEditForm(BootstrapMixin, AddRemoveTagsForm, BulkEditFor class RackReservationFilterForm(BootstrapMixin, TenancyFilterForm): model = RackReservation - field_order = ['q', 'site', 'group_id', 'tenant_group', 'tenant'] + field_order = ['q', 'region', 'site', 'group_id', 'tenant_group', 'tenant'] q = forms.CharField( required=False, label='Search' ) + region = DynamicModelMultipleChoiceField( + queryset=Region.objects.all(), + to_field_name='slug', + required=False + ) site = DynamicModelMultipleChoiceField( queryset=Site.objects.all(), to_field_name='slug', - required=False + required=False, + query_params={ + 'region': '$region' + } ) group_id = DynamicModelMultipleChoiceField( queryset=RackGroup.objects.prefetch_related('site'), @@ -3417,10 +3459,18 @@ class ConnectCableToDeviceForm(BootstrapMixin, forms.ModelForm): """ Base form for connecting a Cable to a Device component """ + termination_b_region = DynamicModelChoiceField( + queryset=Region.objects.all(), + label='Region', + required=False + ) termination_b_site = DynamicModelChoiceField( queryset=Site.objects.all(), label='Site', - required=False + required=False, + query_params={ + 'region_id': '$termination_b_region' + } ) termination_b_rack = DynamicModelChoiceField( queryset=Rack.objects.all(), @@ -3446,8 +3496,8 @@ class ConnectCableToDeviceForm(BootstrapMixin, forms.ModelForm): class Meta: model = Cable fields = [ - 'termination_b_site', 'termination_b_rack', 'termination_b_device', 'termination_b_id', 'type', 'status', - 'label', 'color', 'length', 'length_unit', + 'termination_b_region', 'termination_b_site', 'termination_b_rack', 'termination_b_device', + 'termination_b_id', 'type', 'status', 'label', 'color', 'length', 'length_unit', ] widgets = { 'status': StaticSelect2, @@ -3544,10 +3594,18 @@ class ConnectCableToCircuitTerminationForm(BootstrapMixin, forms.ModelForm): label='Provider', required=False ) + termination_b_region = DynamicModelChoiceField( + queryset=Region.objects.all(), + label='Region', + required=False + ) termination_b_site = DynamicModelChoiceField( queryset=Site.objects.all(), label='Site', - required=False + required=False, + query_params={ + 'region_id': '$termination_b_region' + } ) termination_b_circuit = DynamicModelChoiceField( queryset=Circuit.objects.all(), @@ -3571,8 +3629,8 @@ class ConnectCableToCircuitTerminationForm(BootstrapMixin, forms.ModelForm): class Meta: model = Cable fields = [ - 'termination_b_provider', 'termination_b_site', 'termination_b_circuit', 'termination_b_id', 'type', - 'status', 'label', 'color', 'length', 'length_unit', + 'termination_b_provider', 'termination_b_region', 'termination_b_site', 'termination_b_circuit', + 'termination_b_id', 'type', 'status', 'label', 'color', 'length', 'length_unit', ] def clean_termination_b_id(self): @@ -3581,11 +3639,18 @@ class ConnectCableToCircuitTerminationForm(BootstrapMixin, forms.ModelForm): class ConnectCableToPowerFeedForm(BootstrapMixin, forms.ModelForm): + termination_b_region = DynamicModelChoiceField( + queryset=Region.objects.all(), + label='Region', + required=False + ) termination_b_site = DynamicModelChoiceField( queryset=Site.objects.all(), label='Site', required=False, - display_field='cid' + query_params={ + 'region_id': '$termination_b_region' + } ) termination_b_rackgroup = DynamicModelChoiceField( queryset=RackGroup.objects.all(), @@ -3827,10 +3892,18 @@ class CableFilterForm(BootstrapMixin, forms.Form): required=False, label='Search' ) + region = DynamicModelMultipleChoiceField( + queryset=Region.objects.all(), + to_field_name='slug', + required=False + ) site = DynamicModelMultipleChoiceField( queryset=Site.objects.all(), to_field_name='slug', - required=False + required=False, + query_params={ + 'region': '$region' + } ) tenant = DynamicModelMultipleChoiceField( queryset=Tenant.objects.all(), @@ -3879,10 +3952,18 @@ class CableFilterForm(BootstrapMixin, forms.Form): # class ConsoleConnectionFilterForm(BootstrapMixin, forms.Form): + region = DynamicModelMultipleChoiceField( + queryset=Region.objects.all(), + to_field_name='slug', + required=False + ) site = DynamicModelMultipleChoiceField( queryset=Site.objects.all(), to_field_name='slug', - required=False + required=False, + query_params={ + 'region': '$region' + } ) device_id = DynamicModelMultipleChoiceField( queryset=Device.objects.all(), @@ -3895,10 +3976,18 @@ class ConsoleConnectionFilterForm(BootstrapMixin, forms.Form): class PowerConnectionFilterForm(BootstrapMixin, forms.Form): + region = DynamicModelMultipleChoiceField( + queryset=Region.objects.all(), + to_field_name='slug', + required=False + ) site = DynamicModelMultipleChoiceField( queryset=Site.objects.all(), to_field_name='slug', - required=False + required=False, + query_params={ + 'region': '$region' + } ) device_id = DynamicModelMultipleChoiceField( queryset=Device.objects.all(), @@ -3911,10 +4000,18 @@ class PowerConnectionFilterForm(BootstrapMixin, forms.Form): class InterfaceConnectionFilterForm(BootstrapMixin, forms.Form): + region = DynamicModelMultipleChoiceField( + queryset=Region.objects.all(), + to_field_name='slug', + required=False + ) site = DynamicModelMultipleChoiceField( queryset=Site.objects.all(), to_field_name='slug', - required=False + required=False, + query_params={ + 'region': '$region' + } ) device_id = DynamicModelMultipleChoiceField( queryset=Device.objects.all(), @@ -3938,9 +4035,19 @@ class DeviceSelectionForm(forms.Form): class VirtualChassisCreateForm(BootstrapMixin, forms.ModelForm): + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + initial_params={ + 'sites': '$site' + } + ) site = DynamicModelChoiceField( queryset=Site.objects.all(), - required=False + required=False, + query_params={ + 'region_id': '$region' + } ) rack = DynamicModelChoiceField( queryset=Rack.objects.all(), @@ -3973,7 +4080,7 @@ class VirtualChassisCreateForm(BootstrapMixin, forms.ModelForm): class Meta: model = VirtualChassis fields = [ - 'name', 'domain', 'site', 'rack', 'members', 'initial_position', 'tags', + 'name', 'domain', 'region', 'site', 'rack', 'members', 'initial_position', 'tags', ] def save(self, *args, **kwargs): @@ -4070,9 +4177,19 @@ class DeviceVCMembershipForm(forms.ModelForm): class VCMemberSelectForm(BootstrapMixin, forms.Form): + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + initial_params={ + 'sites': '$site' + } + ) site = DynamicModelChoiceField( queryset=Site.objects.all(), - required=False + required=False, + query_params={ + 'region_id': '$region' + } ) rack = DynamicModelChoiceField( queryset=Rack.objects.all(), @@ -4171,8 +4288,18 @@ class VirtualChassisFilterForm(BootstrapMixin, CustomFieldFilterForm): # class PowerPanelForm(BootstrapMixin, forms.ModelForm): + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + initial_params={ + 'sites': '$site' + } + ) site = DynamicModelChoiceField( - queryset=Site.objects.all() + queryset=Site.objects.all(), + query_params={ + 'region_id': '$region' + } ) rack_group = DynamicModelChoiceField( queryset=RackGroup.objects.all(), @@ -4189,7 +4316,7 @@ class PowerPanelForm(BootstrapMixin, forms.ModelForm): class Meta: model = PowerPanel fields = [ - 'site', 'rack_group', 'name', 'tags', + 'region', 'site', 'rack_group', 'name', 'tags', ] @@ -4224,9 +4351,19 @@ class PowerPanelBulkEditForm(BootstrapMixin, AddRemoveTagsForm, BulkEditForm): queryset=PowerPanel.objects.all(), widget=forms.MultipleHiddenInput ) + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + initial_params={ + 'sites': '$site' + } + ) site = DynamicModelChoiceField( queryset=Site.objects.all(), - required=False + required=False, + query_params={ + 'region_id': '$region' + } ) rack_group = DynamicModelChoiceField( queryset=RackGroup.objects.all(), @@ -4278,11 +4415,21 @@ class PowerPanelFilterForm(BootstrapMixin, CustomFieldFilterForm): # class PowerFeedForm(BootstrapMixin, CustomFieldModelForm): + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + initial_params={ + 'sites__powerpanel': '$power_panel' + } + ) site = DynamicModelChoiceField( queryset=Site.objects.all(), required=False, initial_params={ 'powerpanel': '$power_panel' + }, + query_params={ + 'region_id': '$region' } ) power_panel = DynamicModelChoiceField( @@ -4308,7 +4455,7 @@ class PowerFeedForm(BootstrapMixin, CustomFieldModelForm): class Meta: model = PowerFeed fields = [ - 'site', 'power_panel', 'rack', 'name', 'status', 'type', 'supply', 'phase', 'voltage', 'amperage', + 'region', 'site', 'power_panel', 'rack', 'name', 'status', 'type', 'supply', 'phase', 'voltage', 'amperage', 'max_utilization', 'comments', 'tags', ] widgets = { diff --git a/netbox/dcim/views.py b/netbox/dcim/views.py index 886f3e702..42175d782 100644 --- a/netbox/dcim/views.py +++ b/netbox/dcim/views.py @@ -2043,8 +2043,11 @@ class CableCreateView(ObjectEditView): initial_data = {k: request.GET[k] for k in request.GET} # Set initial site and rack based on side A termination (if not already set) + termination_a_site = getattr(obj.termination_a.parent, 'site', None) + if termination_a_site and 'termination_b_region' not in initial_data: + initial_data['termination_b_region'] = termination_a_site.region if 'termination_b_site' not in initial_data: - initial_data['termination_b_site'] = getattr(obj.termination_a.parent, 'site', None) + initial_data['termination_b_site'] = termination_a_site if 'termination_b_rack' not in initial_data: initial_data['termination_b_rack'] = getattr(obj.termination_a.parent, 'rack', None) diff --git a/netbox/ipam/forms.py b/netbox/ipam/forms.py index b49fb2e41..ce7524dea 100644 --- a/netbox/ipam/forms.py +++ b/netbox/ipam/forms.py @@ -253,10 +253,20 @@ class PrefixForm(BootstrapMixin, TenancyForm, CustomFieldModelForm): label='VRF', display_field='display_name' ) + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + initial_params={ + 'sites': '$site' + } + ) site = DynamicModelChoiceField( queryset=Site.objects.all(), required=False, - null_option='None' + null_option='None', + query_params={ + 'region_id': '$region' + } ) vlan_group = DynamicModelChoiceField( queryset=VLANGroup.objects.all(), @@ -369,9 +379,17 @@ class PrefixBulkEditForm(BootstrapMixin, AddRemoveTagsForm, CustomFieldBulkEditF queryset=Prefix.objects.all(), widget=forms.MultipleHiddenInput() ) + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + to_field_name='slug' + ) site = DynamicModelChoiceField( queryset=Site.objects.all(), - required=False + required=False, + query_params={ + 'region': '$region' + } ) vrf = DynamicModelChoiceField( queryset=VRF.objects.all(), @@ -529,10 +547,21 @@ class IPAddressForm(BootstrapMixin, TenancyForm, ReturnURLForm, CustomFieldModel label='VRF', display_field='display_name' ) + nat_region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + label='Region', + initial_params={ + 'sites': '$nat_site' + } + ) nat_site = DynamicModelChoiceField( queryset=Site.objects.all(), required=False, - label='Site' + label='Site', + query_params={ + 'region_id': '$nat_region' + } ) nat_rack = DynamicModelChoiceField( queryset=Rack.objects.all(), @@ -924,16 +953,26 @@ class IPAddressFilterForm(BootstrapMixin, TenancyFilterForm, CustomFieldFilterFo # class VLANGroupForm(BootstrapMixin, forms.ModelForm): + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + initial_params={ + 'sites': '$site' + } + ) site = DynamicModelChoiceField( queryset=Site.objects.all(), - required=False + required=False, + query_params={ + 'region_id': '$region' + } ) slug = SlugField() class Meta: model = VLANGroup fields = [ - 'site', 'name', 'slug', 'description', + 'region', 'site', 'name', 'slug', 'description', ] @@ -973,10 +1012,20 @@ class VLANGroupFilterForm(BootstrapMixin, forms.Form): # class VLANForm(BootstrapMixin, TenancyForm, CustomFieldModelForm): + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + initial_params={ + 'sites': '$site' + } + ) site = DynamicModelChoiceField( queryset=Site.objects.all(), required=False, - null_option='None' + null_option='None', + query_params={ + 'region_id': '$region' + } ) group = DynamicModelChoiceField( queryset=VLANGroup.objects.all(), @@ -1065,9 +1114,17 @@ class VLANBulkEditForm(BootstrapMixin, AddRemoveTagsForm, CustomFieldBulkEditFor queryset=VLAN.objects.all(), widget=forms.MultipleHiddenInput() ) + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + to_field_name='slug' + ) site = DynamicModelChoiceField( queryset=Site.objects.all(), - required=False + required=False, + query_params={ + 'region': '$region' + } ) group = DynamicModelChoiceField( queryset=VLANGroup.objects.all(), diff --git a/netbox/templates/circuits/circuittermination_edit.html b/netbox/templates/circuits/circuittermination_edit.html index 8a6171e5f..6867872f9 100644 --- a/netbox/templates/circuits/circuittermination_edit.html +++ b/netbox/templates/circuits/circuittermination_edit.html @@ -40,6 +40,7 @@

{{ form.term_side.value }}

+ {% render_field form.region %} {% render_field form.site %} diff --git a/netbox/templates/dcim/cable_connect.html b/netbox/templates/dcim/cable_connect.html index 644dfd3dc..05fd2de1a 100644 --- a/netbox/templates/dcim/cable_connect.html +++ b/netbox/templates/dcim/cable_connect.html @@ -32,6 +32,12 @@
{% if termination_a.device %} {# Device component #} +
+ +
+

{{ termination_a.device.site.region }}

+
+
@@ -111,6 +117,9 @@ {% if 'termination_b_provider' in form.fields %} {% render_field form.termination_b_provider %} {% endif %} + {% if 'termination_b_region' in form.fields %} + {% render_field form.termination_b_region %} + {% endif %} {% if 'termination_b_site' in form.fields %} {% render_field form.termination_b_site %} {% endif %} diff --git a/netbox/templates/dcim/powerfeed_edit.html b/netbox/templates/dcim/powerfeed_edit.html index f4b3ada46..e33aab19b 100644 --- a/netbox/templates/dcim/powerfeed_edit.html +++ b/netbox/templates/dcim/powerfeed_edit.html @@ -3,10 +3,16 @@ {% block form %}
-
Power Feed
+
Power Panel
+ {% render_field form.region %} {% render_field form.site %} {% render_field form.power_panel %} +
+
+
+
Power Feed
+
{% render_field form.rack %} {% render_field form.name %} {% render_field form.status %} diff --git a/netbox/templates/dcim/rack_edit.html b/netbox/templates/dcim/rack_edit.html index cd1192c19..c45aa190d 100644 --- a/netbox/templates/dcim/rack_edit.html +++ b/netbox/templates/dcim/rack_edit.html @@ -5,6 +5,7 @@
Rack
+ {% render_field form.region %} {% render_field form.site %} {% render_field form.name %} {% render_field form.facility_id %} diff --git a/netbox/templates/dcim/rackreservation_edit.html b/netbox/templates/dcim/rackreservation_edit.html index d6fa9cfcb..9dbc17653 100644 --- a/netbox/templates/dcim/rackreservation_edit.html +++ b/netbox/templates/dcim/rackreservation_edit.html @@ -5,6 +5,7 @@
Rack Reservation
+ {% render_field form.region %} {% render_field form.site %} {% render_field form.rack_group %} {% render_field form.rack %} diff --git a/netbox/templates/dcim/virtualchassis_add.html b/netbox/templates/dcim/virtualchassis_add.html index 07b17f378..ac94cc7df 100644 --- a/netbox/templates/dcim/virtualchassis_add.html +++ b/netbox/templates/dcim/virtualchassis_add.html @@ -13,6 +13,7 @@
Member Devices
+ {% render_field form.region %} {% render_field form.site %} {% render_field form.rack %} {% render_field form.members %} diff --git a/netbox/templates/ipam/ipaddress_edit.html b/netbox/templates/ipam/ipaddress_edit.html index e7894dbad..92093dea4 100644 --- a/netbox/templates/ipam/ipaddress_edit.html +++ b/netbox/templates/ipam/ipaddress_edit.html @@ -62,6 +62,7 @@
+ {% render_field form.nat_region %} {% render_field form.nat_site %} {% render_field form.nat_rack %} {% render_field form.nat_device %} diff --git a/netbox/templates/ipam/prefix_edit.html b/netbox/templates/ipam/prefix_edit.html index 401a53e38..126593074 100644 --- a/netbox/templates/ipam/prefix_edit.html +++ b/netbox/templates/ipam/prefix_edit.html @@ -16,6 +16,7 @@
Site/VLAN Assignment
+ {% render_field form.region %} {% render_field form.site %} {% render_field form.vlan_group %} {% render_field form.vlan %} diff --git a/netbox/templates/ipam/vlan_edit.html b/netbox/templates/ipam/vlan_edit.html index 1c191343d..9ea3cdabb 100644 --- a/netbox/templates/ipam/vlan_edit.html +++ b/netbox/templates/ipam/vlan_edit.html @@ -8,12 +8,18 @@ {% render_field form.vid %} {% render_field form.name %} {% render_field form.status %} - {% render_field form.site %} - {% render_field form.group %} {% render_field form.role %} {% render_field form.description %}
+
+
Assignment
+
+ {% render_field form.region %} + {% render_field form.site %} + {% render_field form.group %} +
+
Tenancy
diff --git a/netbox/templates/virtualization/cluster_edit.html b/netbox/templates/virtualization/cluster_edit.html index c4d39d12e..5ad7c53e1 100644 --- a/netbox/templates/virtualization/cluster_edit.html +++ b/netbox/templates/virtualization/cluster_edit.html @@ -8,6 +8,7 @@ {% render_field form.name %} {% render_field form.type %} {% render_field form.group %} + {% render_field form.region %} {% render_field form.site %}
diff --git a/netbox/virtualization/forms.py b/netbox/virtualization/forms.py index f99840f86..ce4ca3e3c 100644 --- a/netbox/virtualization/forms.py +++ b/netbox/virtualization/forms.py @@ -79,9 +79,19 @@ class ClusterForm(BootstrapMixin, TenancyForm, CustomFieldModelForm): queryset=ClusterGroup.objects.all(), required=False ) + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + initial_params={ + 'sites': '$site' + } + ) site = DynamicModelChoiceField( queryset=Site.objects.all(), - required=False + required=False, + query_params={ + 'region_id': '$region' + } ) comments = CommentField() tags = DynamicModelMultipleChoiceField( @@ -92,7 +102,7 @@ class ClusterForm(BootstrapMixin, TenancyForm, CustomFieldModelForm): class Meta: model = Cluster fields = ( - 'name', 'type', 'group', 'tenant', 'site', 'comments', 'tags', + 'name', 'type', 'group', 'tenant', 'region', 'site', 'comments', 'tags', ) @@ -143,9 +153,17 @@ class ClusterBulkEditForm(BootstrapMixin, AddRemoveTagsForm, CustomFieldBulkEdit queryset=Tenant.objects.all(), required=False ) + region = DynamicModelChoiceField( + queryset=Region.objects.all(), + required=False, + to_field_name='slug' + ) site = DynamicModelChoiceField( queryset=Site.objects.all(), - required=False + required=False, + query_params={ + 'region': '$region' + } ) comments = CommentField( widget=SmallTextarea,