)]}'
{"/COMMIT_MSG":[{"author":{"_account_id":1131,"name":"Brian Haley","email":"haleyb.dev@gmail.com","username":"brian-haley"},"change_message_id":"acfecc3969748526293ccf93f30e2c2f0cc54a82","unresolved":false,"context_lines":[{"line_number":20,"context_line":"extension can extend RouterInfo itself which correspond to each features"},{"line_number":21,"context_line":"(ha, distribtued, ha + distributed)"},{"line_number":22,"context_line":""},{"line_number":23,"context_line":"Depends-On: I55a1cb60898ab87ffe137f8c4b0b2f2803bfb219"},{"line_number":24,"context_line":"Closes-Bug: #1804634"},{"line_number":25,"context_line":"Change-Id: I1eff726900a8e67596814ca9a5f392938f154d7b"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":2,"id":"3f79a3b5_31dd8c11","line":23,"updated":"2018-11-28 15:07:29.000000000","message":"You can also use the review link in a Depends-on\n\nDepends-On: https://review.openstack.org/#/c/620348/\n\nBut in this case it won\u0027t work since neutron-lib is released as a library, so you can\u0027t depend on it.  What you should do is put the exception in neutron, then after your neutron-lib patch merges and neutron updates to use a version where it is available, you can then remove the one in neutron.  Typically you\u0027d add a \"TODO(myname) remove when neutron-lib version is available\" above the code.","commit_id":"0a94c7ca28100ee2a039833476948cddc0ce82ee"},{"author":{"_account_id":1131,"name":"Brian Haley","email":"haleyb.dev@gmail.com","username":"brian-haley"},"change_message_id":"b898a76241d87bf1b1b3f9ecfeda3664170d26f2","unresolved":false,"context_lines":[{"line_number":20,"context_line":"extension can extend RouterInfo itself which correspond to each features"},{"line_number":21,"context_line":"(ha, distribtued, ha + distributed)"},{"line_number":22,"context_line":""},{"line_number":23,"context_line":"Depends-On: I55a1cb60898ab87ffe137f8c4b0b2f2803bfb219"},{"line_number":24,"context_line":"Closes-Bug: #1804634"},{"line_number":25,"context_line":"Partially-Implements: blueprint openflow-based-dvr"},{"line_number":26,"context_line":"Change-Id: I1eff726900a8e67596814ca9a5f392938f154d7b"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":22,"id":"3fce034c_41ffdd33","line":23,"updated":"2019-04-15 16:33:16.000000000","message":"Old-style, could have used:\n\nhttps://review.openstack.org/#/c/620348/","commit_id":"98e8f8c4016abdb9ae651be8bfe6ff0d7da31e2b"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"b572ddc4553e4ec9abd0b93fd5b9bec5dd215ca8","unresolved":false,"context_lines":[{"line_number":20,"context_line":"extension can extend RouterInfo itself which correspond to each features"},{"line_number":21,"context_line":"(ha, distribtued, ha + distributed)"},{"line_number":22,"context_line":""},{"line_number":23,"context_line":"Depends-On: I55a1cb60898ab87ffe137f8c4b0b2f2803bfb219"},{"line_number":24,"context_line":"Closes-Bug: #1804634"},{"line_number":25,"context_line":"Partially-Implements: blueprint openflow-based-dvr"},{"line_number":26,"context_line":"Change-Id: I1eff726900a8e67596814ca9a5f392938f154d7b"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":22,"id":"3fce034c_9f07551d","line":23,"in_reply_to":"3fce034c_41ffdd33","updated":"2019-04-16 01:54:07.000000000","message":"Done","commit_id":"98e8f8c4016abdb9ae651be8bfe6ff0d7da31e2b"}],"neutron/agent/l3/agent.py":[{"author":{"_account_id":1131,"name":"Brian Haley","email":"haleyb.dev@gmail.com","username":"brian-haley"},"change_message_id":"acfecc3969748526293ccf93f30e2c2f0cc54a82","unresolved":false,"context_lines":[{"line_number":204,"context_line":"    def create(self, features, **kwargs):"},{"line_number":205,"context_line":"        \"\"\"Create router instance with registered router class"},{"line_number":206,"context_line":""},{"line_number":207,"context_line":"        :param features: a list of strings which means router\u0027s feature"},{"line_number":208,"context_line":"        :param kwargs: arguments for router class"},{"line_number":209,"context_line":"        :returns: a router instance which implements BaseRouterInfo"},{"line_number":210,"context_line":"        :raises: n_exc.RouterNotFoundInRouterFactory"}],"source_content_type":"text/x-python","patch_set":2,"id":"3f79a3b5_b1119cfb","line":207,"range":{"start_line":207,"start_character":43,"end_line":207,"end_character":71},"updated":"2018-11-28 15:07:29.000000000","message":"s/of router\u0027s features (?)","commit_id":"0a94c7ca28100ee2a039833476948cddc0ce82ee"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"54a8a3c23918a1e842e068598fddd1b9b236c76b","unresolved":false,"context_lines":[{"line_number":204,"context_line":"    def create(self, features, **kwargs):"},{"line_number":205,"context_line":"        \"\"\"Create router instance with registered router class"},{"line_number":206,"context_line":""},{"line_number":207,"context_line":"        :param features: a list of strings which means router\u0027s feature"},{"line_number":208,"context_line":"        :param kwargs: arguments for router class"},{"line_number":209,"context_line":"        :returns: a router instance which implements BaseRouterInfo"},{"line_number":210,"context_line":"        :raises: n_exc.RouterNotFoundInRouterFactory"}],"source_content_type":"text/x-python","patch_set":2,"id":"3f79a3b5_bc45f39d","line":207,"range":{"start_line":207,"start_character":43,"end_line":207,"end_character":71},"in_reply_to":"3f79a3b5_b1119cfb","updated":"2018-11-29 02:19:43.000000000","message":"Done","commit_id":"0a94c7ca28100ee2a039833476948cddc0ce82ee"},{"author":{"_account_id":1131,"name":"Brian Haley","email":"haleyb.dev@gmail.com","username":"brian-haley"},"change_message_id":"b64c73a1554a6b86440da5cc69fa740049c011d4","unresolved":false,"context_lines":[{"line_number":326,"context_line":"            factory.register([\u0027distributed\u0027],"},{"line_number":327,"context_line":"                             dvr_local_router.DvrLocalRouter)"},{"line_number":328,"context_line":"            factory.register([\u0027ha\u0027, \u0027distributed\u0027],"},{"line_number":329,"context_line":"                             dvr_local_router.DvrLocalRouter)"},{"line_number":330,"context_line":""},{"line_number":331,"context_line":"    def _check_config_params(self):"},{"line_number":332,"context_line":"        \"\"\"Check items in configuration files."}],"source_content_type":"text/x-python","patch_set":2,"id":"3f79a3b5_f6dabce4","line":329,"updated":"2018-11-27 19:43:19.000000000","message":"One of these two doesn\u0027t look correct, second call is just adding \u0027ha\u0027","commit_id":"0a94c7ca28100ee2a039833476948cddc0ce82ee"},{"author":{"_account_id":1131,"name":"Brian Haley","email":"haleyb.dev@gmail.com","username":"brian-haley"},"change_message_id":"8eccbe58992d18e92083c34ddece050eb65ac73f","unresolved":false,"context_lines":[{"line_number":326,"context_line":"            factory.register([\u0027distributed\u0027],"},{"line_number":327,"context_line":"                             dvr_local_router.DvrLocalRouter)"},{"line_number":328,"context_line":"            factory.register([\u0027ha\u0027, \u0027distributed\u0027],"},{"line_number":329,"context_line":"                             dvr_local_router.DvrLocalRouter)"},{"line_number":330,"context_line":""},{"line_number":331,"context_line":"    def _check_config_params(self):"},{"line_number":332,"context_line":"        \"\"\"Check items in configuration files."}],"source_content_type":"text/x-python","patch_set":2,"id":"3f79a3b5_b640b234","line":329,"in_reply_to":"3f79a3b5_b7119bb0","updated":"2018-11-28 14:13:29.000000000","message":"I might have just mis-understood the code, I guess you are registering both DVR and DVR/HA. Based on the lines above this with the DVR/HA using dvr_edge_ha_router code it just looked wrong, but doesn\u0027t now.","commit_id":"0a94c7ca28100ee2a039833476948cddc0ce82ee"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"601cb1fea3f6e7a03fd23ae7d9c04be90e94b781","unresolved":false,"context_lines":[{"line_number":326,"context_line":"            factory.register([\u0027distributed\u0027],"},{"line_number":327,"context_line":"                             dvr_local_router.DvrLocalRouter)"},{"line_number":328,"context_line":"            factory.register([\u0027ha\u0027, \u0027distributed\u0027],"},{"line_number":329,"context_line":"                             dvr_local_router.DvrLocalRouter)"},{"line_number":330,"context_line":""},{"line_number":331,"context_line":"    def _check_config_params(self):"},{"line_number":332,"context_line":"        \"\"\"Check items in configuration files."}],"source_content_type":"text/x-python","patch_set":2,"id":"3f79a3b5_b7119bb0","line":329,"in_reply_to":"3f79a3b5_f6dabce4","updated":"2018-11-28 01:46:29.000000000","message":"Sorry to bother you. I doubled check what you said, but still does not understand. Can you explain a little bit more..?","commit_id":"0a94c7ca28100ee2a039833476948cddc0ce82ee"},{"author":{"_account_id":16688,"name":"Rodolfo Alonso","email":"ralonsoh@redhat.com","username":"rodolfo-alonso-hernandez"},"change_message_id":"8b730dc13bebcdeb9eccbbba9e4aeb00870f9764","unresolved":false,"context_lines":[{"line_number":416,"context_line":"            ri \u003d self._create_router(router_id, router)"},{"line_number":417,"context_line":"        except n_exc.RouterNotFoundInRouterFactory as e:"},{"line_number":418,"context_line":"            with excutils.save_and_reraise_exception():"},{"line_number":419,"context_line":"                LOG.exception(e.msg)"},{"line_number":420,"context_line":""},{"line_number":421,"context_line":"        registry.notify(resources.ROUTER, events.BEFORE_CREATE,"},{"line_number":422,"context_line":"                        self, router\u003dri)"}],"source_content_type":"text/x-python","patch_set":5,"id":"3f79a3b5_b76c2c34","line":419,"range":{"start_line":419,"start_character":16,"end_line":419,"end_character":36},"updated":"2018-11-28 16:27:16.000000000","message":"small nit: you can write this message in RouterFactory.create() and avoid changing this function","commit_id":"7bc8d661611582b675b5624d5020dfa5f619d1b8"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"54a8a3c23918a1e842e068598fddd1b9b236c76b","unresolved":false,"context_lines":[{"line_number":416,"context_line":"            ri \u003d self._create_router(router_id, router)"},{"line_number":417,"context_line":"        except n_exc.RouterNotFoundInRouterFactory as e:"},{"line_number":418,"context_line":"            with excutils.save_and_reraise_exception():"},{"line_number":419,"context_line":"                LOG.exception(e.msg)"},{"line_number":420,"context_line":""},{"line_number":421,"context_line":"        registry.notify(resources.ROUTER, events.BEFORE_CREATE,"},{"line_number":422,"context_line":"                        self, router\u003dri)"}],"source_content_type":"text/x-python","patch_set":5,"id":"3f79a3b5_9a2b4d7c","line":419,"range":{"start_line":419,"start_character":16,"end_line":419,"end_character":36},"in_reply_to":"3f79a3b5_b76c2c34","updated":"2018-11-29 02:19:43.000000000","message":"Thanks for the detail! I assume that _router_added() should not raise any exception since the logic below except all exceptions.\n\nBut after your comment, I realize this case is different since if I catch the exception here, the KeyError occurs in _process_added_router() right after.\n\nIt\u0027s more applicable to let the exception flow here, as you mentioned.","commit_id":"7bc8d661611582b675b5624d5020dfa5f619d1b8"},{"author":{"_account_id":9531,"name":"liuyulong","display_name":"LIU Yulong","email":"i@liuyulong.me","username":"LIU-Yulong"},"change_message_id":"82676d55de8fcace01a8d4e1e6f2b6dc6a091717","unresolved":false,"context_lines":[{"line_number":185,"context_line":"                          host\u003dself.host, network_id\u003dfip_net)"},{"line_number":186,"context_line":""},{"line_number":187,"context_line":""},{"line_number":188,"context_line":"class RouterFactory(object):"},{"line_number":189,"context_line":""},{"line_number":190,"context_line":"    def __init__(self):"},{"line_number":191,"context_line":"        self._routers \u003d {}"}],"source_content_type":"text/x-python","patch_set":10,"id":"3f79a3b5_3f3e84b6","line":188,"range":{"start_line":188,"start_character":6,"end_line":188,"end_character":19},"updated":"2018-11-30 17:00:41.000000000","message":"This can be defined to that BaseRouterInfo file.","commit_id":"615b3dcf020cd47a9fc0ff59cf1e580b0e5f491c"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"aa03237b26a5ff0d47c271459e0082e6e3182828","unresolved":false,"context_lines":[{"line_number":185,"context_line":"                          host\u003dself.host, network_id\u003dfip_net)"},{"line_number":186,"context_line":""},{"line_number":187,"context_line":""},{"line_number":188,"context_line":"class RouterFactory(object):"},{"line_number":189,"context_line":""},{"line_number":190,"context_line":"    def __init__(self):"},{"line_number":191,"context_line":"        self._routers \u003d {}"}],"source_content_type":"text/x-python","patch_set":10,"id":"3f79a3b5_2d05f70f","line":188,"range":{"start_line":188,"start_character":6,"end_line":188,"end_character":19},"in_reply_to":"3f79a3b5_3f3e84b6","updated":"2018-12-01 02:05:28.000000000","message":"Thanks. As I answer the comments to previous reviewer, I will rebase the change conflicted. \n\nI thought if I rebase the change first, it makes reviewers more hard to notice the change. If I have to, I willing to rebase first.","commit_id":"615b3dcf020cd47a9fc0ff59cf1e580b0e5f491c"},{"author":{"_account_id":9396,"name":"igordcard","email":"igordcard@gmail.com","username":"igordcard"},"change_message_id":"3338fde8309db70084d42d96bc1e3f0171fc2860","unresolved":false,"context_lines":[{"line_number":221,"context_line":"        :raises: n_exc.RouterNotFoundInRouterFactory"},{"line_number":222,"context_line":"        \"\"\""},{"line_number":223,"context_line":"        try:"},{"line_number":224,"context_line":"            router \u003d self._routers[frozenset(features)]"},{"line_number":225,"context_line":"            return router(**kwargs)"},{"line_number":226,"context_line":"        except KeyError:"},{"line_number":227,"context_line":"            exc \u003d l3_exc.RouterNotFoundInRouterFactory("}],"source_content_type":"text/x-python","patch_set":15,"id":"9fdfeff1_2b8fc723","line":224,"updated":"2019-02-26 03:17:49.000000000","message":"With the introduction of OVS routers, this would also be a nice option to include the backend (ovs, linux) as a \"feature\". I\u0027m of the opinion that the whole RouterInfo architecture should be backend-agnostic but we are very far from that. Today, keeping the RouterInfos backend-specific while specifying the backend via a feature in order to get the right RouterInfo looks acceptable to me and a good fit for this patch.","commit_id":"edc610b8de24d4d49e4d77a98fe46dc2cd318e54"},{"author":{"_account_id":9531,"name":"liuyulong","display_name":"LIU Yulong","email":"i@liuyulong.me","username":"LIU-Yulong"},"change_message_id":"8e2e3a08c03fcd7f930df9c603eddc5688ab317d","unresolved":false,"context_lines":[{"line_number":386,"context_line":"            \u0027interface_driver\u0027: self.driver,"},{"line_number":387,"context_line":"        }"},{"line_number":388,"context_line":""},{"line_number":389,"context_line":"        if router.get(\u0027distributed\u0027):"},{"line_number":390,"context_line":"            kwargs[\u0027host\u0027] \u003d self.host"},{"line_number":391,"context_line":""},{"line_number":392,"context_line":"        if router.get(\u0027distributed\u0027) and router.get(\u0027ha\u0027):"},{"line_number":393,"context_line":"            # Case 1: If the router contains information about the HA interface"},{"line_number":394,"context_line":"            # and if the requesting agent is a DVR_SNAT agent then go ahead"},{"line_number":395,"context_line":"            # and create a HA router."},{"line_number":396,"context_line":"            # Case 2: If the router does not contain information about the HA"},{"line_number":397,"context_line":"            # interface this means that this DVR+HA router needs to host only"},{"line_number":398,"context_line":"            # the edge side of it, typically because it\u0027s landing on a node"},{"line_number":399,"context_line":"            # that needs to provision a router namespace because of a DVR"},{"line_number":400,"context_line":"            # service port (e.g. DHCP). So go ahead and create a regular DVR"},{"line_number":401,"context_line":"            # edge router."},{"line_number":402,"context_line":"            if (self.conf.agent_mode \u003d\u003d lib_const.L3_AGENT_MODE_DVR_SNAT and"},{"line_number":403,"context_line":"                    router.get(lib_const.HA_INTERFACE_KEY) is not None):"},{"line_number":404,"context_line":"                kwargs[\u0027state_change_callback\u0027] \u003d self.enqueue_state_change"},{"line_number":405,"context_line":"                return dvr_edge_ha_router.DvrEdgeHaRouter(*args, **kwargs)"},{"line_number":406,"context_line":""},{"line_number":407,"context_line":"        if router.get(\u0027distributed\u0027):"},{"line_number":408,"context_line":"            if self.conf.agent_mode \u003d\u003d lib_const.L3_AGENT_MODE_DVR_SNAT:"},{"line_number":409,"context_line":"                return dvr_router.DvrEdgeRouter(*args, **kwargs)"},{"line_number":410,"context_line":"            else:"},{"line_number":411,"context_line":"                return dvr_local_router.DvrLocalRouter(*args, **kwargs)"},{"line_number":412,"context_line":""},{"line_number":413,"context_line":"        if router.get(\u0027ha\u0027):"},{"line_number":414,"context_line":"            kwargs[\u0027state_change_callback\u0027] \u003d self.enqueue_state_change"},{"line_number":415,"context_line":"            return ha_router.HaRouter(*args, **kwargs)"},{"line_number":416,"context_line":""},{"line_number":417,"context_line":"        return legacy_router.LegacyRouter(*args, **kwargs)"},{"line_number":418,"context_line":""},{"line_number":419,"context_line":"    @lockutils.synchronized(\u0027resize_greenpool\u0027)"},{"line_number":420,"context_line":"    def _resize_process_pool(self):"}],"source_content_type":"text/x-python","patch_set":25,"id":"ffb9cba7_32690225","side":"PARENT","line":417,"range":{"start_line":389,"start_character":0,"end_line":417,"end_character":58},"updated":"2019-04-22 15:26:20.000000000","message":"In order to prevent unexpected regression on this complicated if-else conditions. Could you add test cases for these checks, let the cases go into each conditions and then check the final object type? Or it is already there?","commit_id":"bb9edb25b0f785aa7c54905b668a1e58ec742a8f"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"6489aa9c2183bbbffcba7a67c99550b9a89009f2","unresolved":false,"context_lines":[{"line_number":386,"context_line":"            \u0027interface_driver\u0027: self.driver,"},{"line_number":387,"context_line":"        }"},{"line_number":388,"context_line":""},{"line_number":389,"context_line":"        if router.get(\u0027distributed\u0027):"},{"line_number":390,"context_line":"            kwargs[\u0027host\u0027] \u003d self.host"},{"line_number":391,"context_line":""},{"line_number":392,"context_line":"        if router.get(\u0027distributed\u0027) and router.get(\u0027ha\u0027):"},{"line_number":393,"context_line":"            # Case 1: If the router contains information about the HA interface"},{"line_number":394,"context_line":"            # and if the requesting agent is a DVR_SNAT agent then go ahead"},{"line_number":395,"context_line":"            # and create a HA router."},{"line_number":396,"context_line":"            # Case 2: If the router does not contain information about the HA"},{"line_number":397,"context_line":"            # interface this means that this DVR+HA router needs to host only"},{"line_number":398,"context_line":"            # the edge side of it, typically because it\u0027s landing on a node"},{"line_number":399,"context_line":"            # that needs to provision a router namespace because of a DVR"},{"line_number":400,"context_line":"            # service port (e.g. DHCP). So go ahead and create a regular DVR"},{"line_number":401,"context_line":"            # edge router."},{"line_number":402,"context_line":"            if (self.conf.agent_mode \u003d\u003d lib_const.L3_AGENT_MODE_DVR_SNAT and"},{"line_number":403,"context_line":"                    router.get(lib_const.HA_INTERFACE_KEY) is not None):"},{"line_number":404,"context_line":"                kwargs[\u0027state_change_callback\u0027] \u003d self.enqueue_state_change"},{"line_number":405,"context_line":"                return dvr_edge_ha_router.DvrEdgeHaRouter(*args, **kwargs)"},{"line_number":406,"context_line":""},{"line_number":407,"context_line":"        if router.get(\u0027distributed\u0027):"},{"line_number":408,"context_line":"            if self.conf.agent_mode \u003d\u003d lib_const.L3_AGENT_MODE_DVR_SNAT:"},{"line_number":409,"context_line":"                return dvr_router.DvrEdgeRouter(*args, **kwargs)"},{"line_number":410,"context_line":"            else:"},{"line_number":411,"context_line":"                return dvr_local_router.DvrLocalRouter(*args, **kwargs)"},{"line_number":412,"context_line":""},{"line_number":413,"context_line":"        if router.get(\u0027ha\u0027):"},{"line_number":414,"context_line":"            kwargs[\u0027state_change_callback\u0027] \u003d self.enqueue_state_change"},{"line_number":415,"context_line":"            return ha_router.HaRouter(*args, **kwargs)"},{"line_number":416,"context_line":""},{"line_number":417,"context_line":"        return legacy_router.LegacyRouter(*args, **kwargs)"},{"line_number":418,"context_line":""},{"line_number":419,"context_line":"    @lockutils.synchronized(\u0027resize_greenpool\u0027)"},{"line_number":420,"context_line":"    def _resize_process_pool(self):"}],"source_content_type":"text/x-python","patch_set":25,"id":"ffb9cba7_40e60e47","side":"PARENT","line":417,"range":{"start_line":389,"start_character":0,"end_line":417,"end_character":58},"in_reply_to":"ffb9cba7_32690225","updated":"2019-04-23 05:54:12.000000000","message":"I added simple test cases in test_agent.py. Here is a test result at previous HEAD. (https://pastebin.com/T3E8eceh).","commit_id":"bb9edb25b0f785aa7c54905b668a1e58ec742a8f"}],"neutron/agent/l3/l3_agent_extension_api.py":[{"author":{"_account_id":9531,"name":"liuyulong","display_name":"LIU Yulong","email":"i@liuyulong.me","username":"LIU-Yulong"},"change_message_id":"82676d55de8fcace01a8d4e1e6f2b6dc6a091717","unresolved":false,"context_lines":[{"line_number":26,"context_line":"    agent\u0027s RouterInfo object."},{"line_number":27,"context_line":"    \u0027\u0027\u0027"},{"line_number":28,"context_line":""},{"line_number":29,"context_line":"    def __init__(self, router_info, router_factory):"},{"line_number":30,"context_line":"        self._router_info \u003d router_info"},{"line_number":31,"context_line":"        self._router_factory \u003d router_factory"},{"line_number":32,"context_line":""}],"source_content_type":"text/x-python","patch_set":10,"id":"3f79a3b5_5f3260f6","line":29,"range":{"start_line":29,"start_character":23,"end_line":29,"end_character":34},"updated":"2018-11-30 17:00:41.000000000","message":"router_info is already created here, what\u0027s this factory used for?","commit_id":"615b3dcf020cd47a9fc0ff59cf1e580b0e5f491c"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"aa03237b26a5ff0d47c271459e0082e6e3182828","unresolved":false,"context_lines":[{"line_number":26,"context_line":"    agent\u0027s RouterInfo object."},{"line_number":27,"context_line":"    \u0027\u0027\u0027"},{"line_number":28,"context_line":""},{"line_number":29,"context_line":"    def __init__(self, router_info, router_factory):"},{"line_number":30,"context_line":"        self._router_info \u003d router_info"},{"line_number":31,"context_line":"        self._router_factory \u003d router_factory"},{"line_number":32,"context_line":""}],"source_content_type":"text/x-python","patch_set":10,"id":"3f79a3b5_0d191b75","line":29,"range":{"start_line":29,"start_character":23,"end_line":29,"end_character":34},"in_reply_to":"3f79a3b5_5f3260f6","updated":"2018-12-01 02:05:28.000000000","message":"I think you already know router_info is just dict in which is saved created router_info class.\n\nAnd router_factory is a factory to make router_info itself. Naming is a little bit confusing though.","commit_id":"615b3dcf020cd47a9fc0ff59cf1e580b0e5f491c"},{"author":{"_account_id":9531,"name":"liuyulong","display_name":"LIU Yulong","email":"i@liuyulong.me","username":"LIU-Yulong"},"change_message_id":"82676d55de8fcace01a8d4e1e6f2b6dc6a091717","unresolved":false,"context_lines":[{"line_number":72,"context_line":""},{"line_number":73,"context_line":"    def register_router(self, features, router_cls):"},{"line_number":74,"context_line":"        \"\"\"Register router class with the given features.\"\"\""},{"line_number":75,"context_line":"        self._router_factory.register(features, router_cls)"}],"source_content_type":"text/x-python","patch_set":10,"id":"3f79a3b5_6dfbf915","line":75,"range":{"start_line":75,"start_character":38,"end_line":75,"end_character":58},"updated":"2018-11-30 17:00:41.000000000","message":"IMO, this should exchange order, `feature` is the input for initiating `a class`, or `a class` will be located by such `features`.","commit_id":"615b3dcf020cd47a9fc0ff59cf1e580b0e5f491c"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"aa03237b26a5ff0d47c271459e0082e6e3182828","unresolved":false,"context_lines":[{"line_number":72,"context_line":""},{"line_number":73,"context_line":"    def register_router(self, features, router_cls):"},{"line_number":74,"context_line":"        \"\"\"Register router class with the given features.\"\"\""},{"line_number":75,"context_line":"        self._router_factory.register(features, router_cls)"}],"source_content_type":"text/x-python","patch_set":10,"id":"3f79a3b5_4d44f34e","line":75,"range":{"start_line":75,"start_character":38,"end_line":75,"end_character":58},"in_reply_to":"3f79a3b5_6dfbf915","updated":"2018-12-01 02:05:28.000000000","message":"It makes sense, but I thought features are a kind of key value for creation router class, so that I made this order to follow key, value convention.","commit_id":"615b3dcf020cd47a9fc0ff59cf1e580b0e5f491c"},{"author":{"_account_id":1131,"name":"Brian Haley","email":"haleyb.dev@gmail.com","username":"brian-haley"},"change_message_id":"b898a76241d87bf1b1b3f9ecfeda3664170d26f2","unresolved":false,"context_lines":[{"line_number":28,"context_line":""},{"line_number":29,"context_line":"    def __init__(self, router_info, router_factory):"},{"line_number":30,"context_line":"        self._router_info \u003d router_info"},{"line_number":31,"context_line":"        self._router_factory \u003d router_factory"},{"line_number":32,"context_line":""},{"line_number":33,"context_line":"    def _local_namespaces(self):"},{"line_number":34,"context_line":"        local_ns_list \u003d ip_lib.list_network_namespaces()"}],"source_content_type":"text/x-python","patch_set":22,"id":"3fce034c_2156515e","line":31,"updated":"2019-04-15 16:33:16.000000000","message":"So does this break fwaas tests?\n\nhttp://codesearch.openstack.org/?q\u003dL3AgentExtensionAPI\u0026i\u003dnope\u0026files\u003d\u0026repos\u003d\n\nFor that reason this should have a release note describing the added argument here.","commit_id":"98e8f8c4016abdb9ae651be8bfe6ff0d7da31e2b"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"b572ddc4553e4ec9abd0b93fd5b9bec5dd215ca8","unresolved":false,"context_lines":[{"line_number":28,"context_line":""},{"line_number":29,"context_line":"    def __init__(self, router_info, router_factory):"},{"line_number":30,"context_line":"        self._router_info \u003d router_info"},{"line_number":31,"context_line":"        self._router_factory \u003d router_factory"},{"line_number":32,"context_line":""},{"line_number":33,"context_line":"    def _local_namespaces(self):"},{"line_number":34,"context_line":"        local_ns_list \u003d ip_lib.list_network_namespaces()"}],"source_content_type":"text/x-python","patch_set":22,"id":"3fce034c_2a0ce139","line":31,"in_reply_to":"3fce034c_2156515e","updated":"2019-04-16 01:54:07.000000000","message":"Thanks. I added a release note. I will make PR to fwass side. I did not notice there is a service like codesearch. Cool.","commit_id":"98e8f8c4016abdb9ae651be8bfe6ff0d7da31e2b"},{"author":{"_account_id":11975,"name":"Slawek Kaplonski","email":"skaplons@redhat.com","username":"slaweq"},"change_message_id":"510e642d6690cba6ca9821ef8333ffff07eb9a6b","unresolved":false,"context_lines":[{"line_number":28,"context_line":""},{"line_number":29,"context_line":"    def __init__(self, router_info, router_factory):"},{"line_number":30,"context_line":"        self._router_info \u003d router_info"},{"line_number":31,"context_line":"        self._router_factory \u003d router_factory"},{"line_number":32,"context_line":""},{"line_number":33,"context_line":"    def _local_namespaces(self):"},{"line_number":34,"context_line":"        local_ns_list \u003d ip_lib.list_network_namespaces()"}],"source_content_type":"text/x-python","patch_set":22,"id":"3fce034c_5c72224b","line":31,"in_reply_to":"3fce034c_2a0ce139","updated":"2019-04-18 07:59:32.000000000","message":"Good catch Brian, thx :)","commit_id":"98e8f8c4016abdb9ae651be8bfe6ff0d7da31e2b"},{"author":{"_account_id":11975,"name":"Slawek Kaplonski","email":"skaplons@redhat.com","username":"slaweq"},"change_message_id":"90d17268e423fb60f0732f337b89577956299de6","unresolved":false,"context_lines":[{"line_number":26,"context_line":"    agent\u0027s RouterInfo object."},{"line_number":27,"context_line":"    \u0027\u0027\u0027"},{"line_number":28,"context_line":""},{"line_number":29,"context_line":"    def __init__(self, router_info, router_factory):"},{"line_number":30,"context_line":"        self._router_info \u003d router_info"},{"line_number":31,"context_line":"        self._router_factory \u003d router_factory"},{"line_number":32,"context_line":""}],"source_content_type":"text/x-python","patch_set":25,"id":"3fce034c_fc2c2e03","line":29,"range":{"start_line":29,"start_character":36,"end_line":29,"end_character":50},"updated":"2019-04-18 08:07:03.000000000","message":"One more question: if this can be None (as You did in FwaaS repo), can\u0027t we make it optional with None as default value? That way we would not break anything in other repositories, right?","commit_id":"59accf0e8c9c53a668444ad7d74a86ddad46966e"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"aa8d6dca53f13629e0e73cebd87cc3282bf9e279","unresolved":false,"context_lines":[{"line_number":26,"context_line":"    agent\u0027s RouterInfo object."},{"line_number":27,"context_line":"    \u0027\u0027\u0027"},{"line_number":28,"context_line":""},{"line_number":29,"context_line":"    def __init__(self, router_info, router_factory):"},{"line_number":30,"context_line":"        self._router_info \u003d router_info"},{"line_number":31,"context_line":"        self._router_factory \u003d router_factory"},{"line_number":32,"context_line":""}],"source_content_type":"text/x-python","patch_set":25,"id":"3fce034c_b7e55f0b","line":29,"range":{"start_line":29,"start_character":36,"end_line":29,"end_character":50},"in_reply_to":"3fce034c_fc2c2e03","updated":"2019-04-18 08:51:51.000000000","message":"Yes, you are right. But in that case, I have to add conditional code in register_router(). imho, L3AgentExtensionAPI interface should be completed without any condition. For the test cases, I just pass None because the test cases were not related to the router_factory at all.","commit_id":"59accf0e8c9c53a668444ad7d74a86ddad46966e"},{"author":{"_account_id":1131,"name":"Brian Haley","email":"haleyb.dev@gmail.com","username":"brian-haley"},"change_message_id":"51e4c57e0decdf99925a2f2e670a88c86ec7c449","unresolved":false,"context_lines":[{"line_number":72,"context_line":""},{"line_number":73,"context_line":"    def register_router(self, features, router_cls):"},{"line_number":74,"context_line":"        \"\"\"Register router class with the given features. This is for the"},{"line_number":75,"context_line":"        plugin to ovrride their own ``router_info`` class."},{"line_number":76,"context_line":"        \"\"\""},{"line_number":77,"context_line":"        self._router_factory.register(features, router_cls)"}],"source_content_type":"text/x-python","patch_set":29,"id":"ffb9cba7_379c46bf","line":75,"range":{"start_line":75,"start_character":18,"end_line":75,"end_character":25},"updated":"2019-04-25 14:09:52.000000000","message":"s/override with","commit_id":"a974d545f3284cc2214cf8fbb620e940ab9302bb"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"425339b311d57946aebc1afa8a6885637f8ad1cc","unresolved":false,"context_lines":[{"line_number":72,"context_line":""},{"line_number":73,"context_line":"    def register_router(self, features, router_cls):"},{"line_number":74,"context_line":"        \"\"\"Register router class with the given features. This is for the"},{"line_number":75,"context_line":"        plugin to ovrride their own ``router_info`` class."},{"line_number":76,"context_line":"        \"\"\""},{"line_number":77,"context_line":"        self._router_factory.register(features, router_cls)"}],"source_content_type":"text/x-python","patch_set":29,"id":"ffb9cba7_da5aa6f1","line":75,"range":{"start_line":75,"start_character":18,"end_line":75,"end_character":25},"in_reply_to":"ffb9cba7_379c46bf","updated":"2019-04-26 01:21:07.000000000","message":"Done","commit_id":"a974d545f3284cc2214cf8fbb620e940ab9302bb"},{"author":{"_account_id":11975,"name":"Slawek Kaplonski","email":"skaplons@redhat.com","username":"slaweq"},"change_message_id":"1b5e3989f995b22b2f7ddcf30f9d0becf327214f","unresolved":false,"context_lines":[{"line_number":72,"context_line":""},{"line_number":73,"context_line":"    def register_router(self, features, router_cls):"},{"line_number":74,"context_line":"        \"\"\"Register router class with the given features. This is for the"},{"line_number":75,"context_line":"        plugin to ovrride with their own ``router_info`` class."},{"line_number":76,"context_line":"        \"\"\""},{"line_number":77,"context_line":"        self._router_factory.register(features, router_cls)"}],"source_content_type":"text/x-python","patch_set":31,"id":"ffb9cba7_e2d49cbf","line":75,"range":{"start_line":75,"start_character":18,"end_line":75,"end_character":25},"updated":"2019-04-26 08:04:01.000000000","message":"nitty nit: s/override - but please don\u0027t respin only for that :)","commit_id":"ec875b42b6e92300093c895668532966de9e1327"}],"neutron/agent/l3/router_info.py":[{"author":{"_account_id":16688,"name":"Rodolfo Alonso","email":"ralonsoh@redhat.com","username":"rodolfo-alonso-hernandez"},"change_message_id":"8b730dc13bebcdeb9eccbbba9e4aeb00870f9764","unresolved":false,"context_lines":[{"line_number":100,"context_line":""},{"line_number":101,"context_line":"    @abc.abstractmethod"},{"line_number":102,"context_line":"    def delete(self, agent):"},{"line_number":103,"context_line":"        pass"},{"line_number":104,"context_line":""},{"line_number":105,"context_line":"    @abc.abstractmethod"},{"line_number":106,"context_line":"    def process(self, agent):"}],"source_content_type":"text/x-python","patch_set":5,"id":"3f79a3b5_9760100e","line":103,"updated":"2018-11-28 16:27:16.000000000","message":"An abs method doesn\u0027t need \"pass\" or anything","commit_id":"7bc8d661611582b675b5624d5020dfa5f619d1b8"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"54a8a3c23918a1e842e068598fddd1b9b236c76b","unresolved":false,"context_lines":[{"line_number":100,"context_line":""},{"line_number":101,"context_line":"    @abc.abstractmethod"},{"line_number":102,"context_line":"    def delete(self, agent):"},{"line_number":103,"context_line":"        pass"},{"line_number":104,"context_line":""},{"line_number":105,"context_line":"    @abc.abstractmethod"},{"line_number":106,"context_line":"    def process(self, agent):"}],"source_content_type":"text/x-python","patch_set":5,"id":"3f79a3b5_da5f850f","line":103,"in_reply_to":"3f79a3b5_9760100e","updated":"2018-11-29 02:19:43.000000000","message":"I grep the whole neutron codebase and pass for abstractmethod seems to be case by case. If there is any consensus for the convention, I will follow","commit_id":"7bc8d661611582b675b5624d5020dfa5f619d1b8"},{"author":{"_account_id":16688,"name":"Rodolfo Alonso","email":"ralonsoh@redhat.com","username":"rodolfo-alonso-hernandez"},"change_message_id":"8b730dc13bebcdeb9eccbbba9e4aeb00870f9764","unresolved":false,"context_lines":[{"line_number":111,"context_line":""},{"line_number":112,"context_line":"        :param agent: Passes the agent in order to send RPC messages."},{"line_number":113,"context_line":"        \"\"\""},{"line_number":114,"context_line":"        pass"},{"line_number":115,"context_line":""},{"line_number":116,"context_line":"    def get_ex_gw_port(self):"},{"line_number":117,"context_line":"        return self.router.get(\u0027gw_port\u0027)"}],"source_content_type":"text/x-python","patch_set":5,"id":"3f79a3b5_5766f828","line":114,"range":{"start_line":114,"start_character":8,"end_line":114,"end_character":12},"updated":"2018-11-28 16:27:16.000000000","message":"ditto","commit_id":"7bc8d661611582b675b5624d5020dfa5f619d1b8"},{"author":{"_account_id":16688,"name":"Rodolfo Alonso","email":"ralonsoh@redhat.com","username":"rodolfo-alonso-hernandez"},"change_message_id":"8b730dc13bebcdeb9eccbbba9e4aeb00870f9764","unresolved":false,"context_lines":[{"line_number":167,"context_line":""},{"line_number":168,"context_line":"    def initialize(self, process_monitor):"},{"line_number":169,"context_line":"        super(RouterInfo, self).initialize(process_monitor)"},{"line_number":170,"context_line":"        self.process_monitor \u003d process_monitor"},{"line_number":171,"context_line":"        self.radvd \u003d ra.DaemonMonitor(self.router_id,"},{"line_number":172,"context_line":"                                      self.ns_name,"},{"line_number":173,"context_line":"                                      process_monitor,"}],"source_content_type":"text/x-python","patch_set":5,"id":"3f79a3b5_77469480","line":170,"range":{"start_line":170,"start_character":8,"end_line":170,"end_character":46},"updated":"2018-11-28 16:27:16.000000000","message":"Do you need this now?","commit_id":"7bc8d661611582b675b5624d5020dfa5f619d1b8"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"54a8a3c23918a1e842e068598fddd1b9b236c76b","unresolved":false,"context_lines":[{"line_number":167,"context_line":""},{"line_number":168,"context_line":"    def initialize(self, process_monitor):"},{"line_number":169,"context_line":"        super(RouterInfo, self).initialize(process_monitor)"},{"line_number":170,"context_line":"        self.process_monitor \u003d process_monitor"},{"line_number":171,"context_line":"        self.radvd \u003d ra.DaemonMonitor(self.router_id,"},{"line_number":172,"context_line":"                                      self.ns_name,"},{"line_number":173,"context_line":"                                      process_monitor,"}],"source_content_type":"text/x-python","patch_set":5,"id":"3f79a3b5_5a437547","line":170,"range":{"start_line":170,"start_character":8,"end_line":170,"end_character":46},"in_reply_to":"3f79a3b5_77469480","updated":"2018-11-29 02:19:43.000000000","message":"Thanks! I made a mistake. Fixed.","commit_id":"7bc8d661611582b675b5624d5020dfa5f619d1b8"},{"author":{"_account_id":9531,"name":"liuyulong","display_name":"LIU Yulong","email":"i@liuyulong.me","username":"LIU-Yulong"},"change_message_id":"82676d55de8fcace01a8d4e1e6f2b6dc6a091717","unresolved":false,"context_lines":[{"line_number":46,"context_line":""},{"line_number":47,"context_line":""},{"line_number":48,"context_line":"# TODO(ileixe): remove when neutron-lib version is available"},{"line_number":49,"context_line":"class RouterNotFoundInRouterFactory(exceptions.NeutronException):"},{"line_number":50,"context_line":"    message \u003d _(\"Router \u0027%(router_id)s\u0027 with features \u0027%(features)s\u0027 could \""},{"line_number":51,"context_line":"                \"not be found in router factory.\")"},{"line_number":52,"context_line":""},{"line_number":53,"context_line":""},{"line_number":54,"context_line":"@six.add_metaclass(abc.ABCMeta)"}],"source_content_type":"text/x-python","patch_set":10,"id":"3f79a3b5_edb38998","line":51,"range":{"start_line":49,"start_character":0,"end_line":51,"end_character":50},"updated":"2018-11-30 17:00:41.000000000","message":"You can add this exception to neutron.common.exceptions temporarily.","commit_id":"615b3dcf020cd47a9fc0ff59cf1e580b0e5f491c"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"aa03237b26a5ff0d47c271459e0082e6e3182828","unresolved":false,"context_lines":[{"line_number":46,"context_line":""},{"line_number":47,"context_line":""},{"line_number":48,"context_line":"# TODO(ileixe): remove when neutron-lib version is available"},{"line_number":49,"context_line":"class RouterNotFoundInRouterFactory(exceptions.NeutronException):"},{"line_number":50,"context_line":"    message \u003d _(\"Router \u0027%(router_id)s\u0027 with features \u0027%(features)s\u0027 could \""},{"line_number":51,"context_line":"                \"not be found in router factory.\")"},{"line_number":52,"context_line":""},{"line_number":53,"context_line":""},{"line_number":54,"context_line":"@six.add_metaclass(abc.ABCMeta)"}],"source_content_type":"text/x-python","patch_set":10,"id":"3f79a3b5_0d4efb6c","line":51,"range":{"start_line":49,"start_character":0,"end_line":51,"end_character":50},"in_reply_to":"3f79a3b5_edb38998","updated":"2018-12-01 02:05:28.000000000","message":"Done","commit_id":"615b3dcf020cd47a9fc0ff59cf1e580b0e5f491c"},{"author":{"_account_id":9531,"name":"liuyulong","display_name":"LIU Yulong","email":"i@liuyulong.me","username":"LIU-Yulong"},"change_message_id":"82676d55de8fcace01a8d4e1e6f2b6dc6a091717","unresolved":false,"context_lines":[{"line_number":52,"context_line":""},{"line_number":53,"context_line":""},{"line_number":54,"context_line":"@six.add_metaclass(abc.ABCMeta)"},{"line_number":55,"context_line":"class BaseRouterInfo(object):"},{"line_number":56,"context_line":""},{"line_number":57,"context_line":"    def __init__(self,"},{"line_number":58,"context_line":"                 agent,"}],"source_content_type":"text/x-python","patch_set":10,"id":"3f79a3b5_cd31ed0b","line":55,"range":{"start_line":55,"start_character":6,"end_line":55,"end_character":20},"updated":"2018-11-30 17:00:41.000000000","message":"https://review.openstack.org/#/c/528336/22/neutron/agent/l3/router_info_base.py\nAs the former reviews have already pointed out, you have conflicts with this.","commit_id":"615b3dcf020cd47a9fc0ff59cf1e580b0e5f491c"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"aa03237b26a5ff0d47c271459e0082e6e3182828","unresolved":false,"context_lines":[{"line_number":52,"context_line":""},{"line_number":53,"context_line":""},{"line_number":54,"context_line":"@six.add_metaclass(abc.ABCMeta)"},{"line_number":55,"context_line":"class BaseRouterInfo(object):"},{"line_number":56,"context_line":""},{"line_number":57,"context_line":"    def __init__(self,"},{"line_number":58,"context_line":"                 agent,"}],"source_content_type":"text/x-python","patch_set":10,"id":"3f79a3b5_2d53b717","line":55,"range":{"start_line":55,"start_character":6,"end_line":55,"end_character":20},"in_reply_to":"3f79a3b5_cd31ed0b","updated":"2018-12-01 02:05:28.000000000","message":"ditto","commit_id":"615b3dcf020cd47a9fc0ff59cf1e580b0e5f491c"},{"author":{"_account_id":9396,"name":"igordcard","email":"igordcard@gmail.com","username":"igordcard"},"change_message_id":"3338fde8309db70084d42d96bc1e3f0171fc2860","unresolved":false,"context_lines":[{"line_number":45,"context_line":""},{"line_number":46,"context_line":""},{"line_number":47,"context_line":"@six.add_metaclass(abc.ABCMeta)"},{"line_number":48,"context_line":"class BaseRouterInfo(object):"},{"line_number":49,"context_line":""},{"line_number":50,"context_line":"    def __init__(self,"},{"line_number":51,"context_line":"                 agent,"}],"source_content_type":"text/x-python","patch_set":15,"id":"9fdfeff1_2bb827c6","line":48,"range":{"start_line":48,"start_character":6,"end_line":48,"end_character":20},"updated":"2019-02-26 03:17:49.000000000","message":"Context from my re-refactor of the L3 patch which I\u0027ll be publishing soon: I am also creating a higher-level parent class, simply called RouterInfo.","commit_id":"edc610b8de24d4d49e4d77a98fe46dc2cd318e54"},{"author":{"_account_id":9396,"name":"igordcard","email":"igordcard@gmail.com","username":"igordcard"},"change_message_id":"3338fde8309db70084d42d96bc1e3f0171fc2860","unresolved":false,"context_lines":[{"line_number":122,"context_line":"        return self.get_external_device_name(ex_gw_port[\u0027id\u0027])"},{"line_number":123,"context_line":""},{"line_number":124,"context_line":""},{"line_number":125,"context_line":"class RouterInfo(BaseRouterInfo):"},{"line_number":126,"context_line":""},{"line_number":127,"context_line":"    def __init__(self,"},{"line_number":128,"context_line":"                 agent,"}],"source_content_type":"text/x-python","patch_set":15,"id":"9fdfeff1_4bbd6bb5","line":125,"range":{"start_line":125,"start_character":6,"end_line":125,"end_character":16},"updated":"2019-02-26 03:17:49.000000000","message":"Context from my re-refactor of the L3 patch which I\u0027ll be publishing soon: Instead of keeping the RouterInfo class name, I am renaming it to LinuxRouterInfo to reflect that that it\u0027s backend-specific to Linux. I am also introducing a sibling called OVSRouterInfo.","commit_id":"edc610b8de24d4d49e4d77a98fe46dc2cd318e54"},{"author":{"_account_id":11975,"name":"Slawek Kaplonski","email":"skaplons@redhat.com","username":"slaweq"},"change_message_id":"dd958c33aa75401effe01774fa7ad32f83846dc2","unresolved":false,"context_lines":[{"line_number":21,"context_line":"from neutron_lib.utils import helpers"},{"line_number":22,"context_line":"from oslo_log import log as logging"},{"line_number":23,"context_line":""},{"line_number":24,"context_line":"import six"},{"line_number":25,"context_line":""},{"line_number":26,"context_line":"from neutron._i18n import _"},{"line_number":27,"context_line":"from neutron.agent.l3 import namespaces"}],"source_content_type":"text/x-python","patch_set":18,"id":"3fce034c_8aee6a86","line":24,"updated":"2019-04-12 08:31:31.000000000","message":"this should be moved to the section above","commit_id":"1a7b33179aea754aef3e2b90f1b224b90b306767"},{"author":{"_account_id":11975,"name":"Slawek Kaplonski","email":"skaplons@redhat.com","username":"slaweq"},"change_message_id":"b68d23e20454b381daf5b077b77582df68659b1d","unresolved":false,"context_lines":[{"line_number":21,"context_line":"from neutron_lib.utils import helpers"},{"line_number":22,"context_line":"from oslo_log import log as logging"},{"line_number":23,"context_line":""},{"line_number":24,"context_line":"import six"},{"line_number":25,"context_line":""},{"line_number":26,"context_line":"from neutron._i18n import _"},{"line_number":27,"context_line":"from neutron.agent.l3 import namespaces"}],"source_content_type":"text/x-python","patch_set":18,"id":"3fce034c_6ea8d21e","line":24,"in_reply_to":"3fce034c_1304f214","updated":"2019-04-15 08:06:31.000000000","message":"yep, that is fine, thx","commit_id":"1a7b33179aea754aef3e2b90f1b224b90b306767"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"aae7362173584af1edbcc1f53709efd3fea3fa7d","unresolved":false,"context_lines":[{"line_number":21,"context_line":"from neutron_lib.utils import helpers"},{"line_number":22,"context_line":"from oslo_log import log as logging"},{"line_number":23,"context_line":""},{"line_number":24,"context_line":"import six"},{"line_number":25,"context_line":""},{"line_number":26,"context_line":"from neutron._i18n import _"},{"line_number":27,"context_line":"from neutron.agent.l3 import namespaces"}],"source_content_type":"text/x-python","patch_set":18,"id":"3fce034c_1304f214","line":24,"in_reply_to":"3fce034c_8aee6a86","updated":"2019-04-12 09:22:23.000000000","message":"I\u0027m not sure where is the \u0027above\u0027 since exist codes are varied. Let me know if this fix is not you meant.","commit_id":"1a7b33179aea754aef3e2b90f1b224b90b306767"},{"author":{"_account_id":30156,"name":"Igor D.C.","email":"igor.duarte.cardoso@intel.com","username":"igordc"},"change_message_id":"c00d830c87b9ab6b09c8672e1b55be45a5f53741","unresolved":false,"context_lines":[{"line_number":14,"context_line":""},{"line_number":15,"context_line":"import abc"},{"line_number":16,"context_line":"import collections"},{"line_number":17,"context_line":"import six"},{"line_number":18,"context_line":""},{"line_number":19,"context_line":"import netaddr"},{"line_number":20,"context_line":"from neutron_lib import constants as lib_constants"}],"source_content_type":"text/x-python","patch_set":20,"id":"3fce034c_1c92b6f7","line":17,"range":{"start_line":17,"start_character":0,"end_line":17,"end_character":10},"updated":"2019-04-12 23:33:40.000000000","message":"Move it to the second section, since it\u0027s a third-party module. Right after from \"oslo_log import log as logging\", no empty line.","commit_id":"c64cc8a05d2c018ff03f2ba52d395245d6c6348c"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"08ef6bd7c6fb9a53ea5003caf5b79b9faecffbbc","unresolved":false,"context_lines":[{"line_number":14,"context_line":""},{"line_number":15,"context_line":"import abc"},{"line_number":16,"context_line":"import collections"},{"line_number":17,"context_line":"import six"},{"line_number":18,"context_line":""},{"line_number":19,"context_line":"import netaddr"},{"line_number":20,"context_line":"from neutron_lib import constants as lib_constants"}],"source_content_type":"text/x-python","patch_set":20,"id":"3fce034c_02d1f0cd","line":17,"range":{"start_line":17,"start_character":0,"end_line":17,"end_character":10},"in_reply_to":"3fce034c_1c92b6f7","updated":"2019-04-13 01:25:41.000000000","message":"Thanks fixed.","commit_id":"c64cc8a05d2c018ff03f2ba52d395245d6c6348c"}],"neutron/common/exceptions.py":[{"author":{"_account_id":5367,"name":"boden","email":"bodenvmw@gmail.com","username":"boden"},"change_message_id":"1a4060d49ce8e438e26a769a9107aa99dcf2a046","unresolved":false,"context_lines":[{"line_number":132,"context_line":""},{"line_number":133,"context_line":""},{"line_number":134,"context_line":"# TODO(ileixe): remove when neutron-lib version is available"},{"line_number":135,"context_line":"class RouterNotFoundInRouterFactory(exceptions.NeutronException):"},{"line_number":136,"context_line":"    message \u003d _(\"Router \u0027%(router_id)s\u0027 with features \u0027%(features)s\u0027 could \""},{"line_number":137,"context_line":"                \"not be found in the router factory.\")"}],"source_content_type":"text/x-python","patch_set":14,"id":"3f79a3b5_aa17fe41","line":135,"range":{"start_line":135,"start_character":6,"end_line":135,"end_character":35},"updated":"2018-12-10 15:23:57.000000000","message":"This module has been rehomed into neutron-lib so this exception should go into lib, not neutron.","commit_id":"13adc6b8e2349f0039f6f0206cf09d534dbfe780"},{"author":{"_account_id":5367,"name":"boden","email":"bodenvmw@gmail.com","username":"boden"},"change_message_id":"165ff54880e5b957761cf414b3cc26def80f7780","unresolved":false,"context_lines":[{"line_number":132,"context_line":""},{"line_number":133,"context_line":""},{"line_number":134,"context_line":"# TODO(ileixe): remove when neutron-lib version is available"},{"line_number":135,"context_line":"class RouterNotFoundInRouterFactory(exceptions.NeutronException):"},{"line_number":136,"context_line":"    message \u003d _(\"Router \u0027%(router_id)s\u0027 with features \u0027%(features)s\u0027 could \""},{"line_number":137,"context_line":"                \"not be found in the router factory.\")"}],"source_content_type":"text/x-python","patch_set":14,"id":"ffd0ebdf_cf4492ba","line":135,"range":{"start_line":135,"start_character":6,"end_line":135,"end_character":35},"in_reply_to":"3f79a3b5_aa17fe41","updated":"2019-01-03 13:29:40.000000000","message":"See https://review.openstack.org/#/c/628004/","commit_id":"13adc6b8e2349f0039f6f0206cf09d534dbfe780"}],"neutron/tests/unit/agent/l3/test_agent.py":[{"author":{"_account_id":9531,"name":"liuyulong","display_name":"LIU Yulong","email":"i@liuyulong.me","username":"LIU-Yulong"},"change_message_id":"ec8b47d36ab155832961901aa944cd5433470735","unresolved":false,"context_lines":[{"line_number":430,"context_line":"            self.assertEqual(len(stale_router_ids), destroy_proxy.call_count)"},{"line_number":431,"context_line":"            destroy_proxy.assert_has_calls(expected_calls, any_order\u003dTrue)"},{"line_number":432,"context_line":""},{"line_number":433,"context_line":"    def test_create_router(self):"},{"line_number":434,"context_line":"        agent \u003d l3_agent.L3NATAgent(HOSTNAME, self.conf)"},{"line_number":435,"context_line":""},{"line_number":436,"context_line":"        expected_routers \u003d {"},{"line_number":437,"context_line":"            frozenset([]):"},{"line_number":438,"context_line":"                legacy_router.LegacyRouter,"},{"line_number":439,"context_line":"            frozenset([\u0027ha\u0027]):"},{"line_number":440,"context_line":"                ha_router.HaRouter,"},{"line_number":441,"context_line":"            frozenset([\u0027distributed\u0027]):"},{"line_number":442,"context_line":"                dvr_local_router.DvrLocalRouter,"},{"line_number":443,"context_line":"            frozenset([\u0027ha\u0027, \u0027distributed\u0027]):"},{"line_number":444,"context_line":"                dvr_local_router.DvrLocalRouter"},{"line_number":445,"context_line":"        }"},{"line_number":446,"context_line":""},{"line_number":447,"context_line":"        for features, expected_router in expected_routers.items():"},{"line_number":448,"context_line":"            router_dict \u003d {f: True for f in features}"},{"line_number":449,"context_line":""},{"line_number":450,"context_line":"            router \u003d agent._create_router(_uuid(), router_dict).__class__"},{"line_number":451,"context_line":"            self.assertEqual(router, expected_router)"},{"line_number":452,"context_line":""},{"line_number":453,"context_line":"    def test_create_router_dvr_snat_mode(self):"},{"line_number":454,"context_line":"        self.conf.set_override(\u0027agent_mode\u0027, lib_constants.L3_AGENT_MODE_DVR_SNAT)"},{"line_number":455,"context_line":"        agent \u003d l3_agent.L3NATAgent(HOSTNAME, self.conf)"},{"line_number":456,"context_line":""},{"line_number":457,"context_line":"        expected_routers \u003d {"},{"line_number":458,"context_line":"            frozenset([]):"},{"line_number":459,"context_line":"                legacy_router.LegacyRouter,"},{"line_number":460,"context_line":"            frozenset([\u0027ha\u0027]):"},{"line_number":461,"context_line":"                ha_router.HaRouter,"},{"line_number":462,"context_line":"            frozenset([\u0027distributed\u0027]):"},{"line_number":463,"context_line":"                dvr_router.DvrEdgeRouter,"},{"line_number":464,"context_line":"            frozenset([\u0027ha\u0027, \u0027distributed\u0027]):"},{"line_number":465,"context_line":"                dvr_edge_ha_router.DvrEdgeHaRouter"},{"line_number":466,"context_line":"        }"},{"line_number":467,"context_line":""},{"line_number":468,"context_line":"        for features, expected_router in expected_routers.items():"},{"line_number":469,"context_line":"            router_dict \u003d {f: True for f in features}"},{"line_number":470,"context_line":"            router_dict[lib_constants.HA_INTERFACE_KEY] \u003d True"},{"line_number":471,"context_line":""},{"line_number":472,"context_line":"            router \u003d agent._create_router(_uuid(), router_dict).__class__"},{"line_number":473,"context_line":"            self.assertEqual(router, expected_router)"},{"line_number":474,"context_line":""},{"line_number":475,"context_line":"    def test_router_info_create(self):"},{"line_number":476,"context_line":"        id \u003d _uuid()"}],"source_content_type":"text/x-python","patch_set":26,"id":"ffb9cba7_e6887772","line":473,"range":{"start_line":433,"start_character":0,"end_line":473,"end_character":53},"updated":"2019-04-23 10:18:29.000000000","message":"Sorry for the nit pick.\nActually the cases here cannot ensure there is no regression. You just tested the new code.\nIMO, you should add cases for the function \"_create_router\" like this:\n\ndef test__create_router_legacy():\n    router_id \u003d a_fake_id\n    router \u003d {\"ha\": False, \"distributed\": False, \"anything else needed\"}\n    router_info \u003d agent._create_router(router_id, router)\n    self.assertIsTrue(isinstance(router_info, LegacyRouter))\n\ndef test__create_router_ha():\n    router_id \u003d a_fake_id\n    router \u003d {\"ha\": True, \"distributed\": False, \"anything else needed\"}\n    router_info \u003d agent._create_router(router_id, router)\n    self.assertIsTrue(isinstance(router_info, HaRouter))\n\n\ndef test__create_router_dvr_agent_mode_snat()\n...\ndef test__create_router_dvr_ha_agent_mode_snat()\n...\n\ndef test__create_router_dvr_agent_mode_dvr()\n...\ndef test__create_router_dvr_ha_agent_mode_dvr()\n...","commit_id":"fd6ee44c44de2694e50ca3dda1648448dff78de1"},{"author":{"_account_id":9531,"name":"liuyulong","display_name":"LIU Yulong","email":"i@liuyulong.me","username":"LIU-Yulong"},"change_message_id":"c931c8b6c4a7a138d7d40df29cab09cfd84b2fbf","unresolved":false,"context_lines":[{"line_number":436,"context_line":"        agent \u003d l3_agent.L3NATAgent(HOSTNAME, self.conf)"},{"line_number":437,"context_line":"        router_info \u003d agent._create_router(_uuid(), router)"},{"line_number":438,"context_line":""},{"line_number":439,"context_line":"        self.assertEqual(type(router_info), legacy_router.LegacyRouter)"},{"line_number":440,"context_line":""},{"line_number":441,"context_line":"    def test__create_router_ha_agent(self):"},{"line_number":442,"context_line":"        router \u003d {\u0027distributed\u0027: False, \u0027ha\u0027: True}"}],"source_content_type":"text/x-python","patch_set":27,"id":"ffb9cba7_d5c5c63d","line":439,"range":{"start_line":439,"start_character":25,"end_line":439,"end_character":29},"updated":"2019-04-24 06:33:36.000000000","message":"Nice, that isinstance will return Ture for the parent class too. It is inaccurate. Great work!","commit_id":"1d2d07b226dfb133ac7dfb0574b9299efe50cd7d"},{"author":{"_account_id":11975,"name":"Slawek Kaplonski","email":"skaplons@redhat.com","username":"slaweq"},"change_message_id":"3c951868e1ddca190c6d0bcbf8cec226055603bd","unresolved":false,"context_lines":[{"line_number":436,"context_line":"        agent \u003d l3_agent.L3NATAgent(HOSTNAME, self.conf)"},{"line_number":437,"context_line":"        router_info \u003d agent._create_router(_uuid(), router)"},{"line_number":438,"context_line":""},{"line_number":439,"context_line":"        self.assertEqual(type(router_info), legacy_router.LegacyRouter)"},{"line_number":440,"context_line":""},{"line_number":441,"context_line":"    def test__create_router_ha_agent(self):"},{"line_number":442,"context_line":"        router \u003d {\u0027distributed\u0027: False, \u0027ha\u0027: True}"}],"source_content_type":"text/x-python","patch_set":27,"id":"ffb9cba7_da971f90","line":439,"range":{"start_line":439,"start_character":25,"end_line":439,"end_character":29},"in_reply_to":"ffb9cba7_d5c5c63d","updated":"2019-04-24 20:36:23.000000000","message":"we are generally using pattern:\n\n    self.assertEqual(expected, actual)\n\nplease adjust it here and in all other places in Your patch.","commit_id":"1d2d07b226dfb133ac7dfb0574b9299efe50cd7d"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"6cf0b8441f807916fa410754603e4e2b3870698d","unresolved":false,"context_lines":[{"line_number":436,"context_line":"        agent \u003d l3_agent.L3NATAgent(HOSTNAME, self.conf)"},{"line_number":437,"context_line":"        router_info \u003d agent._create_router(_uuid(), router)"},{"line_number":438,"context_line":""},{"line_number":439,"context_line":"        self.assertEqual(type(router_info), legacy_router.LegacyRouter)"},{"line_number":440,"context_line":""},{"line_number":441,"context_line":"    def test__create_router_ha_agent(self):"},{"line_number":442,"context_line":"        router \u003d {\u0027distributed\u0027: False, \u0027ha\u0027: True}"}],"source_content_type":"text/x-python","patch_set":27,"id":"ffb9cba7_8a7632a4","line":439,"range":{"start_line":439,"start_character":25,"end_line":439,"end_character":29},"in_reply_to":"ffb9cba7_da971f90","updated":"2019-04-25 01:10:19.000000000","message":"Oh, did not realize the detail. Thanks.","commit_id":"1d2d07b226dfb133ac7dfb0574b9299efe50cd7d"}],"neutron/tests/unit/agent/l3/test_l3_agent_extension_api.py":[{"author":{"_account_id":11975,"name":"Slawek Kaplonski","email":"skaplons@redhat.com","username":"slaweq"},"change_message_id":"dd958c33aa75401effe01774fa7ad32f83846dc2","unresolved":false,"context_lines":[{"line_number":20,"context_line":""},{"line_number":21,"context_line":"from neutron.agent.l3 import agent"},{"line_number":22,"context_line":"from neutron.agent.l3 import l3_agent_extension_api as l3_agent_api"},{"line_number":23,"context_line":"from neutron.agent.l3 import router_info as router_info_mod"},{"line_number":24,"context_line":"from neutron.agent.linux import ip_lib"},{"line_number":25,"context_line":"from neutron.conf.agent import common as config"},{"line_number":26,"context_line":"from neutron.conf.agent.l3 import config as l3_config"}],"source_content_type":"text/x-python","patch_set":18,"id":"3fce034c_4aae422f","line":23,"updated":"2019-04-12 08:31:31.000000000","message":"is this change really necessary?","commit_id":"1a7b33179aea754aef3e2b90f1b224b90b306767"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"aae7362173584af1edbcc1f53709efd3fea3fa7d","unresolved":false,"context_lines":[{"line_number":20,"context_line":""},{"line_number":21,"context_line":"from neutron.agent.l3 import agent"},{"line_number":22,"context_line":"from neutron.agent.l3 import l3_agent_extension_api as l3_agent_api"},{"line_number":23,"context_line":"from neutron.agent.l3 import router_info as router_info_mod"},{"line_number":24,"context_line":"from neutron.agent.linux import ip_lib"},{"line_number":25,"context_line":"from neutron.conf.agent import common as config"},{"line_number":26,"context_line":"from neutron.conf.agent.l3 import config as l3_config"}],"source_content_type":"text/x-python","patch_set":18,"id":"3fce034c_5056f02b","line":23,"in_reply_to":"3fce034c_4aae422f","updated":"2019-04-12 09:22:23.000000000","message":"This is changed due to avoid name conflict in test_register_router().\nThere was overriding local variable \u0027router_info\u0027, so I could not help it.","commit_id":"1a7b33179aea754aef3e2b90f1b224b90b306767"},{"author":{"_account_id":30156,"name":"Igor D.C.","email":"igor.duarte.cardoso@intel.com","username":"igordc"},"change_message_id":"c00d830c87b9ab6b09c8672e1b55be45a5f53741","unresolved":false,"context_lines":[{"line_number":20,"context_line":""},{"line_number":21,"context_line":"from neutron.agent.l3 import agent"},{"line_number":22,"context_line":"from neutron.agent.l3 import l3_agent_extension_api as l3_agent_api"},{"line_number":23,"context_line":"from neutron.agent.l3 import router_info as router_info_mod"},{"line_number":24,"context_line":"from neutron.agent.linux import ip_lib"},{"line_number":25,"context_line":"from neutron.conf.agent import common as config"},{"line_number":26,"context_line":"from neutron.conf.agent.l3 import config as l3_config"}],"source_content_type":"text/x-python","patch_set":18,"id":"3fce034c_fc99ea1e","line":23,"in_reply_to":"3fce034c_5056f02b","updated":"2019-04-12 23:33:40.000000000","message":"Well, you can rename the local variable right?","commit_id":"1a7b33179aea754aef3e2b90f1b224b90b306767"}],"releasenotes/notes/l3-agent-extensions-register-router-factory-46a86f845895f4f6.yaml":[{"author":{"_account_id":1131,"name":"Brian Haley","email":"haleyb.dev@gmail.com","username":"brian-haley"},"change_message_id":"bf076b921e649ceafab1ca678102b098dfd6697a","unresolved":false,"context_lines":[{"line_number":1,"context_line":"---"},{"line_number":2,"context_line":"features:"},{"line_number":3,"context_line":"  - |"},{"line_number":4,"context_line":"    A new parameter ``router_factroy`` has been added to"},{"line_number":5,"context_line":"    ``L3AgentExtensionAPI``. This parameter is for later use to override"},{"line_number":6,"context_line":"    ``router_info``. Plugin developers can use ``register_router`` to register"},{"line_number":7,"context_line":"    their own ``router_info`` class."}],"source_content_type":"text/x-yaml","patch_set":28,"id":"ffb9cba7_aa9e96b5","line":4,"range":{"start_line":4,"start_character":29,"end_line":4,"end_character":36},"updated":"2019-04-25 01:18:55.000000000","message":"s/factory","commit_id":"342400100cf6b2c4f9820e9dc109d6d2229acdfd"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"066974ebc030942a7887cb4f29fc3cfe936d4dc1","unresolved":false,"context_lines":[{"line_number":1,"context_line":"---"},{"line_number":2,"context_line":"features:"},{"line_number":3,"context_line":"  - |"},{"line_number":4,"context_line":"    A new parameter ``router_factroy`` has been added to"},{"line_number":5,"context_line":"    ``L3AgentExtensionAPI``. This parameter is for later use to override"},{"line_number":6,"context_line":"    ``router_info``. Plugin developers can use ``register_router`` to register"},{"line_number":7,"context_line":"    their own ``router_info`` class."}],"source_content_type":"text/x-yaml","patch_set":28,"id":"ffb9cba7_8a2e3241","line":4,"range":{"start_line":4,"start_character":29,"end_line":4,"end_character":36},"in_reply_to":"ffb9cba7_aa9e96b5","updated":"2019-04-25 01:30:00.000000000","message":"Done","commit_id":"342400100cf6b2c4f9820e9dc109d6d2229acdfd"},{"author":{"_account_id":1131,"name":"Brian Haley","email":"haleyb.dev@gmail.com","username":"brian-haley"},"change_message_id":"bf076b921e649ceafab1ca678102b098dfd6697a","unresolved":false,"context_lines":[{"line_number":2,"context_line":"features:"},{"line_number":3,"context_line":"  - |"},{"line_number":4,"context_line":"    A new parameter ``router_factroy`` has been added to"},{"line_number":5,"context_line":"    ``L3AgentExtensionAPI``. This parameter is for later use to override"},{"line_number":6,"context_line":"    ``router_info``. Plugin developers can use ``register_router`` to register"},{"line_number":7,"context_line":"    their own ``router_info`` class."},{"line_number":8,"context_line":""}],"source_content_type":"text/x-yaml","patch_set":28,"id":"ffb9cba7_eae1ee2b","line":5,"range":{"start_line":5,"start_character":6,"end_line":5,"end_character":25},"updated":"2019-04-25 01:18:55.000000000","message":"I think you should use the entire path here:\n\nneutron.agent.l3.L3AgentExtensionAPI","commit_id":"342400100cf6b2c4f9820e9dc109d6d2229acdfd"},{"author":{"_account_id":1131,"name":"Brian Haley","email":"haleyb.dev@gmail.com","username":"brian-haley"},"change_message_id":"bf076b921e649ceafab1ca678102b098dfd6697a","unresolved":false,"context_lines":[{"line_number":2,"context_line":"features:"},{"line_number":3,"context_line":"  - |"},{"line_number":4,"context_line":"    A new parameter ``router_factroy`` has been added to"},{"line_number":5,"context_line":"    ``L3AgentExtensionAPI``. This parameter is for later use to override"},{"line_number":6,"context_line":"    ``router_info``. Plugin developers can use ``register_router`` to register"},{"line_number":7,"context_line":"    their own ``router_info`` class."},{"line_number":8,"context_line":""}],"source_content_type":"text/x-yaml","patch_set":28,"id":"ffb9cba7_0ac6c29b","line":5,"range":{"start_line":5,"start_character":51,"end_line":5,"end_character":60},"updated":"2019-04-25 01:18:55.000000000","message":"is it for later use?","commit_id":"342400100cf6b2c4f9820e9dc109d6d2229acdfd"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"066974ebc030942a7887cb4f29fc3cfe936d4dc1","unresolved":false,"context_lines":[{"line_number":2,"context_line":"features:"},{"line_number":3,"context_line":"  - |"},{"line_number":4,"context_line":"    A new parameter ``router_factroy`` has been added to"},{"line_number":5,"context_line":"    ``L3AgentExtensionAPI``. This parameter is for later use to override"},{"line_number":6,"context_line":"    ``router_info``. Plugin developers can use ``register_router`` to register"},{"line_number":7,"context_line":"    their own ``router_info`` class."},{"line_number":8,"context_line":""}],"source_content_type":"text/x-yaml","patch_set":28,"id":"ffb9cba7_aa31b6a4","line":5,"range":{"start_line":5,"start_character":51,"end_line":5,"end_character":60},"in_reply_to":"ffb9cba7_0ac6c29b","updated":"2019-04-25 01:30:00.000000000","message":"Removed. It looks confusing.","commit_id":"342400100cf6b2c4f9820e9dc109d6d2229acdfd"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"066974ebc030942a7887cb4f29fc3cfe936d4dc1","unresolved":false,"context_lines":[{"line_number":2,"context_line":"features:"},{"line_number":3,"context_line":"  - |"},{"line_number":4,"context_line":"    A new parameter ``router_factroy`` has been added to"},{"line_number":5,"context_line":"    ``L3AgentExtensionAPI``. This parameter is for later use to override"},{"line_number":6,"context_line":"    ``router_info``. Plugin developers can use ``register_router`` to register"},{"line_number":7,"context_line":"    their own ``router_info`` class."},{"line_number":8,"context_line":""}],"source_content_type":"text/x-yaml","patch_set":28,"id":"ffb9cba7_6a2bbe2f","line":5,"range":{"start_line":5,"start_character":6,"end_line":5,"end_character":25},"in_reply_to":"ffb9cba7_eae1ee2b","updated":"2019-04-25 01:30:00.000000000","message":"Done","commit_id":"342400100cf6b2c4f9820e9dc109d6d2229acdfd"},{"author":{"_account_id":1131,"name":"Brian Haley","email":"haleyb.dev@gmail.com","username":"brian-haley"},"change_message_id":"bf076b921e649ceafab1ca678102b098dfd6697a","unresolved":false,"context_lines":[{"line_number":3,"context_line":"  - |"},{"line_number":4,"context_line":"    A new parameter ``router_factroy`` has been added to"},{"line_number":5,"context_line":"    ``L3AgentExtensionAPI``. This parameter is for later use to override"},{"line_number":6,"context_line":"    ``router_info``. Plugin developers can use ``register_router`` to register"},{"line_number":7,"context_line":"    their own ``router_info`` class."},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"    L3 agent will use the registered ``router_info`` class when it creates new"}],"source_content_type":"text/x-yaml","patch_set":28,"id":"ffb9cba7_eab32e4c","line":6,"range":{"start_line":6,"start_character":4,"end_line":6,"end_character":19},"updated":"2019-04-25 01:18:55.000000000","message":"s/the ``router_info`` class","commit_id":"342400100cf6b2c4f9820e9dc109d6d2229acdfd"},{"author":{"_account_id":1131,"name":"Brian Haley","email":"haleyb.dev@gmail.com","username":"brian-haley"},"change_message_id":"bf076b921e649ceafab1ca678102b098dfd6697a","unresolved":false,"context_lines":[{"line_number":3,"context_line":"  - |"},{"line_number":4,"context_line":"    A new parameter ``router_factroy`` has been added to"},{"line_number":5,"context_line":"    ``L3AgentExtensionAPI``. This parameter is for later use to override"},{"line_number":6,"context_line":"    ``router_info``. Plugin developers can use ``register_router`` to register"},{"line_number":7,"context_line":"    their own ``router_info`` class."},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"    L3 agent will use the registered ``router_info`` class when it creates new"}],"source_content_type":"text/x-yaml","patch_set":28,"id":"ffb9cba7_8a3712b1","line":6,"range":{"start_line":6,"start_character":49,"end_line":6,"end_character":64},"updated":"2019-04-25 01:18:55.000000000","message":"should mention this is in the L3AgentExtensionAPI class","commit_id":"342400100cf6b2c4f9820e9dc109d6d2229acdfd"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"066974ebc030942a7887cb4f29fc3cfe936d4dc1","unresolved":false,"context_lines":[{"line_number":3,"context_line":"  - |"},{"line_number":4,"context_line":"    A new parameter ``router_factroy`` has been added to"},{"line_number":5,"context_line":"    ``L3AgentExtensionAPI``. This parameter is for later use to override"},{"line_number":6,"context_line":"    ``router_info``. Plugin developers can use ``register_router`` to register"},{"line_number":7,"context_line":"    their own ``router_info`` class."},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"    L3 agent will use the registered ``router_info`` class when it creates new"}],"source_content_type":"text/x-yaml","patch_set":28,"id":"ffb9cba7_0a224253","line":6,"range":{"start_line":6,"start_character":49,"end_line":6,"end_character":64},"in_reply_to":"ffb9cba7_8a3712b1","updated":"2019-04-25 01:30:00.000000000","message":"You mean the function in L3AgentExtesionAPI docstring? I thought so, I added comments about it.","commit_id":"342400100cf6b2c4f9820e9dc109d6d2229acdfd"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"066974ebc030942a7887cb4f29fc3cfe936d4dc1","unresolved":false,"context_lines":[{"line_number":3,"context_line":"  - |"},{"line_number":4,"context_line":"    A new parameter ``router_factroy`` has been added to"},{"line_number":5,"context_line":"    ``L3AgentExtensionAPI``. This parameter is for later use to override"},{"line_number":6,"context_line":"    ``router_info``. Plugin developers can use ``register_router`` to register"},{"line_number":7,"context_line":"    their own ``router_info`` class."},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"    L3 agent will use the registered ``router_info`` class when it creates new"}],"source_content_type":"text/x-yaml","patch_set":28,"id":"ffb9cba7_2a1dc60e","line":6,"range":{"start_line":6,"start_character":4,"end_line":6,"end_character":19},"in_reply_to":"ffb9cba7_eab32e4c","updated":"2019-04-25 01:30:00.000000000","message":"Done","commit_id":"342400100cf6b2c4f9820e9dc109d6d2229acdfd"},{"author":{"_account_id":1131,"name":"Brian Haley","email":"haleyb.dev@gmail.com","username":"brian-haley"},"change_message_id":"bf076b921e649ceafab1ca678102b098dfd6697a","unresolved":false,"context_lines":[{"line_number":6,"context_line":"    ``router_info``. Plugin developers can use ``register_router`` to register"},{"line_number":7,"context_line":"    their own ``router_info`` class."},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"    L3 agent will use the registered ``router_info`` class when it creates new"},{"line_number":10,"context_line":"    ``router_info`` instance."}],"source_content_type":"text/x-yaml","patch_set":28,"id":"ffb9cba7_2aaaa6d1","line":9,"range":{"start_line":9,"start_character":4,"end_line":9,"end_character":6},"updated":"2019-04-25 01:18:55.000000000","message":"s/The L3","commit_id":"342400100cf6b2c4f9820e9dc109d6d2229acdfd"},{"author":{"_account_id":1131,"name":"Brian Haley","email":"haleyb.dev@gmail.com","username":"brian-haley"},"change_message_id":"bf076b921e649ceafab1ca678102b098dfd6697a","unresolved":false,"context_lines":[{"line_number":6,"context_line":"    ``router_info``. Plugin developers can use ``register_router`` to register"},{"line_number":7,"context_line":"    their own ``router_info`` class."},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"    L3 agent will use the registered ``router_info`` class when it creates new"},{"line_number":10,"context_line":"    ``router_info`` instance."}],"source_content_type":"text/x-yaml","patch_set":28,"id":"ffb9cba7_cab8aa2b","line":9,"range":{"start_line":9,"start_character":75,"end_line":9,"end_character":78},"updated":"2019-04-25 01:18:55.000000000","message":"s/a new","commit_id":"342400100cf6b2c4f9820e9dc109d6d2229acdfd"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"066974ebc030942a7887cb4f29fc3cfe936d4dc1","unresolved":false,"context_lines":[{"line_number":6,"context_line":"    ``router_info``. Plugin developers can use ``register_router`` to register"},{"line_number":7,"context_line":"    their own ``router_info`` class."},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"    L3 agent will use the registered ``router_info`` class when it creates new"},{"line_number":10,"context_line":"    ``router_info`` instance."}],"source_content_type":"text/x-yaml","patch_set":28,"id":"ffb9cba7_ca1bca18","line":9,"range":{"start_line":9,"start_character":4,"end_line":9,"end_character":6},"in_reply_to":"ffb9cba7_2aaaa6d1","updated":"2019-04-25 01:30:00.000000000","message":"Done","commit_id":"342400100cf6b2c4f9820e9dc109d6d2229acdfd"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"066974ebc030942a7887cb4f29fc3cfe936d4dc1","unresolved":false,"context_lines":[{"line_number":6,"context_line":"    ``router_info``. Plugin developers can use ``register_router`` to register"},{"line_number":7,"context_line":"    their own ``router_info`` class."},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"    L3 agent will use the registered ``router_info`` class when it creates new"},{"line_number":10,"context_line":"    ``router_info`` instance."}],"source_content_type":"text/x-yaml","patch_set":28,"id":"ffb9cba7_8ad39238","line":9,"range":{"start_line":9,"start_character":75,"end_line":9,"end_character":78},"in_reply_to":"ffb9cba7_cab8aa2b","updated":"2019-04-25 01:30:00.000000000","message":"Done","commit_id":"342400100cf6b2c4f9820e9dc109d6d2229acdfd"},{"author":{"_account_id":1131,"name":"Brian Haley","email":"haleyb.dev@gmail.com","username":"brian-haley"},"change_message_id":"51e4c57e0decdf99925a2f2e670a88c86ec7c449","unresolved":false,"context_lines":[{"line_number":2,"context_line":"features:"},{"line_number":3,"context_line":"  - |"},{"line_number":4,"context_line":"    A new parameter ``router_factory`` has been added to"},{"line_number":5,"context_line":"    ``neutron.agent.l3.L3AgentExtensionAPI``. This parameter is to override"},{"line_number":6,"context_line":"    the ``router_info``. Plugin developers can use ``register_router`` to"},{"line_number":7,"context_line":"    register their own ``router_info`` class."},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"    The L3 agent will use the registered ``router_info`` class when it creates"}],"source_content_type":"text/x-yaml","patch_set":29,"id":"ffb9cba7_17826250","line":6,"range":{"start_line":5,"start_character":46,"end_line":6,"end_character":24},"updated":"2019-04-25 14:09:52.000000000","message":"This sentence needs more info, I\u0027m getting confused myself on what it\u0027s overriding.  We\u0027re using the argument to register a router_info class to use in the RouterFactory class?  Maybe it\u0027s better to copy text from the commit message here?","commit_id":"a974d545f3284cc2214cf8fbb620e940ab9302bb"},{"author":{"_account_id":26970,"name":"Yang Youseok","email":"ileixe@gmail.com","username":"ileixe"},"change_message_id":"425339b311d57946aebc1afa8a6885637f8ad1cc","unresolved":false,"context_lines":[{"line_number":2,"context_line":"features:"},{"line_number":3,"context_line":"  - |"},{"line_number":4,"context_line":"    A new parameter ``router_factory`` has been added to"},{"line_number":5,"context_line":"    ``neutron.agent.l3.L3AgentExtensionAPI``. This parameter is to override"},{"line_number":6,"context_line":"    the ``router_info``. Plugin developers can use ``register_router`` to"},{"line_number":7,"context_line":"    register their own ``router_info`` class."},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"    The L3 agent will use the registered ``router_info`` class when it creates"}],"source_content_type":"text/x-yaml","patch_set":29,"id":"ffb9cba7_da0f06df","line":6,"range":{"start_line":5,"start_character":46,"end_line":6,"end_character":24},"in_reply_to":"ffb9cba7_17826250","updated":"2019-04-26 01:21:07.000000000","message":"Why I choose \u0027override\u0027 in this context, currently there is no way to register new features using this registration function. \n\nExtension developer only can override router_info which is previously registered by L3 agent with predefined feature set. If else, it just make RouterNotFound exception.\n\nI changed those sentence using commit messages.","commit_id":"a974d545f3284cc2214cf8fbb620e940ab9302bb"}]}
