mirror of
https://github.com/netbox-community/netbox.git
synced 2025-07-19 09:53:34 -06:00
Closes #3648: Mark cable termination models as connected without attaching a cable
This commit is contained in:
parent
6ed2e7b636
commit
8dd7123923
@ -4,6 +4,14 @@
|
|||||||
|
|
||||||
**WARNING:** This is a beta release and is not suitable for production use. It is intended for development and evaluation purposes only. No upgrade path to the final v2.11 release will be provided from this beta, and users should assume that all data entered into the application will be lost.
|
**WARNING:** This is a beta release and is not suitable for production use. It is intended for development and evaluation purposes only. No upgrade path to the final v2.11 release will be provided from this beta, and users should assume that all data entered into the application will be lost.
|
||||||
|
|
||||||
|
### New Features
|
||||||
|
|
||||||
|
#### Mark as Connected Without a Cable ([#3648](https://github.com/netbox-community/netbox/issues/3648))
|
||||||
|
|
||||||
|
Cable termination objects (circuit terminations, power feeds, and most device components) can now be marked as "connected" without actually attaching a cable. This helps simplify the process of modeling an infrastructure boundary where you don't necessarily know or care what is connected to the far end of a cable, but still need to designate the near end termination.
|
||||||
|
|
||||||
|
In addition to the new `mark_connected` boolean field, the REST API representation of these objects now also includes a read-only boolean field named `_occupied`. This conveniently returns true if either a cable is attached or `mark_connected` is true.
|
||||||
|
|
||||||
### Enhancements
|
### Enhancements
|
||||||
|
|
||||||
* [#5370](https://github.com/netbox-community/netbox/issues/5370) - Extend custom field support to organizational models
|
* [#5370](https://github.com/netbox-community/netbox/issues/5370) - Extend custom field support to organizational models
|
||||||
@ -16,3 +24,19 @@
|
|||||||
|
|
||||||
* [#1638](https://github.com/netbox-community/netbox/issues/1638) - Migrate all primary keys to 64-bit integers
|
* [#1638](https://github.com/netbox-community/netbox/issues/1638) - Migrate all primary keys to 64-bit integers
|
||||||
* [#5873](https://github.com/netbox-community/netbox/issues/5873) - Use numeric IDs in all object URLs
|
* [#5873](https://github.com/netbox-community/netbox/issues/5873) - Use numeric IDs in all object URLs
|
||||||
|
|
||||||
|
### REST API Changes
|
||||||
|
|
||||||
|
* All primary keys are now 64-bit integers
|
||||||
|
* All device components
|
||||||
|
* Added support for custom fields
|
||||||
|
* Added `created` and `last_updated` fields to track object creation and modification
|
||||||
|
* All device component templates
|
||||||
|
* Added `created` and `last_updated` fields to track object creation and modification
|
||||||
|
* All organizational models
|
||||||
|
* Added support for custom fields
|
||||||
|
* All cable termination models (cabled device components, power feeds, and circuit terminations)
|
||||||
|
* Added `mark_connected` boolean field to force connection status
|
||||||
|
* Added `_occupied` read-only boolean field as common attribute for determining whether an object is occupied
|
||||||
|
* extras.CustomField
|
||||||
|
* Added new custom field type: `multi-select`
|
||||||
|
@ -51,4 +51,4 @@ class NestedCircuitTerminationSerializer(WritableNestedSerializer):
|
|||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
model = CircuitTermination
|
model = CircuitTermination
|
||||||
fields = ['id', 'url', 'circuit', 'term_side', 'cable']
|
fields = ['id', 'url', 'circuit', 'term_side', 'cable', '_occupied']
|
||||||
|
@ -82,6 +82,6 @@ class CircuitTerminationSerializer(CableTerminationSerializer, ConnectedEndpoint
|
|||||||
model = CircuitTermination
|
model = CircuitTermination
|
||||||
fields = [
|
fields = [
|
||||||
'id', 'url', 'circuit', 'term_side', 'site', 'port_speed', 'upstream_speed', 'xconnect_id', 'pp_info',
|
'id', 'url', 'circuit', 'term_side', 'site', 'port_speed', 'upstream_speed', 'xconnect_id', 'pp_info',
|
||||||
'description', 'cable', 'cable_peer', 'cable_peer_type', 'connected_endpoint', 'connected_endpoint_type',
|
'description', 'mark_connected', 'cable', 'cable_peer', 'cable_peer_type', 'connected_endpoint',
|
||||||
'connected_endpoint_reachable'
|
'connected_endpoint_type', 'connected_endpoint_reachable', '_occupied',
|
||||||
]
|
]
|
||||||
|
@ -330,7 +330,8 @@ class CircuitTerminationForm(BootstrapMixin, forms.ModelForm):
|
|||||||
class Meta:
|
class Meta:
|
||||||
model = CircuitTermination
|
model = CircuitTermination
|
||||||
fields = [
|
fields = [
|
||||||
'term_side', 'region', 'site', 'port_speed', 'upstream_speed', 'xconnect_id', 'pp_info', 'description',
|
'term_side', 'region', 'site', 'mark_connected', 'port_speed', 'upstream_speed', 'xconnect_id', 'pp_info',
|
||||||
|
'description',
|
||||||
]
|
]
|
||||||
help_texts = {
|
help_texts = {
|
||||||
'port_speed': "Physical circuit speed",
|
'port_speed': "Physical circuit speed",
|
||||||
|
16
netbox/circuits/migrations/0026_mark_connected.py
Normal file
16
netbox/circuits/migrations/0026_mark_connected.py
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
from django.db import migrations, models
|
||||||
|
|
||||||
|
|
||||||
|
class Migration(migrations.Migration):
|
||||||
|
|
||||||
|
dependencies = [
|
||||||
|
('circuits', '0025_standardize_models'),
|
||||||
|
]
|
||||||
|
|
||||||
|
operations = [
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='circuittermination',
|
||||||
|
name='mark_connected',
|
||||||
|
field=models.BooleanField(default=False),
|
||||||
|
),
|
||||||
|
]
|
@ -129,7 +129,7 @@ class CircuitTest(APIViewTestCases.APIViewTestCase):
|
|||||||
|
|
||||||
class CircuitTerminationTest(APIViewTestCases.APIViewTestCase):
|
class CircuitTerminationTest(APIViewTestCases.APIViewTestCase):
|
||||||
model = CircuitTermination
|
model = CircuitTermination
|
||||||
brief_fields = ['cable', 'circuit', 'id', 'term_side', 'url']
|
brief_fields = ['_occupied', 'cable', 'circuit', 'id', 'term_side', 'url']
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
def setUpTestData(cls):
|
def setUpTestData(cls):
|
||||||
|
@ -230,7 +230,7 @@ class NestedConsoleServerPortSerializer(WritableNestedSerializer):
|
|||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
model = models.ConsoleServerPort
|
model = models.ConsoleServerPort
|
||||||
fields = ['id', 'url', 'device', 'name', 'cable']
|
fields = ['id', 'url', 'device', 'name', 'cable', '_occupied']
|
||||||
|
|
||||||
|
|
||||||
class NestedConsolePortSerializer(WritableNestedSerializer):
|
class NestedConsolePortSerializer(WritableNestedSerializer):
|
||||||
@ -239,7 +239,7 @@ class NestedConsolePortSerializer(WritableNestedSerializer):
|
|||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
model = models.ConsolePort
|
model = models.ConsolePort
|
||||||
fields = ['id', 'url', 'device', 'name', 'cable']
|
fields = ['id', 'url', 'device', 'name', 'cable', '_occupied']
|
||||||
|
|
||||||
|
|
||||||
class NestedPowerOutletSerializer(WritableNestedSerializer):
|
class NestedPowerOutletSerializer(WritableNestedSerializer):
|
||||||
@ -248,7 +248,7 @@ class NestedPowerOutletSerializer(WritableNestedSerializer):
|
|||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
model = models.PowerOutlet
|
model = models.PowerOutlet
|
||||||
fields = ['id', 'url', 'device', 'name', 'cable']
|
fields = ['id', 'url', 'device', 'name', 'cable', '_occupied']
|
||||||
|
|
||||||
|
|
||||||
class NestedPowerPortSerializer(WritableNestedSerializer):
|
class NestedPowerPortSerializer(WritableNestedSerializer):
|
||||||
@ -257,7 +257,7 @@ class NestedPowerPortSerializer(WritableNestedSerializer):
|
|||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
model = models.PowerPort
|
model = models.PowerPort
|
||||||
fields = ['id', 'url', 'device', 'name', 'cable']
|
fields = ['id', 'url', 'device', 'name', 'cable', '_occupied']
|
||||||
|
|
||||||
|
|
||||||
class NestedInterfaceSerializer(WritableNestedSerializer):
|
class NestedInterfaceSerializer(WritableNestedSerializer):
|
||||||
@ -266,7 +266,7 @@ class NestedInterfaceSerializer(WritableNestedSerializer):
|
|||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
model = models.Interface
|
model = models.Interface
|
||||||
fields = ['id', 'url', 'device', 'name', 'cable']
|
fields = ['id', 'url', 'device', 'name', 'cable', '_occupied']
|
||||||
|
|
||||||
|
|
||||||
class NestedRearPortSerializer(WritableNestedSerializer):
|
class NestedRearPortSerializer(WritableNestedSerializer):
|
||||||
@ -275,7 +275,7 @@ class NestedRearPortSerializer(WritableNestedSerializer):
|
|||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
model = models.RearPort
|
model = models.RearPort
|
||||||
fields = ['id', 'url', 'device', 'name', 'cable']
|
fields = ['id', 'url', 'device', 'name', 'cable', '_occupied']
|
||||||
|
|
||||||
|
|
||||||
class NestedFrontPortSerializer(WritableNestedSerializer):
|
class NestedFrontPortSerializer(WritableNestedSerializer):
|
||||||
@ -284,7 +284,7 @@ class NestedFrontPortSerializer(WritableNestedSerializer):
|
|||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
model = models.FrontPort
|
model = models.FrontPort
|
||||||
fields = ['id', 'url', 'device', 'name', 'cable']
|
fields = ['id', 'url', 'device', 'name', 'cable', '_occupied']
|
||||||
|
|
||||||
|
|
||||||
class NestedDeviceBaySerializer(WritableNestedSerializer):
|
class NestedDeviceBaySerializer(WritableNestedSerializer):
|
||||||
@ -350,4 +350,4 @@ class NestedPowerFeedSerializer(WritableNestedSerializer):
|
|||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
model = models.PowerFeed
|
model = models.PowerFeed
|
||||||
fields = ['id', 'url', 'name', 'cable']
|
fields = ['id', 'url', 'name', 'cable', '_occupied']
|
||||||
|
@ -509,9 +509,9 @@ class ConsoleServerPortSerializer(TaggedObjectSerializer, CableTerminationSerial
|
|||||||
class Meta:
|
class Meta:
|
||||||
model = ConsoleServerPort
|
model = ConsoleServerPort
|
||||||
fields = [
|
fields = [
|
||||||
'id', 'url', 'device', 'name', 'label', 'type', 'description', 'cable', 'cable_peer', 'cable_peer_type',
|
'id', 'url', 'device', 'name', 'label', 'type', 'description', 'mark_connected', 'cable', 'cable_peer',
|
||||||
'connected_endpoint', 'connected_endpoint_type', 'connected_endpoint_reachable', 'tags', 'custom_fields',
|
'cable_peer_type', 'connected_endpoint', 'connected_endpoint_type', 'connected_endpoint_reachable', 'tags',
|
||||||
'created', 'last_updated',
|
'custom_fields', 'created', 'last_updated', '_occupied',
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
@ -528,9 +528,9 @@ class ConsolePortSerializer(TaggedObjectSerializer, CableTerminationSerializer,
|
|||||||
class Meta:
|
class Meta:
|
||||||
model = ConsolePort
|
model = ConsolePort
|
||||||
fields = [
|
fields = [
|
||||||
'id', 'url', 'device', 'name', 'label', 'type', 'description', 'cable', 'cable_peer', 'cable_peer_type',
|
'id', 'url', 'device', 'name', 'label', 'type', 'description', 'mark_connected', 'cable', 'cable_peer',
|
||||||
'connected_endpoint', 'connected_endpoint_type', 'connected_endpoint_reachable', 'tags', 'custom_fields',
|
'cable_peer_type', 'connected_endpoint', 'connected_endpoint_type', 'connected_endpoint_reachable', 'tags',
|
||||||
'created', 'last_updated',
|
'custom_fields', 'created', 'last_updated', '_occupied',
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
@ -557,9 +557,9 @@ class PowerOutletSerializer(TaggedObjectSerializer, CableTerminationSerializer,
|
|||||||
class Meta:
|
class Meta:
|
||||||
model = PowerOutlet
|
model = PowerOutlet
|
||||||
fields = [
|
fields = [
|
||||||
'id', 'url', 'device', 'name', 'label', 'type', 'power_port', 'feed_leg', 'description', 'cable',
|
'id', 'url', 'device', 'name', 'label', 'type', 'power_port', 'feed_leg', 'description', 'mark_connected',
|
||||||
'cable_peer', 'cable_peer_type', 'connected_endpoint', 'connected_endpoint_type',
|
'cable', 'cable_peer', 'cable_peer_type', 'connected_endpoint', 'connected_endpoint_type',
|
||||||
'connected_endpoint_reachable', 'tags', 'custom_fields', 'created', 'last_updated',
|
'connected_endpoint_reachable', 'tags', 'custom_fields', 'created', 'last_updated', '_occupied',
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
@ -576,9 +576,9 @@ class PowerPortSerializer(TaggedObjectSerializer, CableTerminationSerializer, Co
|
|||||||
class Meta:
|
class Meta:
|
||||||
model = PowerPort
|
model = PowerPort
|
||||||
fields = [
|
fields = [
|
||||||
'id', 'url', 'device', 'name', 'label', 'type', 'maximum_draw', 'allocated_draw', 'description', 'cable',
|
'id', 'url', 'device', 'name', 'label', 'type', 'maximum_draw', 'allocated_draw', 'description',
|
||||||
'cable_peer', 'cable_peer_type', 'connected_endpoint', 'connected_endpoint_type',
|
'mark_connected', 'cable', 'cable_peer', 'cable_peer_type', 'connected_endpoint', 'connected_endpoint_type',
|
||||||
'connected_endpoint_reachable', 'tags', 'custom_fields', 'created', 'last_updated',
|
'connected_endpoint_reachable', 'tags', 'custom_fields', 'created', 'last_updated', '_occupied',
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
@ -602,9 +602,9 @@ class InterfaceSerializer(TaggedObjectSerializer, CableTerminationSerializer, Co
|
|||||||
model = Interface
|
model = Interface
|
||||||
fields = [
|
fields = [
|
||||||
'id', 'url', 'device', 'name', 'label', 'type', 'enabled', 'lag', 'mtu', 'mac_address', 'mgmt_only',
|
'id', 'url', 'device', 'name', 'label', 'type', 'enabled', 'lag', 'mtu', 'mac_address', 'mgmt_only',
|
||||||
'description', 'mode', 'untagged_vlan', 'tagged_vlans', 'cable', 'cable_peer', 'cable_peer_type',
|
'description', 'mode', 'untagged_vlan', 'tagged_vlans', 'mark_connected', 'cable', 'cable_peer',
|
||||||
'connected_endpoint', 'connected_endpoint_type', 'connected_endpoint_reachable', 'tags', 'custom_fields',
|
'cable_peer_type', 'connected_endpoint', 'connected_endpoint_type', 'connected_endpoint_reachable', 'tags',
|
||||||
'created', 'last_updated', 'count_ipaddresses',
|
'custom_fields', 'created', 'last_updated', 'count_ipaddresses', '_occupied',
|
||||||
]
|
]
|
||||||
|
|
||||||
def validate(self, data):
|
def validate(self, data):
|
||||||
@ -630,8 +630,8 @@ class RearPortSerializer(TaggedObjectSerializer, CableTerminationSerializer, Cus
|
|||||||
class Meta:
|
class Meta:
|
||||||
model = RearPort
|
model = RearPort
|
||||||
fields = [
|
fields = [
|
||||||
'id', 'url', 'device', 'name', 'label', 'type', 'positions', 'description', 'cable', 'cable_peer',
|
'id', 'url', 'device', 'name', 'label', 'type', 'positions', 'description', 'mark_connected', 'cable',
|
||||||
'cable_peer_type', 'tags', 'custom_fields', 'created', 'last_updated',
|
'cable_peer', 'cable_peer_type', 'tags', 'custom_fields', 'created', 'last_updated', '_occupied',
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
@ -656,8 +656,9 @@ class FrontPortSerializer(TaggedObjectSerializer, CableTerminationSerializer, Cu
|
|||||||
class Meta:
|
class Meta:
|
||||||
model = FrontPort
|
model = FrontPort
|
||||||
fields = [
|
fields = [
|
||||||
'id', 'url', 'device', 'name', 'label', 'type', 'rear_port', 'rear_port_position', 'description', 'cable',
|
'id', 'url', 'device', 'name', 'label', 'type', 'rear_port', 'rear_port_position', 'description',
|
||||||
'cable_peer', 'cable_peer_type', 'tags', 'custom_fields', 'created', 'last_updated',
|
'mark_connected', 'cable', 'cable_peer', 'cable_peer_type', 'tags', 'custom_fields', 'created',
|
||||||
|
'last_updated', '_occupied',
|
||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
@ -892,7 +893,7 @@ class PowerFeedSerializer(
|
|||||||
model = PowerFeed
|
model = PowerFeed
|
||||||
fields = [
|
fields = [
|
||||||
'id', 'url', 'power_panel', 'rack', 'name', 'status', 'type', 'supply', 'phase', 'voltage', 'amperage',
|
'id', 'url', 'power_panel', 'rack', 'name', 'status', 'type', 'supply', 'phase', 'voltage', 'amperage',
|
||||||
'max_utilization', 'comments', 'cable', 'cable_peer', 'cable_peer_type', 'connected_endpoint',
|
'max_utilization', 'comments', 'mark_connected', 'cable', 'cable_peer', 'cable_peer_type',
|
||||||
'connected_endpoint_type', 'connected_endpoint_reachable', 'tags', 'custom_fields', 'created',
|
'connected_endpoint', 'connected_endpoint_type', 'connected_endpoint_reachable', 'tags', 'custom_fields',
|
||||||
'last_updated',
|
'created', 'last_updated', '_occupied',
|
||||||
]
|
]
|
||||||
|
@ -2324,7 +2324,7 @@ class ConsolePortForm(BootstrapMixin, CustomFieldModelForm):
|
|||||||
class Meta:
|
class Meta:
|
||||||
model = ConsolePort
|
model = ConsolePort
|
||||||
fields = [
|
fields = [
|
||||||
'device', 'name', 'label', 'type', 'description', 'tags',
|
'device', 'name', 'label', 'type', 'mark_connected', 'description', 'tags',
|
||||||
]
|
]
|
||||||
widgets = {
|
widgets = {
|
||||||
'device': forms.HiddenInput(),
|
'device': forms.HiddenInput(),
|
||||||
@ -2338,19 +2338,19 @@ class ConsolePortCreateForm(ComponentCreateForm):
|
|||||||
required=False,
|
required=False,
|
||||||
widget=StaticSelect2()
|
widget=StaticSelect2()
|
||||||
)
|
)
|
||||||
field_order = ('device', 'name_pattern', 'label_pattern', 'type', 'description', 'tags')
|
field_order = ('device', 'name_pattern', 'label_pattern', 'type', 'mark_connected', 'description', 'tags')
|
||||||
|
|
||||||
|
|
||||||
class ConsolePortBulkCreateForm(
|
class ConsolePortBulkCreateForm(
|
||||||
form_from_model(ConsolePort, ['type']),
|
form_from_model(ConsolePort, ['type', 'mark_connected']),
|
||||||
DeviceBulkAddComponentForm
|
DeviceBulkAddComponentForm
|
||||||
):
|
):
|
||||||
model = ConsolePort
|
model = ConsolePort
|
||||||
field_order = ('name_pattern', 'label_pattern', 'type', 'description', 'tags')
|
field_order = ('name_pattern', 'label_pattern', 'type', 'mark_connected', 'description', 'tags')
|
||||||
|
|
||||||
|
|
||||||
class ConsolePortBulkEditForm(
|
class ConsolePortBulkEditForm(
|
||||||
form_from_model(ConsolePort, ['label', 'type', 'description']),
|
form_from_model(ConsolePort, ['label', 'type', 'mark_connected', 'description']),
|
||||||
BootstrapMixin,
|
BootstrapMixin,
|
||||||
AddRemoveTagsForm,
|
AddRemoveTagsForm,
|
||||||
CustomFieldBulkEditForm
|
CustomFieldBulkEditForm
|
||||||
@ -2772,8 +2772,8 @@ class InterfaceForm(BootstrapMixin, InterfaceCommonForm, CustomFieldModelForm):
|
|||||||
class Meta:
|
class Meta:
|
||||||
model = Interface
|
model = Interface
|
||||||
fields = [
|
fields = [
|
||||||
'device', 'name', 'label', 'type', 'enabled', 'lag', 'mac_address', 'mtu', 'mgmt_only', 'description',
|
'device', 'name', 'label', 'type', 'enabled', 'lag', 'mac_address', 'mtu', 'mgmt_only', 'mark_connected',
|
||||||
'mode', 'untagged_vlan', 'tagged_vlans', 'tags',
|
'description', 'mode', 'untagged_vlan', 'tagged_vlans', 'tags',
|
||||||
]
|
]
|
||||||
widgets = {
|
widgets = {
|
||||||
'device': forms.HiddenInput(),
|
'device': forms.HiddenInput(),
|
||||||
@ -3625,7 +3625,7 @@ class ConnectCableToConsolePortForm(ConnectCableToDeviceForm):
|
|||||||
termination_b_id = DynamicModelChoiceField(
|
termination_b_id = DynamicModelChoiceField(
|
||||||
queryset=ConsolePort.objects.all(),
|
queryset=ConsolePort.objects.all(),
|
||||||
label='Name',
|
label='Name',
|
||||||
disabled_indicator='cable',
|
disabled_indicator='_occupied',
|
||||||
query_params={
|
query_params={
|
||||||
'device_id': '$termination_b_device'
|
'device_id': '$termination_b_device'
|
||||||
}
|
}
|
||||||
@ -3636,7 +3636,7 @@ class ConnectCableToConsoleServerPortForm(ConnectCableToDeviceForm):
|
|||||||
termination_b_id = DynamicModelChoiceField(
|
termination_b_id = DynamicModelChoiceField(
|
||||||
queryset=ConsoleServerPort.objects.all(),
|
queryset=ConsoleServerPort.objects.all(),
|
||||||
label='Name',
|
label='Name',
|
||||||
disabled_indicator='cable',
|
disabled_indicator='_occupied',
|
||||||
query_params={
|
query_params={
|
||||||
'device_id': '$termination_b_device'
|
'device_id': '$termination_b_device'
|
||||||
}
|
}
|
||||||
@ -3647,7 +3647,7 @@ class ConnectCableToPowerPortForm(ConnectCableToDeviceForm):
|
|||||||
termination_b_id = DynamicModelChoiceField(
|
termination_b_id = DynamicModelChoiceField(
|
||||||
queryset=PowerPort.objects.all(),
|
queryset=PowerPort.objects.all(),
|
||||||
label='Name',
|
label='Name',
|
||||||
disabled_indicator='cable',
|
disabled_indicator='_occupied',
|
||||||
query_params={
|
query_params={
|
||||||
'device_id': '$termination_b_device'
|
'device_id': '$termination_b_device'
|
||||||
}
|
}
|
||||||
@ -3658,7 +3658,7 @@ class ConnectCableToPowerOutletForm(ConnectCableToDeviceForm):
|
|||||||
termination_b_id = DynamicModelChoiceField(
|
termination_b_id = DynamicModelChoiceField(
|
||||||
queryset=PowerOutlet.objects.all(),
|
queryset=PowerOutlet.objects.all(),
|
||||||
label='Name',
|
label='Name',
|
||||||
disabled_indicator='cable',
|
disabled_indicator='_occupied',
|
||||||
query_params={
|
query_params={
|
||||||
'device_id': '$termination_b_device'
|
'device_id': '$termination_b_device'
|
||||||
}
|
}
|
||||||
@ -3669,7 +3669,7 @@ class ConnectCableToInterfaceForm(ConnectCableToDeviceForm):
|
|||||||
termination_b_id = DynamicModelChoiceField(
|
termination_b_id = DynamicModelChoiceField(
|
||||||
queryset=Interface.objects.all(),
|
queryset=Interface.objects.all(),
|
||||||
label='Name',
|
label='Name',
|
||||||
disabled_indicator='cable',
|
disabled_indicator='_occupied',
|
||||||
query_params={
|
query_params={
|
||||||
'device_id': '$termination_b_device',
|
'device_id': '$termination_b_device',
|
||||||
'kind': 'physical',
|
'kind': 'physical',
|
||||||
@ -3681,7 +3681,7 @@ class ConnectCableToFrontPortForm(ConnectCableToDeviceForm):
|
|||||||
termination_b_id = DynamicModelChoiceField(
|
termination_b_id = DynamicModelChoiceField(
|
||||||
queryset=FrontPort.objects.all(),
|
queryset=FrontPort.objects.all(),
|
||||||
label='Name',
|
label='Name',
|
||||||
disabled_indicator='cable',
|
disabled_indicator='_occupied',
|
||||||
query_params={
|
query_params={
|
||||||
'device_id': '$termination_b_device'
|
'device_id': '$termination_b_device'
|
||||||
}
|
}
|
||||||
@ -3692,7 +3692,7 @@ class ConnectCableToRearPortForm(ConnectCableToDeviceForm):
|
|||||||
termination_b_id = DynamicModelChoiceField(
|
termination_b_id = DynamicModelChoiceField(
|
||||||
queryset=RearPort.objects.all(),
|
queryset=RearPort.objects.all(),
|
||||||
label='Name',
|
label='Name',
|
||||||
disabled_indicator='cable',
|
disabled_indicator='_occupied',
|
||||||
query_params={
|
query_params={
|
||||||
'device_id': '$termination_b_device'
|
'device_id': '$termination_b_device'
|
||||||
}
|
}
|
||||||
@ -3731,7 +3731,7 @@ class ConnectCableToCircuitTerminationForm(BootstrapMixin, CustomFieldModelForm)
|
|||||||
queryset=CircuitTermination.objects.all(),
|
queryset=CircuitTermination.objects.all(),
|
||||||
label='Side',
|
label='Side',
|
||||||
display_field='term_side',
|
display_field='term_side',
|
||||||
disabled_indicator='cable',
|
disabled_indicator='_occupied',
|
||||||
query_params={
|
query_params={
|
||||||
'circuit_id': '$termination_b_circuit'
|
'circuit_id': '$termination_b_circuit'
|
||||||
}
|
}
|
||||||
@ -3788,7 +3788,7 @@ class ConnectCableToPowerFeedForm(BootstrapMixin, CustomFieldModelForm):
|
|||||||
termination_b_id = DynamicModelChoiceField(
|
termination_b_id = DynamicModelChoiceField(
|
||||||
queryset=PowerFeed.objects.all(),
|
queryset=PowerFeed.objects.all(),
|
||||||
label='Name',
|
label='Name',
|
||||||
disabled_indicator='cable',
|
disabled_indicator='_occupied',
|
||||||
query_params={
|
query_params={
|
||||||
'power_panel_id': '$termination_b_powerpanel'
|
'power_panel_id': '$termination_b_powerpanel'
|
||||||
}
|
}
|
||||||
@ -4538,12 +4538,12 @@ class PowerFeedForm(BootstrapMixin, CustomFieldModelForm):
|
|||||||
class Meta:
|
class Meta:
|
||||||
model = PowerFeed
|
model = PowerFeed
|
||||||
fields = [
|
fields = [
|
||||||
'region', 'site', 'power_panel', 'rack', 'name', 'status', 'type', 'supply', 'phase', 'voltage', 'amperage',
|
'region', 'site', 'power_panel', 'rack', 'name', 'status', 'type', 'mark_connected', 'supply', 'phase',
|
||||||
'max_utilization', 'comments', 'tags',
|
'voltage', 'amperage', 'max_utilization', 'comments', 'tags',
|
||||||
]
|
]
|
||||||
fieldsets = (
|
fieldsets = (
|
||||||
('Power Panel', ('region', 'site', 'power_panel')),
|
('Power Panel', ('region', 'site', 'power_panel')),
|
||||||
('Power Feed', ('rack', 'name', 'status', 'type', 'tags')),
|
('Power Feed', ('rack', 'name', 'status', 'type', 'mark_connected', 'tags')),
|
||||||
('Characteristics', ('supply', 'voltage', 'amperage', 'phase', 'max_utilization')),
|
('Characteristics', ('supply', 'voltage', 'amperage', 'phase', 'max_utilization')),
|
||||||
)
|
)
|
||||||
widgets = {
|
widgets = {
|
||||||
|
51
netbox/dcim/migrations/0124_mark_connected.py
Normal file
51
netbox/dcim/migrations/0124_mark_connected.py
Normal file
@ -0,0 +1,51 @@
|
|||||||
|
from django.db import migrations, models
|
||||||
|
|
||||||
|
|
||||||
|
class Migration(migrations.Migration):
|
||||||
|
|
||||||
|
dependencies = [
|
||||||
|
('dcim', '0123_standardize_models'),
|
||||||
|
]
|
||||||
|
|
||||||
|
operations = [
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='consoleport',
|
||||||
|
name='mark_connected',
|
||||||
|
field=models.BooleanField(default=False),
|
||||||
|
),
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='consoleserverport',
|
||||||
|
name='mark_connected',
|
||||||
|
field=models.BooleanField(default=False),
|
||||||
|
),
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='frontport',
|
||||||
|
name='mark_connected',
|
||||||
|
field=models.BooleanField(default=False),
|
||||||
|
),
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='interface',
|
||||||
|
name='mark_connected',
|
||||||
|
field=models.BooleanField(default=False),
|
||||||
|
),
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='powerfeed',
|
||||||
|
name='mark_connected',
|
||||||
|
field=models.BooleanField(default=False),
|
||||||
|
),
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='poweroutlet',
|
||||||
|
name='mark_connected',
|
||||||
|
field=models.BooleanField(default=False),
|
||||||
|
),
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='powerport',
|
||||||
|
name='mark_connected',
|
||||||
|
field=models.BooleanField(default=False),
|
||||||
|
),
|
||||||
|
migrations.AddField(
|
||||||
|
model_name='rearport',
|
||||||
|
name='mark_connected',
|
||||||
|
field=models.BooleanField(default=False),
|
||||||
|
),
|
||||||
|
]
|
@ -126,6 +126,10 @@ class CableTermination(models.Model):
|
|||||||
ct_field='_cable_peer_type',
|
ct_field='_cable_peer_type',
|
||||||
fk_field='_cable_peer_id'
|
fk_field='_cable_peer_id'
|
||||||
)
|
)
|
||||||
|
mark_connected = models.BooleanField(
|
||||||
|
default=False,
|
||||||
|
help_text="Treat as if a cable is connected"
|
||||||
|
)
|
||||||
|
|
||||||
# Generic relations to Cable. These ensure that an attached Cable is deleted if the terminated object is deleted.
|
# Generic relations to Cable. These ensure that an attached Cable is deleted if the terminated object is deleted.
|
||||||
_cabled_as_a = GenericRelation(
|
_cabled_as_a = GenericRelation(
|
||||||
@ -142,9 +146,19 @@ class CableTermination(models.Model):
|
|||||||
class Meta:
|
class Meta:
|
||||||
abstract = True
|
abstract = True
|
||||||
|
|
||||||
|
def clean(self):
|
||||||
|
super().clean()
|
||||||
|
|
||||||
|
if self.mark_connected and self.cable_id:
|
||||||
|
raise ValidationError("Cannot set mark_connected with a cable connected.")
|
||||||
|
|
||||||
def get_cable_peer(self):
|
def get_cable_peer(self):
|
||||||
return self._cable_peer
|
return self._cable_peer
|
||||||
|
|
||||||
|
@property
|
||||||
|
def _occupied(self):
|
||||||
|
return bool(self.mark_connected or self.cable_id)
|
||||||
|
|
||||||
|
|
||||||
class PathEndpoint(models.Model):
|
class PathEndpoint(models.Model):
|
||||||
"""
|
"""
|
||||||
@ -212,7 +226,7 @@ class ConsolePort(CableTermination, PathEndpoint, ComponentModel):
|
|||||||
)
|
)
|
||||||
tags = TaggableManager(through=TaggedItem)
|
tags = TaggableManager(through=TaggedItem)
|
||||||
|
|
||||||
csv_headers = ['device', 'name', 'label', 'type', 'description']
|
csv_headers = ['device', 'name', 'label', 'type', 'mark_connected', 'description']
|
||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
ordering = ('device', '_name')
|
ordering = ('device', '_name')
|
||||||
@ -227,6 +241,7 @@ class ConsolePort(CableTermination, PathEndpoint, ComponentModel):
|
|||||||
self.name,
|
self.name,
|
||||||
self.label,
|
self.label,
|
||||||
self.type,
|
self.type,
|
||||||
|
self.mark_connected,
|
||||||
self.description,
|
self.description,
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -248,7 +263,7 @@ class ConsoleServerPort(CableTermination, PathEndpoint, ComponentModel):
|
|||||||
)
|
)
|
||||||
tags = TaggableManager(through=TaggedItem)
|
tags = TaggableManager(through=TaggedItem)
|
||||||
|
|
||||||
csv_headers = ['device', 'name', 'label', 'type', 'description']
|
csv_headers = ['device', 'name', 'label', 'type', 'mark_connected', 'description']
|
||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
ordering = ('device', '_name')
|
ordering = ('device', '_name')
|
||||||
@ -263,6 +278,7 @@ class ConsoleServerPort(CableTermination, PathEndpoint, ComponentModel):
|
|||||||
self.name,
|
self.name,
|
||||||
self.label,
|
self.label,
|
||||||
self.type,
|
self.type,
|
||||||
|
self.mark_connected,
|
||||||
self.description,
|
self.description,
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -296,7 +312,9 @@ class PowerPort(CableTermination, PathEndpoint, ComponentModel):
|
|||||||
)
|
)
|
||||||
tags = TaggableManager(through=TaggedItem)
|
tags = TaggableManager(through=TaggedItem)
|
||||||
|
|
||||||
csv_headers = ['device', 'name', 'label', 'type', 'maximum_draw', 'allocated_draw', 'description']
|
csv_headers = [
|
||||||
|
'device', 'name', 'label', 'type', 'mark_connected', 'maximum_draw', 'allocated_draw', 'description',
|
||||||
|
]
|
||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
ordering = ('device', '_name')
|
ordering = ('device', '_name')
|
||||||
@ -311,6 +329,7 @@ class PowerPort(CableTermination, PathEndpoint, ComponentModel):
|
|||||||
self.name,
|
self.name,
|
||||||
self.label,
|
self.label,
|
||||||
self.get_type_display(),
|
self.get_type_display(),
|
||||||
|
self.mark_connected,
|
||||||
self.maximum_draw,
|
self.maximum_draw,
|
||||||
self.allocated_draw,
|
self.allocated_draw,
|
||||||
self.description,
|
self.description,
|
||||||
@ -406,7 +425,7 @@ class PowerOutlet(CableTermination, PathEndpoint, ComponentModel):
|
|||||||
)
|
)
|
||||||
tags = TaggableManager(through=TaggedItem)
|
tags = TaggableManager(through=TaggedItem)
|
||||||
|
|
||||||
csv_headers = ['device', 'name', 'label', 'type', 'power_port', 'feed_leg', 'description']
|
csv_headers = ['device', 'name', 'label', 'type', 'mark_connected', 'power_port', 'feed_leg', 'description']
|
||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
ordering = ('device', '_name')
|
ordering = ('device', '_name')
|
||||||
@ -421,6 +440,7 @@ class PowerOutlet(CableTermination, PathEndpoint, ComponentModel):
|
|||||||
self.name,
|
self.name,
|
||||||
self.label,
|
self.label,
|
||||||
self.get_type_display(),
|
self.get_type_display(),
|
||||||
|
self.mark_connected,
|
||||||
self.power_port.name if self.power_port else None,
|
self.power_port.name if self.power_port else None,
|
||||||
self.get_feed_leg_display(),
|
self.get_feed_leg_display(),
|
||||||
self.description,
|
self.description,
|
||||||
@ -532,7 +552,8 @@ class Interface(CableTermination, PathEndpoint, ComponentModel, BaseInterface):
|
|||||||
tags = TaggableManager(through=TaggedItem)
|
tags = TaggableManager(through=TaggedItem)
|
||||||
|
|
||||||
csv_headers = [
|
csv_headers = [
|
||||||
'device', 'name', 'label', 'lag', 'type', 'enabled', 'mac_address', 'mtu', 'mgmt_only', 'description', 'mode',
|
'device', 'name', 'label', 'lag', 'type', 'enabled', 'mark_connected', 'mac_address', 'mtu', 'mgmt_only',
|
||||||
|
'description', 'mode',
|
||||||
]
|
]
|
||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
@ -550,6 +571,7 @@ class Interface(CableTermination, PathEndpoint, ComponentModel, BaseInterface):
|
|||||||
self.lag.name if self.lag else None,
|
self.lag.name if self.lag else None,
|
||||||
self.get_type_display(),
|
self.get_type_display(),
|
||||||
self.enabled,
|
self.enabled,
|
||||||
|
self.mark_connected,
|
||||||
self.mac_address,
|
self.mac_address,
|
||||||
self.mtu,
|
self.mtu,
|
||||||
self.mgmt_only,
|
self.mgmt_only,
|
||||||
@ -648,7 +670,9 @@ class FrontPort(CableTermination, ComponentModel):
|
|||||||
)
|
)
|
||||||
tags = TaggableManager(through=TaggedItem)
|
tags = TaggableManager(through=TaggedItem)
|
||||||
|
|
||||||
csv_headers = ['device', 'name', 'label', 'type', 'rear_port', 'rear_port_position', 'description']
|
csv_headers = [
|
||||||
|
'device', 'name', 'label', 'type', 'mark_connected', 'rear_port', 'rear_port_position', 'description',
|
||||||
|
]
|
||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
ordering = ('device', '_name')
|
ordering = ('device', '_name')
|
||||||
@ -666,6 +690,7 @@ class FrontPort(CableTermination, ComponentModel):
|
|||||||
self.name,
|
self.name,
|
||||||
self.label,
|
self.label,
|
||||||
self.get_type_display(),
|
self.get_type_display(),
|
||||||
|
self.mark_connected,
|
||||||
self.rear_port.name,
|
self.rear_port.name,
|
||||||
self.rear_port_position,
|
self.rear_port_position,
|
||||||
self.description,
|
self.description,
|
||||||
@ -706,7 +731,7 @@ class RearPort(CableTermination, ComponentModel):
|
|||||||
)
|
)
|
||||||
tags = TaggableManager(through=TaggedItem)
|
tags = TaggableManager(through=TaggedItem)
|
||||||
|
|
||||||
csv_headers = ['device', 'name', 'label', 'type', 'positions', 'description']
|
csv_headers = ['device', 'name', 'label', 'type', 'mark_connected', 'positions', 'description']
|
||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
ordering = ('device', '_name')
|
ordering = ('device', '_name')
|
||||||
@ -732,6 +757,7 @@ class RearPort(CableTermination, ComponentModel):
|
|||||||
self.name,
|
self.name,
|
||||||
self.label,
|
self.label,
|
||||||
self.get_type_display(),
|
self.get_type_display(),
|
||||||
|
self.mark_connected,
|
||||||
self.positions,
|
self.positions,
|
||||||
self.description,
|
self.description,
|
||||||
)
|
)
|
||||||
|
@ -138,12 +138,12 @@ class PowerFeed(PrimaryModel, PathEndpoint, CableTermination):
|
|||||||
objects = RestrictedQuerySet.as_manager()
|
objects = RestrictedQuerySet.as_manager()
|
||||||
|
|
||||||
csv_headers = [
|
csv_headers = [
|
||||||
'site', 'power_panel', 'rack_group', 'rack', 'name', 'status', 'type', 'supply', 'phase', 'voltage',
|
'site', 'power_panel', 'rack_group', 'rack', 'name', 'status', 'type', 'mark_connected', 'supply', 'phase',
|
||||||
'amperage', 'max_utilization', 'comments',
|
'voltage', 'amperage', 'max_utilization', 'comments',
|
||||||
]
|
]
|
||||||
clone_fields = [
|
clone_fields = [
|
||||||
'power_panel', 'rack', 'status', 'type', 'supply', 'phase', 'voltage', 'amperage', 'max_utilization',
|
'power_panel', 'rack', 'status', 'type', 'mark_connected', 'supply', 'phase', 'voltage', 'amperage',
|
||||||
'available_power',
|
'max_utilization', 'available_power',
|
||||||
]
|
]
|
||||||
|
|
||||||
class Meta:
|
class Meta:
|
||||||
@ -165,6 +165,7 @@ class PowerFeed(PrimaryModel, PathEndpoint, CableTermination):
|
|||||||
self.name,
|
self.name,
|
||||||
self.get_status_display(),
|
self.get_status_display(),
|
||||||
self.get_type_display(),
|
self.get_type_display(),
|
||||||
|
self.mark_connected,
|
||||||
self.get_supply_display(),
|
self.get_supply_display(),
|
||||||
self.get_phase_display(),
|
self.get_phase_display(),
|
||||||
self.voltage,
|
self.voltage,
|
||||||
|
@ -213,6 +213,7 @@ class DeviceComponentTable(BaseTable):
|
|||||||
cable = tables.Column(
|
cable = tables.Column(
|
||||||
linkify=True
|
linkify=True
|
||||||
)
|
)
|
||||||
|
mark_connected = BooleanColumn()
|
||||||
|
|
||||||
class Meta(BaseTable.Meta):
|
class Meta(BaseTable.Meta):
|
||||||
order_by = ('device', 'name')
|
order_by = ('device', 'name')
|
||||||
@ -228,6 +229,7 @@ class CableTerminationTable(BaseTable):
|
|||||||
orderable=False,
|
orderable=False,
|
||||||
verbose_name='Cable Peer'
|
verbose_name='Cable Peer'
|
||||||
)
|
)
|
||||||
|
mark_connected = BooleanColumn()
|
||||||
|
|
||||||
|
|
||||||
class PathEndpointTable(CableTerminationTable):
|
class PathEndpointTable(CableTerminationTable):
|
||||||
@ -247,7 +249,8 @@ class ConsolePortTable(DeviceComponentTable, PathEndpointTable):
|
|||||||
class Meta(DeviceComponentTable.Meta):
|
class Meta(DeviceComponentTable.Meta):
|
||||||
model = ConsolePort
|
model = ConsolePort
|
||||||
fields = (
|
fields = (
|
||||||
'pk', 'device', 'name', 'label', 'type', 'description', 'cable', 'cable_peer', 'connection', 'tags',
|
'pk', 'device', 'name', 'label', 'type', 'description', 'mark_connected', 'cable', 'cable_peer',
|
||||||
|
'connection', 'tags',
|
||||||
)
|
)
|
||||||
default_columns = ('pk', 'device', 'name', 'label', 'type', 'description')
|
default_columns = ('pk', 'device', 'name', 'label', 'type', 'description')
|
||||||
|
|
||||||
@ -266,7 +269,8 @@ class DeviceConsolePortTable(ConsolePortTable):
|
|||||||
class Meta(DeviceComponentTable.Meta):
|
class Meta(DeviceComponentTable.Meta):
|
||||||
model = ConsolePort
|
model = ConsolePort
|
||||||
fields = (
|
fields = (
|
||||||
'pk', 'name', 'label', 'type', 'description', 'cable', 'cable_peer', 'connection', 'tags', 'actions'
|
'pk', 'name', 'label', 'type', 'description', 'mark_connected', 'cable', 'cable_peer', 'connection',
|
||||||
|
'tags', 'actions'
|
||||||
)
|
)
|
||||||
default_columns = ('pk', 'name', 'label', 'type', 'description', 'cable', 'connection', 'actions')
|
default_columns = ('pk', 'name', 'label', 'type', 'description', 'cable', 'connection', 'actions')
|
||||||
row_attrs = {
|
row_attrs = {
|
||||||
@ -281,7 +285,10 @@ class ConsoleServerPortTable(DeviceComponentTable, PathEndpointTable):
|
|||||||
|
|
||||||
class Meta(DeviceComponentTable.Meta):
|
class Meta(DeviceComponentTable.Meta):
|
||||||
model = ConsoleServerPort
|
model = ConsoleServerPort
|
||||||
fields = ('pk', 'device', 'name', 'label', 'type', 'description', 'cable', 'cable_peer', 'connection', 'tags')
|
fields = (
|
||||||
|
'pk', 'device', 'name', 'label', 'type', 'description', 'mark_connected', 'cable', 'cable_peer',
|
||||||
|
'connection', 'tags',
|
||||||
|
)
|
||||||
default_columns = ('pk', 'device', 'name', 'label', 'type', 'description')
|
default_columns = ('pk', 'device', 'name', 'label', 'type', 'description')
|
||||||
|
|
||||||
|
|
||||||
@ -300,7 +307,8 @@ class DeviceConsoleServerPortTable(ConsoleServerPortTable):
|
|||||||
class Meta(DeviceComponentTable.Meta):
|
class Meta(DeviceComponentTable.Meta):
|
||||||
model = ConsoleServerPort
|
model = ConsoleServerPort
|
||||||
fields = (
|
fields = (
|
||||||
'pk', 'name', 'label', 'type', 'description', 'cable', 'cable_peer', 'connection', 'tags', 'actions'
|
'pk', 'name', 'label', 'type', 'description', 'mark_connected', 'cable', 'cable_peer', 'connection', 'tags',
|
||||||
|
'actions',
|
||||||
)
|
)
|
||||||
default_columns = ('pk', 'name', 'label', 'type', 'description', 'cable', 'connection', 'actions')
|
default_columns = ('pk', 'name', 'label', 'type', 'description', 'cable', 'connection', 'actions')
|
||||||
row_attrs = {
|
row_attrs = {
|
||||||
@ -316,8 +324,8 @@ class PowerPortTable(DeviceComponentTable, PathEndpointTable):
|
|||||||
class Meta(DeviceComponentTable.Meta):
|
class Meta(DeviceComponentTable.Meta):
|
||||||
model = PowerPort
|
model = PowerPort
|
||||||
fields = (
|
fields = (
|
||||||
'pk', 'device', 'name', 'label', 'type', 'description', 'maximum_draw', 'allocated_draw', 'cable',
|
'pk', 'device', 'name', 'label', 'type', 'description', 'mark_connected', 'maximum_draw', 'allocated_draw',
|
||||||
'cable_peer', 'connection', 'tags',
|
'cable', 'cable_peer', 'connection', 'tags',
|
||||||
)
|
)
|
||||||
default_columns = ('pk', 'device', 'name', 'label', 'type', 'maximum_draw', 'allocated_draw', 'description')
|
default_columns = ('pk', 'device', 'name', 'label', 'type', 'maximum_draw', 'allocated_draw', 'description')
|
||||||
|
|
||||||
@ -337,8 +345,8 @@ class DevicePowerPortTable(PowerPortTable):
|
|||||||
class Meta(DeviceComponentTable.Meta):
|
class Meta(DeviceComponentTable.Meta):
|
||||||
model = PowerPort
|
model = PowerPort
|
||||||
fields = (
|
fields = (
|
||||||
'pk', 'name', 'label', 'type', 'maximum_draw', 'allocated_draw', 'description', 'cable', 'cable_peer',
|
'pk', 'name', 'label', 'type', 'maximum_draw', 'allocated_draw', 'description', 'mark_connected', 'cable',
|
||||||
'connection', 'tags', 'actions',
|
'cable_peer', 'connection', 'tags', 'actions',
|
||||||
)
|
)
|
||||||
default_columns = (
|
default_columns = (
|
||||||
'pk', 'name', 'label', 'type', 'maximum_draw', 'allocated_draw', 'description', 'cable', 'connection',
|
'pk', 'name', 'label', 'type', 'maximum_draw', 'allocated_draw', 'description', 'cable', 'connection',
|
||||||
@ -360,8 +368,8 @@ class PowerOutletTable(DeviceComponentTable, PathEndpointTable):
|
|||||||
class Meta(DeviceComponentTable.Meta):
|
class Meta(DeviceComponentTable.Meta):
|
||||||
model = PowerOutlet
|
model = PowerOutlet
|
||||||
fields = (
|
fields = (
|
||||||
'pk', 'device', 'name', 'label', 'type', 'description', 'power_port', 'feed_leg', 'cable', 'cable_peer',
|
'pk', 'device', 'name', 'label', 'type', 'description', 'power_port', 'feed_leg', 'mark_connected', 'cable',
|
||||||
'connection', 'tags',
|
'cable_peer', 'connection', 'tags',
|
||||||
)
|
)
|
||||||
default_columns = ('pk', 'device', 'name', 'label', 'type', 'power_port', 'feed_leg', 'description')
|
default_columns = ('pk', 'device', 'name', 'label', 'type', 'power_port', 'feed_leg', 'description')
|
||||||
|
|
||||||
@ -380,8 +388,8 @@ class DevicePowerOutletTable(PowerOutletTable):
|
|||||||
class Meta(DeviceComponentTable.Meta):
|
class Meta(DeviceComponentTable.Meta):
|
||||||
model = PowerOutlet
|
model = PowerOutlet
|
||||||
fields = (
|
fields = (
|
||||||
'pk', 'name', 'label', 'type', 'power_port', 'feed_leg', 'description', 'cable', 'cable_peer', 'connection',
|
'pk', 'name', 'label', 'type', 'power_port', 'feed_leg', 'description', 'mark_connected', 'cable',
|
||||||
'tags', 'actions',
|
'cable_peer', 'connection', 'tags', 'actions',
|
||||||
)
|
)
|
||||||
default_columns = (
|
default_columns = (
|
||||||
'pk', 'name', 'label', 'type', 'power_port', 'feed_leg', 'description', 'cable', 'connection', 'actions',
|
'pk', 'name', 'label', 'type', 'power_port', 'feed_leg', 'description', 'cable', 'connection', 'actions',
|
||||||
@ -416,7 +424,8 @@ class InterfaceTable(DeviceComponentTable, BaseInterfaceTable, PathEndpointTable
|
|||||||
model = Interface
|
model = Interface
|
||||||
fields = (
|
fields = (
|
||||||
'pk', 'device', 'name', 'label', 'enabled', 'type', 'mgmt_only', 'mtu', 'mode', 'mac_address',
|
'pk', 'device', 'name', 'label', 'enabled', 'type', 'mgmt_only', 'mtu', 'mode', 'mac_address',
|
||||||
'description', 'cable', 'cable_peer', 'connection', 'tags', 'ip_addresses', 'untagged_vlan', 'tagged_vlans',
|
'description', 'mark_connected', 'cable', 'cable_peer', 'connection', 'tags', 'ip_addresses',
|
||||||
|
'untagged_vlan', 'tagged_vlans',
|
||||||
)
|
)
|
||||||
default_columns = ('pk', 'device', 'name', 'label', 'enabled', 'type', 'description')
|
default_columns = ('pk', 'device', 'name', 'label', 'enabled', 'type', 'description')
|
||||||
|
|
||||||
@ -442,7 +451,8 @@ class DeviceInterfaceTable(InterfaceTable):
|
|||||||
model = Interface
|
model = Interface
|
||||||
fields = (
|
fields = (
|
||||||
'pk', 'name', 'label', 'enabled', 'type', 'lag', 'mgmt_only', 'mtu', 'mode', 'mac_address', 'description',
|
'pk', 'name', 'label', 'enabled', 'type', 'lag', 'mgmt_only', 'mtu', 'mode', 'mac_address', 'description',
|
||||||
'cable', 'cable_peer', 'connection', 'tags', 'ip_addresses', 'untagged_vlan', 'tagged_vlans', 'actions',
|
'mark_connected', 'cable', 'cable_peer', 'connection', 'tags', 'ip_addresses', 'untagged_vlan',
|
||||||
|
'tagged_vlans', 'actions',
|
||||||
)
|
)
|
||||||
default_columns = (
|
default_columns = (
|
||||||
'pk', 'name', 'label', 'enabled', 'type', 'lag', 'mtu', 'mode', 'description', 'ip_addresses', 'cable',
|
'pk', 'name', 'label', 'enabled', 'type', 'lag', 'mtu', 'mode', 'description', 'ip_addresses', 'cable',
|
||||||
@ -468,8 +478,8 @@ class FrontPortTable(DeviceComponentTable, CableTerminationTable):
|
|||||||
class Meta(DeviceComponentTable.Meta):
|
class Meta(DeviceComponentTable.Meta):
|
||||||
model = FrontPort
|
model = FrontPort
|
||||||
fields = (
|
fields = (
|
||||||
'pk', 'device', 'name', 'label', 'type', 'rear_port', 'rear_port_position', 'description', 'cable',
|
'pk', 'device', 'name', 'label', 'type', 'rear_port', 'rear_port_position', 'description', 'mark_connected',
|
||||||
'cable_peer', 'tags',
|
'cable', 'cable_peer', 'tags',
|
||||||
)
|
)
|
||||||
default_columns = ('pk', 'device', 'name', 'label', 'type', 'rear_port', 'rear_port_position', 'description')
|
default_columns = ('pk', 'device', 'name', 'label', 'type', 'rear_port', 'rear_port_position', 'description')
|
||||||
|
|
||||||
@ -489,8 +499,8 @@ class DeviceFrontPortTable(FrontPortTable):
|
|||||||
class Meta(DeviceComponentTable.Meta):
|
class Meta(DeviceComponentTable.Meta):
|
||||||
model = FrontPort
|
model = FrontPort
|
||||||
fields = (
|
fields = (
|
||||||
'pk', 'name', 'label', 'type', 'rear_port', 'rear_port_position', 'description', 'cable', 'cable_peer',
|
'pk', 'name', 'label', 'type', 'rear_port', 'rear_port_position', 'description', 'mark_connected', 'cable',
|
||||||
'tags', 'actions',
|
'cable_peer', 'tags', 'actions',
|
||||||
)
|
)
|
||||||
default_columns = (
|
default_columns = (
|
||||||
'pk', 'name', 'label', 'type', 'rear_port', 'rear_port_position', 'description', 'cable', 'cable_peer',
|
'pk', 'name', 'label', 'type', 'rear_port', 'rear_port_position', 'description', 'cable', 'cable_peer',
|
||||||
@ -508,7 +518,10 @@ class RearPortTable(DeviceComponentTable, CableTerminationTable):
|
|||||||
|
|
||||||
class Meta(DeviceComponentTable.Meta):
|
class Meta(DeviceComponentTable.Meta):
|
||||||
model = RearPort
|
model = RearPort
|
||||||
fields = ('pk', 'device', 'name', 'label', 'type', 'positions', 'description', 'cable', 'cable_peer', 'tags')
|
fields = (
|
||||||
|
'pk', 'device', 'name', 'label', 'type', 'positions', 'description', 'mark_connected', 'cable',
|
||||||
|
'cable_peer', 'tags',
|
||||||
|
)
|
||||||
default_columns = ('pk', 'device', 'name', 'label', 'type', 'description')
|
default_columns = ('pk', 'device', 'name', 'label', 'type', 'description')
|
||||||
|
|
||||||
|
|
||||||
@ -527,7 +540,8 @@ class DeviceRearPortTable(RearPortTable):
|
|||||||
class Meta(DeviceComponentTable.Meta):
|
class Meta(DeviceComponentTable.Meta):
|
||||||
model = RearPort
|
model = RearPort
|
||||||
fields = (
|
fields = (
|
||||||
'pk', 'name', 'label', 'type', 'positions', 'description', 'cable', 'cable_peer', 'tags', 'actions',
|
'pk', 'name', 'label', 'type', 'positions', 'description', 'mark_connected', 'cable', 'cable_peer', 'tags',
|
||||||
|
'actions',
|
||||||
)
|
)
|
||||||
default_columns = (
|
default_columns = (
|
||||||
'pk', 'name', 'label', 'type', 'positions', 'description', 'cable', 'cable_peer', 'actions',
|
'pk', 'name', 'label', 'type', 'positions', 'description', 'cable', 'cable_peer', 'actions',
|
||||||
|
@ -68,7 +68,7 @@ class PowerFeedTable(CableTerminationTable):
|
|||||||
model = PowerFeed
|
model = PowerFeed
|
||||||
fields = (
|
fields = (
|
||||||
'pk', 'name', 'power_panel', 'rack', 'status', 'type', 'supply', 'voltage', 'amperage', 'phase',
|
'pk', 'name', 'power_panel', 'rack', 'status', 'type', 'supply', 'voltage', 'amperage', 'phase',
|
||||||
'max_utilization', 'cable', 'cable_peer', 'connection', 'available_power', 'tags',
|
'max_utilization', 'mark_connected', 'cable', 'cable_peer', 'connection', 'available_power', 'tags',
|
||||||
)
|
)
|
||||||
default_columns = (
|
default_columns = (
|
||||||
'pk', 'name', 'power_panel', 'rack', 'status', 'type', 'supply', 'voltage', 'amperage', 'phase', 'cable',
|
'pk', 'name', 'power_panel', 'rack', 'status', 'type', 'supply', 'voltage', 'amperage', 'phase', 'cable',
|
||||||
|
@ -979,7 +979,7 @@ class DeviceTest(APIViewTestCases.APIViewTestCase):
|
|||||||
|
|
||||||
class ConsolePortTest(Mixins.ComponentTraceMixin, APIViewTestCases.APIViewTestCase):
|
class ConsolePortTest(Mixins.ComponentTraceMixin, APIViewTestCases.APIViewTestCase):
|
||||||
model = ConsolePort
|
model = ConsolePort
|
||||||
brief_fields = ['cable', 'device', 'id', 'name', 'url']
|
brief_fields = ['_occupied', 'cable', 'device', 'id', 'name', 'url']
|
||||||
bulk_update_data = {
|
bulk_update_data = {
|
||||||
'description': 'New description',
|
'description': 'New description',
|
||||||
}
|
}
|
||||||
@ -1018,7 +1018,7 @@ class ConsolePortTest(Mixins.ComponentTraceMixin, APIViewTestCases.APIViewTestCa
|
|||||||
|
|
||||||
class ConsoleServerPortTest(Mixins.ComponentTraceMixin, APIViewTestCases.APIViewTestCase):
|
class ConsoleServerPortTest(Mixins.ComponentTraceMixin, APIViewTestCases.APIViewTestCase):
|
||||||
model = ConsoleServerPort
|
model = ConsoleServerPort
|
||||||
brief_fields = ['cable', 'device', 'id', 'name', 'url']
|
brief_fields = ['_occupied', 'cable', 'device', 'id', 'name', 'url']
|
||||||
bulk_update_data = {
|
bulk_update_data = {
|
||||||
'description': 'New description',
|
'description': 'New description',
|
||||||
}
|
}
|
||||||
@ -1057,7 +1057,7 @@ class ConsoleServerPortTest(Mixins.ComponentTraceMixin, APIViewTestCases.APIView
|
|||||||
|
|
||||||
class PowerPortTest(Mixins.ComponentTraceMixin, APIViewTestCases.APIViewTestCase):
|
class PowerPortTest(Mixins.ComponentTraceMixin, APIViewTestCases.APIViewTestCase):
|
||||||
model = PowerPort
|
model = PowerPort
|
||||||
brief_fields = ['cable', 'device', 'id', 'name', 'url']
|
brief_fields = ['_occupied', 'cable', 'device', 'id', 'name', 'url']
|
||||||
bulk_update_data = {
|
bulk_update_data = {
|
||||||
'description': 'New description',
|
'description': 'New description',
|
||||||
}
|
}
|
||||||
@ -1096,7 +1096,7 @@ class PowerPortTest(Mixins.ComponentTraceMixin, APIViewTestCases.APIViewTestCase
|
|||||||
|
|
||||||
class PowerOutletTest(Mixins.ComponentTraceMixin, APIViewTestCases.APIViewTestCase):
|
class PowerOutletTest(Mixins.ComponentTraceMixin, APIViewTestCases.APIViewTestCase):
|
||||||
model = PowerOutlet
|
model = PowerOutlet
|
||||||
brief_fields = ['cable', 'device', 'id', 'name', 'url']
|
brief_fields = ['_occupied', 'cable', 'device', 'id', 'name', 'url']
|
||||||
bulk_update_data = {
|
bulk_update_data = {
|
||||||
'description': 'New description',
|
'description': 'New description',
|
||||||
}
|
}
|
||||||
@ -1135,7 +1135,7 @@ class PowerOutletTest(Mixins.ComponentTraceMixin, APIViewTestCases.APIViewTestCa
|
|||||||
|
|
||||||
class InterfaceTest(Mixins.ComponentTraceMixin, APIViewTestCases.APIViewTestCase):
|
class InterfaceTest(Mixins.ComponentTraceMixin, APIViewTestCases.APIViewTestCase):
|
||||||
model = Interface
|
model = Interface
|
||||||
brief_fields = ['cable', 'device', 'id', 'name', 'url']
|
brief_fields = ['_occupied', 'cable', 'device', 'id', 'name', 'url']
|
||||||
bulk_update_data = {
|
bulk_update_data = {
|
||||||
'description': 'New description',
|
'description': 'New description',
|
||||||
}
|
}
|
||||||
@ -1193,7 +1193,7 @@ class InterfaceTest(Mixins.ComponentTraceMixin, APIViewTestCases.APIViewTestCase
|
|||||||
|
|
||||||
class FrontPortTest(APIViewTestCases.APIViewTestCase):
|
class FrontPortTest(APIViewTestCases.APIViewTestCase):
|
||||||
model = FrontPort
|
model = FrontPort
|
||||||
brief_fields = ['cable', 'device', 'id', 'name', 'url']
|
brief_fields = ['_occupied', 'cable', 'device', 'id', 'name', 'url']
|
||||||
bulk_update_data = {
|
bulk_update_data = {
|
||||||
'description': 'New description',
|
'description': 'New description',
|
||||||
}
|
}
|
||||||
@ -1251,7 +1251,7 @@ class FrontPortTest(APIViewTestCases.APIViewTestCase):
|
|||||||
|
|
||||||
class RearPortTest(APIViewTestCases.APIViewTestCase):
|
class RearPortTest(APIViewTestCases.APIViewTestCase):
|
||||||
model = RearPort
|
model = RearPort
|
||||||
brief_fields = ['cable', 'device', 'id', 'name', 'url']
|
brief_fields = ['_occupied', 'cable', 'device', 'id', 'name', 'url']
|
||||||
bulk_update_data = {
|
bulk_update_data = {
|
||||||
'description': 'New description',
|
'description': 'New description',
|
||||||
}
|
}
|
||||||
@ -1628,7 +1628,7 @@ class PowerPanelTest(APIViewTestCases.APIViewTestCase):
|
|||||||
|
|
||||||
class PowerFeedTest(APIViewTestCases.APIViewTestCase):
|
class PowerFeedTest(APIViewTestCases.APIViewTestCase):
|
||||||
model = PowerFeed
|
model = PowerFeed
|
||||||
brief_fields = ['cable', 'id', 'name', 'url']
|
brief_fields = ['_occupied', 'cable', 'id', 'name', 'url']
|
||||||
bulk_update_data = {
|
bulk_update_data = {
|
||||||
'status': 'planned',
|
'status': 'planned',
|
||||||
}
|
}
|
||||||
|
@ -28,6 +28,7 @@
|
|||||||
</div>
|
</div>
|
||||||
{% render_field form.region %}
|
{% render_field form.region %}
|
||||||
{% render_field form.site %}
|
{% render_field form.site %}
|
||||||
|
{% render_field form.mark_connected %}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="panel panel-default">
|
<div class="panel panel-default">
|
||||||
|
@ -38,7 +38,10 @@
|
|||||||
<tr>
|
<tr>
|
||||||
<td>Termination</td>
|
<td>Termination</td>
|
||||||
<td>
|
<td>
|
||||||
{% if termination.cable %}
|
{% if termination.mark_connected %}
|
||||||
|
<span class="text-success"><i class="mdi mdi-check-bold"></i></span>
|
||||||
|
<span class="text-muted">Marked as connected</span>
|
||||||
|
{% elif termination.cable %}
|
||||||
{% if perms.dcim.delete_cable %}
|
{% if perms.dcim.delete_cable %}
|
||||||
<div class="pull-right">
|
<div class="pull-right">
|
||||||
<a href="{% url 'dcim:cable_delete' pk=termination.cable.pk %}?return_url={{ termination.circuit.get_absolute_url }}" title="Remove cable" class="btn btn-danger btn-xs">
|
<a href="{% url 'dcim:cable_delete' pk=termination.cable.pk %}?return_url={{ termination.circuit.get_absolute_url }}" title="Remove cable" class="btn btn-danger btn-xs">
|
||||||
|
@ -43,7 +43,11 @@
|
|||||||
<div class="panel-heading">
|
<div class="panel-heading">
|
||||||
<strong>Connection</strong>
|
<strong>Connection</strong>
|
||||||
</div>
|
</div>
|
||||||
{% if object.cable %}
|
{% if object.mark_connected %}
|
||||||
|
<div class="panel-body text-muted">
|
||||||
|
<span class="text-success"><i class="mdi mdi-check-bold"></i></span> Marked as connected
|
||||||
|
</div>
|
||||||
|
{% elif object.cable %}
|
||||||
<table class="table table-hover panel-body attr-table">
|
<table class="table table-hover panel-body attr-table">
|
||||||
<tr>
|
<tr>
|
||||||
<td>Cable</td>
|
<td>Cable</td>
|
||||||
|
@ -43,7 +43,11 @@
|
|||||||
<div class="panel-heading">
|
<div class="panel-heading">
|
||||||
<strong>Connection</strong>
|
<strong>Connection</strong>
|
||||||
</div>
|
</div>
|
||||||
{% if object.cable %}
|
{% if object.mark_connected %}
|
||||||
|
<div class="panel-body text-muted">
|
||||||
|
<span class="text-success"><i class="mdi mdi-check-bold"></i></span> Marked as connected
|
||||||
|
</div>
|
||||||
|
{% elif object.cable %}
|
||||||
<table class="table table-hover panel-body attr-table">
|
<table class="table table-hover panel-body attr-table">
|
||||||
<tr>
|
<tr>
|
||||||
<td>Cable</td>
|
<td>Cable</td>
|
||||||
|
@ -53,7 +53,11 @@
|
|||||||
<div class="panel-heading">
|
<div class="panel-heading">
|
||||||
<strong>Connection</strong>
|
<strong>Connection</strong>
|
||||||
</div>
|
</div>
|
||||||
{% if object.cable %}
|
{% if object.mark_connected %}
|
||||||
|
<div class="panel-body text-muted">
|
||||||
|
<span class="text-success"><i class="mdi mdi-check-bold"></i></span> Marked as connected
|
||||||
|
</div>
|
||||||
|
{% elif object.cable %}
|
||||||
<table class="table table-hover panel-body attr-table">
|
<table class="table table-hover panel-body attr-table">
|
||||||
<tr>
|
<tr>
|
||||||
<td>Cable</td>
|
<td>Cable</td>
|
||||||
|
@ -76,7 +76,11 @@
|
|||||||
<div class="panel-heading">
|
<div class="panel-heading">
|
||||||
<strong>Connection</strong>
|
<strong>Connection</strong>
|
||||||
</div>
|
</div>
|
||||||
{% if object.cable %}
|
{% if object.mark_connected %}
|
||||||
|
<div class="panel-body text-muted">
|
||||||
|
<span class="text-success"><i class="mdi mdi-check-bold"></i></span> Marked as connected
|
||||||
|
</div>
|
||||||
|
{% elif object.cable %}
|
||||||
<table class="table table-hover panel-body attr-table">
|
<table class="table table-hover panel-body attr-table">
|
||||||
<tr>
|
<tr>
|
||||||
<td>Cable</td>
|
<td>Cable</td>
|
||||||
|
@ -23,6 +23,7 @@
|
|||||||
{% render_field form.mac_address %}
|
{% render_field form.mac_address %}
|
||||||
{% render_field form.mtu %}
|
{% render_field form.mtu %}
|
||||||
{% render_field form.mgmt_only %}
|
{% render_field form.mgmt_only %}
|
||||||
|
{% render_field form.mark_connected %}
|
||||||
{% render_field form.description %}
|
{% render_field form.description %}
|
||||||
{% render_field form.tags %}
|
{% render_field form.tags %}
|
||||||
</div>
|
</div>
|
||||||
@ -35,12 +36,14 @@
|
|||||||
{% render_field form.tagged_vlans %}
|
{% render_field form.tagged_vlans %}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
{% if form.custom_fields %}
|
||||||
<div class="panel panel-default">
|
<div class="panel panel-default">
|
||||||
<div class="panel-heading"><strong>Custom Fields</strong></div>
|
<div class="panel-heading"><strong>Custom Fields</strong></div>
|
||||||
<div class="panel-body">
|
<div class="panel-body">
|
||||||
{% render_custom_fields form %}
|
{% render_custom_fields form %}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
{% endif %}
|
||||||
{% endblock %}
|
{% endblock %}
|
||||||
|
|
||||||
{% block buttons %}
|
{% block buttons %}
|
||||||
|
@ -159,7 +159,11 @@
|
|||||||
<div class="panel-heading">
|
<div class="panel-heading">
|
||||||
<strong>Connection</strong>
|
<strong>Connection</strong>
|
||||||
</div>
|
</div>
|
||||||
{% if object.cable %}
|
{% if object.mark_connected %}
|
||||||
|
<div class="panel-body text-muted">
|
||||||
|
<span class="text-success"><i class="mdi mdi-check-bold"></i></span> Marked as connected
|
||||||
|
</div>
|
||||||
|
{% elif object.cable %}
|
||||||
<table class="table table-hover panel-body attr-table">
|
<table class="table table-hover panel-body attr-table">
|
||||||
<tr>
|
<tr>
|
||||||
<td>Cable</td>
|
<td>Cable</td>
|
||||||
|
@ -51,7 +51,11 @@
|
|||||||
<div class="panel-heading">
|
<div class="panel-heading">
|
||||||
<strong>Connection</strong>
|
<strong>Connection</strong>
|
||||||
</div>
|
</div>
|
||||||
{% if object.cable %}
|
{% if object.mark_connected %}
|
||||||
|
<div class="panel-body text-muted">
|
||||||
|
<span class="text-success"><i class="mdi mdi-check-bold"></i></span> Marked as connected
|
||||||
|
</div>
|
||||||
|
{% elif object.cable %}
|
||||||
<table class="table table-hover panel-body attr-table">
|
<table class="table table-hover panel-body attr-table">
|
||||||
<tr>
|
<tr>
|
||||||
<td>Cable</td>
|
<td>Cable</td>
|
||||||
|
@ -51,7 +51,11 @@
|
|||||||
<div class="panel-heading">
|
<div class="panel-heading">
|
||||||
<strong>Connection</strong>
|
<strong>Connection</strong>
|
||||||
</div>
|
</div>
|
||||||
{% if object.cable %}
|
{% if object.mark_connected %}
|
||||||
|
<div class="panel-body text-muted">
|
||||||
|
<span class="text-success"><i class="mdi mdi-check-bold"></i></span> Marked as connected
|
||||||
|
</div>
|
||||||
|
{% elif object.cable %}
|
||||||
<table class="table table-hover panel-body attr-table">
|
<table class="table table-hover panel-body attr-table">
|
||||||
<tr>
|
<tr>
|
||||||
<td>Cable</td>
|
<td>Cable</td>
|
||||||
|
@ -47,7 +47,11 @@
|
|||||||
<div class="panel-heading">
|
<div class="panel-heading">
|
||||||
<strong>Connection</strong>
|
<strong>Connection</strong>
|
||||||
</div>
|
</div>
|
||||||
{% if object.cable %}
|
{% if object.mark_connected %}
|
||||||
|
<div class="panel-body text-muted">
|
||||||
|
<span class="text-success"><i class="mdi mdi-check-bold"></i></span> Marked as connected
|
||||||
|
</div>
|
||||||
|
{% elif object.cable %}
|
||||||
<table class="table table-hover panel-body attr-table">
|
<table class="table table-hover panel-body attr-table">
|
||||||
<tr>
|
<tr>
|
||||||
<td>Cable</td>
|
<td>Cable</td>
|
||||||
|
Loading…
Reference in New Issue
Block a user