Fixes #1047: Correct ordering of numbered subinterfaces

This commit is contained in:
Jeremy Stretch 2017-04-06 15:13:20 -04:00
parent f3eee25527
commit 1dd2bdcb8e

View File

@ -781,9 +781,9 @@ class InterfaceManager(models.Manager):
IFACE_ORDERING_CHOICES (typically indicated by a parent Device's DeviceType). IFACE_ORDERING_CHOICES (typically indicated by a parent Device's DeviceType).
To order interfaces naturally, the `name` field is split into five distinct components: leading text (name), To order interfaces naturally, the `name` field is split into five distinct components: leading text (name),
slot, subslot, position, and channel: slot, subslot, position, channel, and virtual circuit:
{name}{slot}/{subslot}/{position}:{channel} {name}{slot}/{subslot}/{position}:{channel}.{vc}
Components absent from the interface name are ignored. For example, an interface named GigabitEthernet0/1 would Components absent from the interface name are ignored. For example, an interface named GigabitEthernet0/1 would
be parsed as follows: be parsed as follows:
@ -793,21 +793,23 @@ class InterfaceManager(models.Manager):
subslot = 0 subslot = 0
position = 1 position = 1
channel = None channel = None
vc = 0
The chosen sorting method will determine which fields are ordered first in the query. The chosen sorting method will determine which fields are ordered first in the query.
""" """
queryset = self.get_queryset() queryset = self.get_queryset()
sql_col = '{}.name'.format(queryset.model._meta.db_table) sql_col = '{}.name'.format(queryset.model._meta.db_table)
ordering = { ordering = {
IFACE_ORDERING_POSITION: ('_slot', '_subslot', '_position', '_channel', '_name'), IFACE_ORDERING_POSITION: ('_slot', '_subslot', '_position', '_channel', '_vc', '_name'),
IFACE_ORDERING_NAME: ('_name', '_slot', '_subslot', '_position', '_channel'), IFACE_ORDERING_NAME: ('_name', '_slot', '_subslot', '_position', '_channel', '_vc'),
}[method] }[method]
return queryset.extra(select={ return queryset.extra(select={
'_name': "SUBSTRING({} FROM '^([^0-9]+)')".format(sql_col), '_name': "SUBSTRING({} FROM '^([^0-9]+)')".format(sql_col),
'_slot': "CAST(SUBSTRING({} FROM '([0-9]+)\/[0-9]+\/[0-9]+(:[0-9]+)?$') AS integer)".format(sql_col), '_slot': "CAST(SUBSTRING({} FROM '([0-9]+)\/[0-9]+\/[0-9]+(:[0-9]+)?(\.[0-9]+)?$') AS integer)".format(sql_col),
'_subslot': "CAST(SUBSTRING({} FROM '([0-9]+)\/[0-9]+(:[0-9]+)?$') AS integer)".format(sql_col), '_subslot': "CAST(SUBSTRING({} FROM '([0-9]+)\/[0-9]+(:[0-9]+)?(\.[0-9]+)?$') AS integer)".format(sql_col),
'_position': "CAST(SUBSTRING({} FROM '([0-9]+)(:[0-9]+)?$') AS integer)".format(sql_col), '_position': "CAST(SUBSTRING({} FROM '([0-9]+)(:[0-9]+)?(\.[0-9]+)?$') AS integer)".format(sql_col),
'_channel': "CAST(SUBSTRING({} FROM ':([0-9]+)$') AS integer)".format(sql_col), '_channel': "COALESCE(CAST(SUBSTRING({} FROM ':([0-9]+)(\.[0-9]+)?$') AS integer), 0)".format(sql_col),
'_vc': "COALESCE(CAST(SUBSTRING({} FROM '\.([0-9]+)$') AS integer), 0)".format(sql_col),
}).order_by(*ordering) }).order_by(*ordering)