)]}'
{"nova/network/neutronv2/api.py":[{"author":{"_account_id":15334,"name":"Stephen Finucane","display_name":"stephenfin","email":"stephenfin@redhat.com","username":"sfinucan"},"change_message_id":"b395614ca5f47180689d997c3d75ae6f73d60d6f","unresolved":false,"context_lines":[{"line_number":1399,"context_line":"            raise exception.PortBindingActivationFailed("},{"line_number":1400,"context_line":"                port_id\u003dport_id, host\u003dhost)"},{"line_number":1401,"context_line":""},{"line_number":1402,"context_line":"    @staticmethod"},{"line_number":1403,"context_line":"    def _activate_port_binding(context, client, port_id, host):"},{"line_number":1404,"context_line":"        \"\"\"Activates an inactive port binding."},{"line_number":1405,"context_line":""},{"line_number":1406,"context_line":"        :param context: The request context for the operation."},{"line_number":1407,"context_line":"        :param client: keystoneauth1.adapter.Adapter"},{"line_number":1408,"context_line":"        :param port_id: ID of the port to activate the a binding on"},{"line_number":1409,"context_line":"        :param host: A string name of the host identifying the binding to be"},{"line_number":1410,"context_line":"            activated"},{"line_number":1411,"context_line":"        :return: requests.Response object"},{"line_number":1412,"context_line":"        \"\"\""},{"line_number":1413,"context_line":"        return client.put("},{"line_number":1414,"context_line":"            \u0027/v2.0/ports/%s/bindings/%s/activate\u0027 % (port_id, host),"},{"line_number":1415,"context_line":"            raise_exc\u003dFalse,"},{"line_number":1416,"context_line":"            global_request_id\u003dcontext.global_id)"},{"line_number":1417,"context_line":""},{"line_number":1418,"context_line":"    @staticmethod"},{"line_number":1419,"context_line":"    def _get_port_binding(context, client, port_id, host):"},{"line_number":1420,"context_line":"        \"\"\"Returns a port binding of a given port on a given host"},{"line_number":1421,"context_line":""},{"line_number":1422,"context_line":"        :param context: The request context for the operation."},{"line_number":1423,"context_line":"        :param client: keystoneauth1.adapter.Adapter"},{"line_number":1424,"context_line":"        :param port_id: ID of the port to get the binding"},{"line_number":1425,"context_line":"        :param host: A string name of the host identifying the binding to be"},{"line_number":1426,"context_line":"            returned"},{"line_number":1427,"context_line":"        :return: requests.Response object"},{"line_number":1428,"context_line":"        \"\"\""},{"line_number":1429,"context_line":"        return client.get("},{"line_number":1430,"context_line":"            \u0027/v2.0/ports/%s/bindings/%s\u0027 % (port_id, host),"},{"line_number":1431,"context_line":"            raise_exc\u003dFalse,"},{"line_number":1432,"context_line":"            global_request_id\u003dcontext.global_id)"},{"line_number":1433,"context_line":""},{"line_number":1434,"context_line":"    def _get_pci_device_profile(self, pci_dev):"},{"line_number":1435,"context_line":"        dev_spec \u003d self.pci_whitelist.get_devspec(pci_dev)"}],"source_content_type":"text/x-python","patch_set":4,"id":"3fa7e38b_c11af716","line":1432,"range":{"start_line":1402,"start_character":0,"end_line":1432,"end_character":48},"updated":"2019-11-29 15:37:09.000000000","message":"It\u0027d be great if we could subclass the client returned from \u0027_get_ksa_client\u0027 and put these in there. Alas, I\u0027m not sure how much work this is","commit_id":"956e958a0351aab19b4b089ae4dec82e6d31d28e"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"06312da69b9c9c4588cf80b142d4177f92e23df9","unresolved":false,"context_lines":[{"line_number":1399,"context_line":"            raise exception.PortBindingActivationFailed("},{"line_number":1400,"context_line":"                port_id\u003dport_id, host\u003dhost)"},{"line_number":1401,"context_line":""},{"line_number":1402,"context_line":"    @staticmethod"},{"line_number":1403,"context_line":"    def _activate_port_binding(context, client, port_id, host):"},{"line_number":1404,"context_line":"        \"\"\"Activates an inactive port binding."},{"line_number":1405,"context_line":""},{"line_number":1406,"context_line":"        :param context: The request context for the operation."},{"line_number":1407,"context_line":"        :param client: keystoneauth1.adapter.Adapter"},{"line_number":1408,"context_line":"        :param port_id: ID of the port to activate the a binding on"},{"line_number":1409,"context_line":"        :param host: A string name of the host identifying the binding to be"},{"line_number":1410,"context_line":"            activated"},{"line_number":1411,"context_line":"        :return: requests.Response object"},{"line_number":1412,"context_line":"        \"\"\""},{"line_number":1413,"context_line":"        return client.put("},{"line_number":1414,"context_line":"            \u0027/v2.0/ports/%s/bindings/%s/activate\u0027 % (port_id, host),"},{"line_number":1415,"context_line":"            raise_exc\u003dFalse,"},{"line_number":1416,"context_line":"            global_request_id\u003dcontext.global_id)"},{"line_number":1417,"context_line":""},{"line_number":1418,"context_line":"    @staticmethod"},{"line_number":1419,"context_line":"    def _get_port_binding(context, client, port_id, host):"},{"line_number":1420,"context_line":"        \"\"\"Returns a port binding of a given port on a given host"},{"line_number":1421,"context_line":""},{"line_number":1422,"context_line":"        :param context: The request context for the operation."},{"line_number":1423,"context_line":"        :param client: keystoneauth1.adapter.Adapter"},{"line_number":1424,"context_line":"        :param port_id: ID of the port to get the binding"},{"line_number":1425,"context_line":"        :param host: A string name of the host identifying the binding to be"},{"line_number":1426,"context_line":"            returned"},{"line_number":1427,"context_line":"        :return: requests.Response object"},{"line_number":1428,"context_line":"        \"\"\""},{"line_number":1429,"context_line":"        return client.get("},{"line_number":1430,"context_line":"            \u0027/v2.0/ports/%s/bindings/%s\u0027 % (port_id, host),"},{"line_number":1431,"context_line":"            raise_exc\u003dFalse,"},{"line_number":1432,"context_line":"            global_request_id\u003dcontext.global_id)"},{"line_number":1433,"context_line":""},{"line_number":1434,"context_line":"    def _get_pci_device_profile(self, pci_dev):"},{"line_number":1435,"context_line":"        dev_spec \u003d self.pci_whitelist.get_devspec(pci_dev)"}],"source_content_type":"text/x-python","patch_set":4,"id":"3fa7e38b_8982d6c6","line":1432,"range":{"start_line":1402,"start_character":0,"end_line":1432,"end_character":48},"in_reply_to":"3fa7e38b_c11af716","updated":"2019-12-03 09:55:52.000000000","message":"I made a TODO to myself to look into this separately.","commit_id":"956e958a0351aab19b4b089ae4dec82e6d31d28e"},{"author":{"_account_id":6873,"name":"Matt Riedemann","email":"mriedem.os@gmail.com","username":"mriedem"},"change_message_id":"5132c2e04ee09d44fd759c26d9c039e6df446a1e","unresolved":false,"context_lines":[{"line_number":1215,"context_line":"                           vnic_types\u003dNone, port_profiles\u003dNone):"},{"line_number":1216,"context_line":"        \"\"\"Attempts to bind the ports from the instance on the given host"},{"line_number":1217,"context_line":""},{"line_number":1218,"context_line":"        If the ports are already actively bound to another host, like the"},{"line_number":1219,"context_line":"        source host during live migration, then the new port bindings will"},{"line_number":1220,"context_line":"        be inactive, assuming $host is the destination host for the live"},{"line_number":1221,"context_line":"        migration."},{"line_number":1222,"context_line":""},{"line_number":1223,"context_line":"        In the event of an error, any ports which were successfully bound to"},{"line_number":1224,"context_line":"        the host should have those host bindings removed from the ports."}],"source_content_type":"text/x-python","patch_set":7,"id":"3fa7e38b_fc3ad494","line":1221,"range":{"start_line":1218,"start_character":8,"end_line":1221,"end_character":18},"updated":"2019-12-06 20:52:17.000000000","message":"OK so in your _create_port_binding implementation in the fixture you\u0027re going to be defaulting all bindings to INACTIVE. That\u0027s fine if the port already has bindings, but if it\u0027s the first port binding for a server/port/host then it would be ACTIVE I\u0027d think.","commit_id":"2bab107eab6b5ec3046438f9a9ce18c2c1000aa9"},{"author":{"_account_id":6873,"name":"Matt Riedemann","email":"mriedem.os@gmail.com","username":"mriedem"},"change_message_id":"5132c2e04ee09d44fd759c26d9c039e6df446a1e","unresolved":false,"context_lines":[{"line_number":1405,"context_line":""},{"line_number":1406,"context_line":"        :param context: The request context for the operation."},{"line_number":1407,"context_line":"        :param client: keystoneauth1.adapter.Adapter"},{"line_number":1408,"context_line":"        :param port_id: ID of the port to activate the a binding on"},{"line_number":1409,"context_line":"        :param host: A string name of the host identifying the binding to be"},{"line_number":1410,"context_line":"            activated"},{"line_number":1411,"context_line":"        :return: requests.Response object"}],"source_content_type":"text/x-python","patch_set":7,"id":"3fa7e38b_bc953c8a","line":1408,"range":{"start_line":1408,"start_character":55,"end_line":1408,"end_character":57},"updated":"2019-12-06 20:52:17.000000000","message":"nix","commit_id":"2bab107eab6b5ec3046438f9a9ce18c2c1000aa9"},{"author":{"_account_id":15334,"name":"Stephen Finucane","display_name":"stephenfin","email":"stephenfin@redhat.com","username":"sfinucan"},"change_message_id":"1cec474456cf2015f9686233f4763a87a83807d9","unresolved":false,"context_lines":[{"line_number":1413,"context_line":"        return client.put("},{"line_number":1414,"context_line":"            \u0027/v2.0/ports/%s/bindings/%s/activate\u0027 % (port_id, host),"},{"line_number":1415,"context_line":"            raise_exc\u003dFalse,"},{"line_number":1416,"context_line":"            global_request_id\u003dcontext.global_id)"},{"line_number":1417,"context_line":""},{"line_number":1418,"context_line":"    @staticmethod"},{"line_number":1419,"context_line":"    def _get_port_binding(context, client, port_id, host):"}],"source_content_type":"text/x-python","patch_set":7,"id":"3fa7e38b_669be372","line":1416,"updated":"2019-12-04 10:25:40.000000000","message":"It\u0027s so strange that python-neutronclient doesn\u0027t expose this. Doesn\u0027t look like openstacksdk does either :(","commit_id":"2bab107eab6b5ec3046438f9a9ce18c2c1000aa9"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"839bfe1d6b604983efe4dcf3a33290c238ce8e13","unresolved":false,"context_lines":[{"line_number":1413,"context_line":"        return client.put("},{"line_number":1414,"context_line":"            \u0027/v2.0/ports/%s/bindings/%s/activate\u0027 % (port_id, host),"},{"line_number":1415,"context_line":"            raise_exc\u003dFalse,"},{"line_number":1416,"context_line":"            global_request_id\u003dcontext.global_id)"},{"line_number":1417,"context_line":""},{"line_number":1418,"context_line":"    @staticmethod"},{"line_number":1419,"context_line":"    def _get_port_binding(context, client, port_id, host):"}],"source_content_type":"text/x-python","patch_set":7,"id":"3fa7e38b_3c8f3a23","line":1416,"in_reply_to":"3fa7e38b_669be372","updated":"2019-12-04 12:36:56.000000000","message":"this API doesn\u0027t even have API ref at the moment, see https://bugs.launchpad.net/neutron/+bug/1853873","commit_id":"2bab107eab6b5ec3046438f9a9ce18c2c1000aa9"}],"nova/tests/fixtures.py":[{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"0bdb673b856282f039fa316d3ec29515dce725e2","unresolved":false,"context_lines":[{"line_number":1735,"context_line":"                        % (host, port_id))"},{"line_number":1736,"context_line":""},{"line_number":1737,"context_line":"        # It makes sure that only one binding is active for a port"},{"line_number":1738,"context_line":"        for h, binding in self._port_bindings.items():"},{"line_number":1739,"context_line":"            if h \u003d\u003d host:"},{"line_number":1740,"context_line":"                binding[\u0027status\u0027] \u003d \u0027ACTIVE\u0027"},{"line_number":1741,"context_line":"            else:"}],"source_content_type":"text/x-python","patch_set":1,"id":"3fa7e38b_9370f1a6","line":1738,"range":{"start_line":1738,"start_character":26,"end_line":1738,"end_character":54},"updated":"2019-11-27 15:37:01.000000000","message":"this should be self._port_bindings[port_id].items()","commit_id":"c16c0214a7888b92897eb5cdbcd69db2dddedd37"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"979c28f92263b709c25b4391cc424c3265743853","unresolved":false,"context_lines":[{"line_number":1735,"context_line":"                        % (host, port_id))"},{"line_number":1736,"context_line":""},{"line_number":1737,"context_line":"        # It makes sure that only one binding is active for a port"},{"line_number":1738,"context_line":"        for h, binding in self._port_bindings.items():"},{"line_number":1739,"context_line":"            if h \u003d\u003d host:"},{"line_number":1740,"context_line":"                binding[\u0027status\u0027] \u003d \u0027ACTIVE\u0027"},{"line_number":1741,"context_line":"            else:"}],"source_content_type":"text/x-python","patch_set":1,"id":"3fa7e38b_ac710eae","line":1738,"range":{"start_line":1738,"start_character":26,"end_line":1738,"end_character":54},"in_reply_to":"3fa7e38b_9370f1a6","updated":"2019-11-27 17:43:49.000000000","message":"Done","commit_id":"c16c0214a7888b92897eb5cdbcd69db2dddedd37"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"979c28f92263b709c25b4391cc424c3265743853","unresolved":false,"context_lines":[{"line_number":1803,"context_line":"            binding \u003d self._get_active_binding(port[\u0027id\u0027]) or {}"},{"line_number":1804,"context_line":"            for key, value in binding.items():"},{"line_number":1805,"context_line":"                if key !\u003d \u0027host\u0027:"},{"line_number":1806,"context_line":"                    port[\u0027binding_\u0027 + key] \u003d value"},{"line_number":1807,"context_line":"                else:"},{"line_number":1808,"context_line":"                    # it is a special case in naming"},{"line_number":1809,"context_line":"                    port[\u0027binding_host_id\u0027] \u003d binding[\u0027host\u0027]"}],"source_content_type":"text/x-python","patch_set":1,"id":"3fa7e38b_6c6b16b9","line":1806,"range":{"start_line":1806,"start_character":33,"end_line":1806,"end_character":34},"updated":"2019-11-27 17:43:49.000000000","message":"this should be \u0027:\u0027","commit_id":"c16c0214a7888b92897eb5cdbcd69db2dddedd37"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"979c28f92263b709c25b4391cc424c3265743853","unresolved":false,"context_lines":[{"line_number":1806,"context_line":"                    port[\u0027binding_\u0027 + key] \u003d value"},{"line_number":1807,"context_line":"                else:"},{"line_number":1808,"context_line":"                    # it is a special case in naming"},{"line_number":1809,"context_line":"                    port[\u0027binding_host_id\u0027] \u003d binding[\u0027host\u0027]"},{"line_number":1810,"context_line":""},{"line_number":1811,"context_line":"    def show_port(self, port_id, **_params):"},{"line_number":1812,"context_line":"        if port_id not in self._ports:"}],"source_content_type":"text/x-python","patch_set":1,"id":"3fa7e38b_2c651ee3","line":1809,"range":{"start_line":1809,"start_character":33,"end_line":1809,"end_character":34},"updated":"2019-11-27 17:43:49.000000000","message":"ditto","commit_id":"c16c0214a7888b92897eb5cdbcd69db2dddedd37"},{"author":{"_account_id":15334,"name":"Stephen Finucane","display_name":"stephenfin","email":"stephenfin@redhat.com","username":"sfinucan"},"change_message_id":"b395614ca5f47180689d997c3d75ae6f73d60d6f","unresolved":false,"context_lines":[{"line_number":1631,"context_line":"                copy.deepcopy(self.port_with_resource_request)"},{"line_number":1632,"context_line":"        }"},{"line_number":1633,"context_line":"        # Store multiple port bindings per port in a dict keyed by the host."},{"line_number":1634,"context_line":"        # At startup we assume that non of the ports are bound."},{"line_number":1635,"context_line":"        # {\u003cport_id\u003e: {\u003chostname\u003e: \u003cbinding\u003e}}"},{"line_number":1636,"context_line":"        self._port_bindings \u003d collections.defaultdict(dict)"},{"line_number":1637,"context_line":""}],"source_content_type":"text/x-python","patch_set":4,"id":"3fa7e38b_611783f0","line":1634,"range":{"start_line":1634,"start_character":36,"end_line":1634,"end_character":39},"updated":"2019-11-29 15:37:09.000000000","message":"none","commit_id":"956e958a0351aab19b4b089ae4dec82e6d31d28e"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"06312da69b9c9c4588cf80b142d4177f92e23df9","unresolved":false,"context_lines":[{"line_number":1631,"context_line":"                copy.deepcopy(self.port_with_resource_request)"},{"line_number":1632,"context_line":"        }"},{"line_number":1633,"context_line":"        # Store multiple port bindings per port in a dict keyed by the host."},{"line_number":1634,"context_line":"        # At startup we assume that non of the ports are bound."},{"line_number":1635,"context_line":"        # {\u003cport_id\u003e: {\u003chostname\u003e: \u003cbinding\u003e}}"},{"line_number":1636,"context_line":"        self._port_bindings \u003d collections.defaultdict(dict)"},{"line_number":1637,"context_line":""}],"source_content_type":"text/x-python","patch_set":4,"id":"3fa7e38b_c961ae3a","line":1634,"range":{"start_line":1634,"start_character":36,"end_line":1634,"end_character":39},"in_reply_to":"3fa7e38b_611783f0","updated":"2019-12-03 09:55:52.000000000","message":"Done","commit_id":"956e958a0351aab19b4b089ae4dec82e6d31d28e"},{"author":{"_account_id":15334,"name":"Stephen Finucane","display_name":"stephenfin","email":"stephenfin@redhat.com","username":"sfinucan"},"change_message_id":"b395614ca5f47180689d997c3d75ae6f73d60d6f","unresolved":false,"context_lines":[{"line_number":1714,"context_line":"        return fake_requests.FakeResponse(200, content\u003djsonutils.dumps(data))"},{"line_number":1715,"context_line":""},{"line_number":1716,"context_line":"    def delete_port_binding(self, context, client, port_id, host):"},{"line_number":1717,"context_line":"        if port_id not in self._ports:"},{"line_number":1718,"context_line":"            return fake_requests.FakeResponse("},{"line_number":1719,"context_line":"                404, content\u003d\u0027Port %s not found\u0027 % port_id)"},{"line_number":1720,"context_line":"        if host not in self._port_bindings[port_id]:"},{"line_number":1721,"context_line":"            return fake_requests.FakeResponse("},{"line_number":1722,"context_line":"                404,"},{"line_number":1723,"context_line":"                content\u003d\u0027Binding for host %s for port %s not found\u0027"},{"line_number":1724,"context_line":"                        % (host, port_id))"},{"line_number":1725,"context_line":""},{"line_number":1726,"context_line":"        del self._port_bindings[port_id][host]"},{"line_number":1727,"context_line":""}],"source_content_type":"text/x-python","patch_set":4,"id":"3fa7e38b_e1a613c1","line":1724,"range":{"start_line":1717,"start_character":0,"end_line":1724,"end_character":42},"updated":"2019-11-29 15:37:09.000000000","message":"could we drag this out to a common helper? Looks identical in the next two and quite similar to the above (minus the check for the host being registered in port_bindings)","commit_id":"956e958a0351aab19b4b089ae4dec82e6d31d28e"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"06312da69b9c9c4588cf80b142d4177f92e23df9","unresolved":false,"context_lines":[{"line_number":1714,"context_line":"        return fake_requests.FakeResponse(200, content\u003djsonutils.dumps(data))"},{"line_number":1715,"context_line":""},{"line_number":1716,"context_line":"    def delete_port_binding(self, context, client, port_id, host):"},{"line_number":1717,"context_line":"        if port_id not in self._ports:"},{"line_number":1718,"context_line":"            return fake_requests.FakeResponse("},{"line_number":1719,"context_line":"                404, content\u003d\u0027Port %s not found\u0027 % port_id)"},{"line_number":1720,"context_line":"        if host not in self._port_bindings[port_id]:"},{"line_number":1721,"context_line":"            return fake_requests.FakeResponse("},{"line_number":1722,"context_line":"                404,"},{"line_number":1723,"context_line":"                content\u003d\u0027Binding for host %s for port %s not found\u0027"},{"line_number":1724,"context_line":"                        % (host, port_id))"},{"line_number":1725,"context_line":""},{"line_number":1726,"context_line":"        del self._port_bindings[port_id][host]"},{"line_number":1727,"context_line":""}],"source_content_type":"text/x-python","patch_set":4,"id":"3fa7e38b_098a66bb","line":1724,"range":{"start_line":1717,"start_character":0,"end_line":1724,"end_character":42},"in_reply_to":"3fa7e38b_e1a613c1","updated":"2019-12-03 09:55:52.000000000","message":"Moved the repeated code to a helper","commit_id":"956e958a0351aab19b4b089ae4dec82e6d31d28e"},{"author":{"_account_id":15334,"name":"Stephen Finucane","display_name":"stephenfin","email":"stephenfin@redhat.com","username":"sfinucan"},"change_message_id":"b395614ca5f47180689d997c3d75ae6f73d60d6f","unresolved":false,"context_lines":[{"line_number":1800,"context_line":"                return binding"},{"line_number":1801,"context_line":""},{"line_number":1802,"context_line":"    def _merge_in_active_binding(self, port):"},{"line_number":1803,"context_line":"        if port[\u0027id\u0027] in self._port_bindings:"},{"line_number":1804,"context_line":"            binding \u003d self._get_active_binding(port[\u0027id\u0027]) or {}"},{"line_number":1805,"context_line":"            for key, value in binding.items():"},{"line_number":1806,"context_line":"                if key !\u003d \u0027host\u0027:"}],"source_content_type":"text/x-python","patch_set":4,"id":"3fa7e38b_a1901b51","line":1803,"range":{"start_line":1803,"start_character":0,"end_line":1803,"end_character":45},"updated":"2019-11-29 15:37:09.000000000","message":"nit:\n\n  if port[\u0027id\u0027] not in self._port_bindings:\n      return\n\n  binding \u003d ...","commit_id":"956e958a0351aab19b4b089ae4dec82e6d31d28e"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"06312da69b9c9c4588cf80b142d4177f92e23df9","unresolved":false,"context_lines":[{"line_number":1800,"context_line":"                return binding"},{"line_number":1801,"context_line":""},{"line_number":1802,"context_line":"    def _merge_in_active_binding(self, port):"},{"line_number":1803,"context_line":"        if port[\u0027id\u0027] in self._port_bindings:"},{"line_number":1804,"context_line":"            binding \u003d self._get_active_binding(port[\u0027id\u0027]) or {}"},{"line_number":1805,"context_line":"            for key, value in binding.items():"},{"line_number":1806,"context_line":"                if key !\u003d \u0027host\u0027:"}],"source_content_type":"text/x-python","patch_set":4,"id":"3fa7e38b_e9a7ca4f","line":1803,"range":{"start_line":1803,"start_character":0,"end_line":1803,"end_character":45},"in_reply_to":"3fa7e38b_a1901b51","updated":"2019-12-03 09:55:52.000000000","message":"Done","commit_id":"956e958a0351aab19b4b089ae4dec82e6d31d28e"},{"author":{"_account_id":15334,"name":"Stephen Finucane","display_name":"stephenfin","email":"stephenfin@redhat.com","username":"sfinucan"},"change_message_id":"b395614ca5f47180689d997c3d75ae6f73d60d6f","unresolved":false,"context_lines":[{"line_number":1819,"context_line":"    def delete_port(self, port_id, **_params):"},{"line_number":1820,"context_line":"        if port_id in self._ports:"},{"line_number":1821,"context_line":"            del self._ports[port_id]"},{"line_number":1822,"context_line":"            # Not all flow uses explicit binding creation so we need to delete"},{"line_number":1823,"context_line":"            # bindings conditionally"},{"line_number":1824,"context_line":"            if port_id in self._port_bindings:"},{"line_number":1825,"context_line":"                del self._port_bindings[port_id]"}],"source_content_type":"text/x-python","patch_set":4,"id":"3fa7e38b_81971f46","line":1822,"updated":"2019-11-29 15:37:09.000000000","message":"o rly?","commit_id":"956e958a0351aab19b4b089ae4dec82e6d31d28e"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"06312da69b9c9c4588cf80b142d4177f92e23df9","unresolved":false,"context_lines":[{"line_number":1819,"context_line":"    def delete_port(self, port_id, **_params):"},{"line_number":1820,"context_line":"        if port_id in self._ports:"},{"line_number":1821,"context_line":"            del self._ports[port_id]"},{"line_number":1822,"context_line":"            # Not all flow uses explicit binding creation so we need to delete"},{"line_number":1823,"context_line":"            # bindings conditionally"},{"line_number":1824,"context_line":"            if port_id in self._port_bindings:"},{"line_number":1825,"context_line":"                del self._port_bindings[port_id]"}],"source_content_type":"text/x-python","patch_set":4,"id":"3fa7e38b_292162b6","line":1822,"in_reply_to":"3fa7e38b_81971f46","updated":"2019-12-03 09:55:52.000000000","message":"Made this note a bit more specific about what the other flows do.","commit_id":"956e958a0351aab19b4b089ae4dec82e6d31d28e"},{"author":{"_account_id":6873,"name":"Matt Riedemann","email":"mriedem.os@gmail.com","username":"mriedem"},"change_message_id":"5132c2e04ee09d44fd759c26d9c039e6df446a1e","unresolved":false,"context_lines":[{"line_number":1707,"context_line":"                404, content\u003d\u0027Port %s not found\u0027 % port_id)"},{"line_number":1708,"context_line":""},{"line_number":1709,"context_line":"        host \u003d data[\u0027binding\u0027][\u0027host\u0027]"},{"line_number":1710,"context_line":"        if \u0027status\u0027 not in data[\u0027binding\u0027]:"},{"line_number":1711,"context_line":"            data[\u0027binding\u0027][\u0027status\u0027] \u003d \u0027INACTIVE\u0027"},{"line_number":1712,"context_line":"        self._port_bindings[port_id][host] \u003d copy.deepcopy(data[\u0027binding\u0027])"},{"line_number":1713,"context_line":""}],"source_content_type":"text/x-python","patch_set":7,"id":"3fa7e38b_9c4ba026","line":1710,"updated":"2019-12-06 20:52:17.000000000","message":"This is always going to be True isn\u0027t it? At least when creating a new port binding.","commit_id":"2bab107eab6b5ec3046438f9a9ce18c2c1000aa9"},{"author":{"_account_id":6873,"name":"Matt Riedemann","email":"mriedem.os@gmail.com","username":"mriedem"},"change_message_id":"5132c2e04ee09d44fd759c26d9c039e6df446a1e","unresolved":false,"context_lines":[{"line_number":1743,"context_line":"        # It makes sure that only one binding is active for a port"},{"line_number":1744,"context_line":"        for h, binding in self._port_bindings[port_id].items():"},{"line_number":1745,"context_line":"            if h \u003d\u003d host:"},{"line_number":1746,"context_line":"                binding[\u0027status\u0027] \u003d \u0027ACTIVE\u0027"},{"line_number":1747,"context_line":"            else:"},{"line_number":1748,"context_line":"                binding[\u0027status\u0027] \u003d \u0027INACTIVE\u0027"},{"line_number":1749,"context_line":""}],"source_content_type":"text/x-python","patch_set":7,"id":"3fa7e38b_5c63e8b1","line":1746,"updated":"2019-12-06 20:52:17.000000000","message":"Technically I think the neutron API returns a 409 response if you activate an already active binding, but that\u0027s not really worth handling here. If activate_port_binding gets a 409 response it just logs a warning.","commit_id":"2bab107eab6b5ec3046438f9a9ce18c2c1000aa9"},{"author":{"_account_id":6873,"name":"Matt Riedemann","email":"mriedem.os@gmail.com","username":"mriedem"},"change_message_id":"5132c2e04ee09d44fd759c26d9c039e6df446a1e","unresolved":false,"context_lines":[{"line_number":1798,"context_line":"            if binding[\u0027status\u0027] \u003d\u003d \u0027ACTIVE\u0027:"},{"line_number":1799,"context_line":"                return binding"},{"line_number":1800,"context_line":""},{"line_number":1801,"context_line":"    def _merge_in_active_binding(self, port):"},{"line_number":1802,"context_line":"        if port[\u0027id\u0027] not in self._port_bindings:"},{"line_number":1803,"context_line":"            return"},{"line_number":1804,"context_line":""}],"source_content_type":"text/x-python","patch_set":7,"id":"3fa7e38b_bc71bc79","line":1801,"updated":"2019-12-06 20:52:17.000000000","message":"A docstring would be nice.","commit_id":"2bab107eab6b5ec3046438f9a9ce18c2c1000aa9"},{"author":{"_account_id":6873,"name":"Matt Riedemann","email":"mriedem.os@gmail.com","username":"mriedem"},"change_message_id":"5132c2e04ee09d44fd759c26d9c039e6df446a1e","unresolved":false,"context_lines":[{"line_number":1804,"context_line":""},{"line_number":1805,"context_line":"        binding \u003d self._get_active_binding(port[\u0027id\u0027]) or {}"},{"line_number":1806,"context_line":"        for key, value in binding.items():"},{"line_number":1807,"context_line":"            if key !\u003d \u0027host\u0027:"},{"line_number":1808,"context_line":"                port[\u0027binding:\u0027 + key] \u003d value"},{"line_number":1809,"context_line":"            else:"},{"line_number":1810,"context_line":"                # it is a special case in naming"}],"source_content_type":"text/x-python","patch_set":7,"id":"3fa7e38b_9c6400b5","line":1807,"updated":"2019-12-06 20:52:17.000000000","message":"OK so this would be like vnic_type and profile.","commit_id":"2bab107eab6b5ec3046438f9a9ce18c2c1000aa9"},{"author":{"_account_id":6873,"name":"Matt Riedemann","email":"mriedem.os@gmail.com","username":"mriedem"},"change_message_id":"5132c2e04ee09d44fd759c26d9c039e6df446a1e","unresolved":false,"context_lines":[{"line_number":1808,"context_line":"                port[\u0027binding:\u0027 + key] \u003d value"},{"line_number":1809,"context_line":"            else:"},{"line_number":1810,"context_line":"                # it is a special case in naming"},{"line_number":1811,"context_line":"                port[\u0027binding:host_id\u0027] \u003d binding[\u0027host\u0027]"},{"line_number":1812,"context_line":""},{"line_number":1813,"context_line":"    def show_port(self, port_id, **_params):"},{"line_number":1814,"context_line":"        if port_id not in self._ports:"}],"source_content_type":"text/x-python","patch_set":7,"id":"3fa7e38b_5c08c8d7","line":1811,"updated":"2019-12-06 20:52:17.000000000","message":"Ack, the port uses binding:host_id:\n\nhttps://docs.openstack.org/api-ref/network/v2/index.html#port-binding-extended-attributes\n\nBut the port bindings API doesn\u0027t:\n\nhttps://github.com/openstack/neutron-lib/blob/1.29.1/neutron_lib/api/definitions/portbindings_extended.py#L58","commit_id":"2bab107eab6b5ec3046438f9a9ce18c2c1000aa9"},{"author":{"_account_id":6873,"name":"Matt Riedemann","email":"mriedem.os@gmail.com","username":"mriedem"},"change_message_id":"5132c2e04ee09d44fd759c26d9c039e6df446a1e","unresolved":false,"context_lines":[{"line_number":1820,"context_line":"    def delete_port(self, port_id, **_params):"},{"line_number":1821,"context_line":"        if port_id in self._ports:"},{"line_number":1822,"context_line":"            del self._ports[port_id]"},{"line_number":1823,"context_line":"            # Not all flow uses explicit binding creation by calling"},{"line_number":1824,"context_line":"            # neutronv2.api.API.bind_ports_to_host(). Non livemigration flows"},{"line_number":1825,"context_line":"            # simply update the port to bind it. So we need to delete bindings"},{"line_number":1826,"context_line":"            # conditionally"}],"source_content_type":"text/x-python","patch_set":7,"id":"3fa7e38b_fc0894d8","line":1823,"range":{"start_line":1823,"start_character":22,"end_line":1823,"end_character":31},"updated":"2019-12-06 20:52:17.000000000","message":"flows use","commit_id":"2bab107eab6b5ec3046438f9a9ce18c2c1000aa9"},{"author":{"_account_id":6873,"name":"Matt Riedemann","email":"mriedem.os@gmail.com","username":"mriedem"},"change_message_id":"5132c2e04ee09d44fd759c26d9c039e6df446a1e","unresolved":false,"context_lines":[{"line_number":1824,"context_line":"            # neutronv2.api.API.bind_ports_to_host(). Non livemigration flows"},{"line_number":1825,"context_line":"            # simply update the port to bind it. So we need to delete bindings"},{"line_number":1826,"context_line":"            # conditionally"},{"line_number":1827,"context_line":"            if port_id in self._port_bindings:"},{"line_number":1828,"context_line":"                del self._port_bindings[port_id]"},{"line_number":1829,"context_line":""},{"line_number":1830,"context_line":"    def list_ports(self, is_admin, retrieve_all\u003dTrue, **_params):"}],"source_content_type":"text/x-python","patch_set":7,"id":"3fa7e38b_9cf960c6","line":1827,"updated":"2019-12-06 20:52:17.000000000","message":"see update_port below","commit_id":"2bab107eab6b5ec3046438f9a9ce18c2c1000aa9"},{"author":{"_account_id":6873,"name":"Matt Riedemann","email":"mriedem.os@gmail.com","username":"mriedem"},"change_message_id":"5132c2e04ee09d44fd759c26d9c039e6df446a1e","unresolved":false,"context_lines":[{"line_number":1884,"context_line":"        # the self._ports dict."},{"line_number":1885,"context_line":"        return {\u0027port\u0027: copy.deepcopy(new_port)}"},{"line_number":1886,"context_line":""},{"line_number":1887,"context_line":"    def update_port(self, port_id, body\u003dNone):"},{"line_number":1888,"context_line":"        port \u003d self._ports[port_id]"},{"line_number":1889,"context_line":"        # We need to deepcopy here as well as the body can have a nested dict"},{"line_number":1890,"context_line":"        # which can be modified by the caller after this update_port call"}],"source_content_type":"text/x-python","patch_set":7,"id":"3fa7e38b_3cd14c30","line":1887,"updated":"2019-12-06 20:52:17.000000000","message":"I was thinking we\u0027d put something into _port_bindings if the port update body has a binding:host_id value in it, i.e.:\n\nhttps://github.com/openstack/nova/blob/1f382b4d0f7f6023a7273a0c67b387b951102cff/nova/network/neutronv2/api.py#L3331\n\nhttps://github.com/openstack/nova/blob/1f382b4d0f7f6023a7273a0c67b387b951102cff/nova/network/neutronv2/api.py#L565\n\nThen delete_port above wouldn\u0027t need to be special-cased, right?\n\nAnyway, it\u0027s something that could be dealt with later if necessary.","commit_id":"2bab107eab6b5ec3046438f9a9ce18c2c1000aa9"},{"author":{"_account_id":6873,"name":"Matt Riedemann","email":"mriedem.os@gmail.com","username":"mriedem"},"change_message_id":"2120c4198b803e4c6f97668340acc3174c97b97a","unresolved":false,"context_lines":[{"line_number":1833,"context_line":"    def delete_port(self, port_id, **_params):"},{"line_number":1834,"context_line":"        if port_id in self._ports:"},{"line_number":1835,"context_line":"            del self._ports[port_id]"},{"line_number":1836,"context_line":"            # Not all flow use explicit binding creation by calling"},{"line_number":1837,"context_line":"            # neutronv2.api.API.bind_ports_to_host(). Non live migration flows"},{"line_number":1838,"context_line":"            # simply update the port to bind it. So we need to delete bindings"},{"line_number":1839,"context_line":"            # conditionally"}],"source_content_type":"text/x-python","patch_set":9,"id":"3fa7e38b_a2ede024","line":1836,"range":{"start_line":1836,"start_character":22,"end_line":1836,"end_character":26},"updated":"2019-12-11 13:55:44.000000000","message":"flows","commit_id":"448b971e88540198d800e17b3b673e7c1bd379f2"},{"author":{"_account_id":6873,"name":"Matt Riedemann","email":"mriedem.os@gmail.com","username":"mriedem"},"change_message_id":"2120c4198b803e4c6f97668340acc3174c97b97a","unresolved":false,"context_lines":[{"line_number":1900,"context_line":"    def update_port(self, port_id, body\u003dNone):"},{"line_number":1901,"context_line":"        # TODO(gibi): check if the port update binds the port and update the"},{"line_number":1902,"context_line":"        # internal _port_bindings dict accordingly. Such a binding always"},{"line_number":1903,"context_line":"        # becomes and active port binding of the port."},{"line_number":1904,"context_line":"        port \u003d self._ports[port_id]"},{"line_number":1905,"context_line":"        # We need to deepcopy here as well as the body can have a nested dict"},{"line_number":1906,"context_line":"        # which can be modified by the caller after this update_port call"}],"source_content_type":"text/x-python","patch_set":9,"id":"3fa7e38b_c2f01cff","line":1903,"range":{"start_line":1903,"start_character":18,"end_line":1903,"end_character":21},"updated":"2019-12-11 13:55:44.000000000","message":"an","commit_id":"448b971e88540198d800e17b3b673e7c1bd379f2"}]}
