Getting traceback because code doesn't check whether there are any elements of fixed_ips before trying to return the first fixed IP for the 'first' port of a router.
Given a router such as:
jujumanage@maas-tele2-vno1:~$ openstack port list --router 7334420e-5c27-4eb2-babd-eccc564a391b
+--------------------------------------+------+-------------------+---------------------------------------------------------------------------+--------+
| ID | Name | MAC Address | Fixed IP Addresses | Status |
+--------------------------------------+------+-------------------+---------------------------------------------------------------------------+--------+
| 287d6b20-7b95-403b-9357-4200eb3f8242 | | fa:16:3e:44:a4:a6 | | DOWN |
| 3ba11b13-5df5-4f4e-a5a3-d96b043ae0c5 | | fa:16:3e:44:17:26 | ip_address='10.81.13.9', subnet_id='9a8d4077-c9d4-4316-bc62-b3ff6b037a9b' | ACTIVE |
| 3fa1ad4b-84d2-4e44-b27d-84b2c7b2166c | | fa:16:3e:16:88:4d | ip_address='10.81.13.1', subnet_id='e5cbcb81-84f3-49fd-b4d4-64f10542419b' | ACTIVE |
+--------------------------------------+------+-------------------+---------------------------------------------------------------------------+--------+
We see the prometheus-openstack-exporter metrics provides a 500 error with this traceback (found with strace -f -s 9999 -p :
[pid 4893] sendto(13, "Traceback (most recent call last):
File \"/snap/prometheus-openstack-exporter/25/bin/prometheus-openstack-exporter\", line 615, in do_GET
swift.get_stats() + \
File \"/snap/prometheus-openstack-exporter/25/bin/prometheus-openstack-exporter\", line 289, in get_stats
ips.update(self.get_router_ips())
File \"/snap/prometheus-openstack-exporter/25/bin/prometheus-openstack-exporter\", line 254, in get_router_ips
if self._get_router_ip(r[id]):
File \"/snap/prometheus-openstack-exporter/25/bin/prometheus-openstack-exporter\", line 234, in _get_router_ip
return port[\"fixed_ips\"][0][\"ip_address\"]
IndexError: list index out of range
It appears that one should also exclude "DOWN" ports, and make a sanity check that there is any length of the port["fixed_ips"] before iterating it.
Getting traceback because code doesn't check whether there are any elements of fixed_ips before trying to return the first fixed IP for the 'first' port of a router.
Given a router such as:
jujumanage@maas-tele2-vno1:~$ openstack port list --router 7334420e-5c27-4eb2-babd-eccc564a391b +--------------------------------------+------+-------------------+---------------------------------------------------------------------------+--------+ | ID | Name | MAC Address | Fixed IP Addresses | Status | +--------------------------------------+------+-------------------+---------------------------------------------------------------------------+--------+ | 287d6b20-7b95-403b-9357-4200eb3f8242 | | fa:16:3e:44:a4:a6 | | DOWN | | 3ba11b13-5df5-4f4e-a5a3-d96b043ae0c5 | | fa:16:3e:44:17:26 | ip_address='10.81.13.9', subnet_id='9a8d4077-c9d4-4316-bc62-b3ff6b037a9b' | ACTIVE | | 3fa1ad4b-84d2-4e44-b27d-84b2c7b2166c | | fa:16:3e:16:88:4d | ip_address='10.81.13.1', subnet_id='e5cbcb81-84f3-49fd-b4d4-64f10542419b' | ACTIVE | +--------------------------------------+------+-------------------+---------------------------------------------------------------------------+--------+
We see the prometheus-openstack-exporter metrics provides a 500 error with this traceback (found with strace -f -s 9999 -p:
[pid 4893] sendto(13, "Traceback (most recent call last): File \"/snap/prometheus-openstack-exporter/25/bin/prometheus-openstack-exporter\", line 615, in do_GET swift.get_stats() + \ File \"/snap/prometheus-openstack-exporter/25/bin/prometheus-openstack-exporter\", line 289, in get_stats ips.update(self.get_router_ips()) File \"/snap/prometheus-openstack-exporter/25/bin/prometheus-openstack-exporter\", line 254, in get_router_ips if self._get_router_ip(r[id]): File \"/snap/prometheus-openstack-exporter/25/bin/prometheus-openstack-exporter\", line 234, in _get_router_ip return port[\"fixed_ips\"][0][\"ip_address\"] IndexError: list index out of range
It appears that one should also exclude "DOWN" ports, and make a sanity check that there is any length of the port["fixed_ips"] before iterating it.