)]}'
{"/COMMIT_MSG":[{"author":{"_account_id":2889,"name":"Aeva Black","email":"aeva.online@gmail.com","username":"tenbrae"},"change_message_id":"a8914c0537f122190e7343205f275cd4720ad092","unresolved":false,"context_lines":[{"line_number":1,"context_line":"Parent:     8c2ac37f (Prevent URL collisions with sub-controllers: nodes/ports)"},{"line_number":2,"context_line":"Author:     Ubuntu \u003cMichael Turek\u003e"},{"line_number":3,"context_line":"AuthorDate: 2016-07-25 20:08:14 +0000"},{"line_number":4,"context_line":"Commit:     Michael Turek \u003cmjturek@linux.vnet.ibm.com\u003e"},{"line_number":5,"context_line":"CommitDate: 2016-08-16 14:18:05 +0000"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":15,"id":"3ac371cc_348a001c","line":2,"updated":"2016-08-16 23:00:39.000000000","message":"This Author line appears to be misformatted somehow -- it should be \"First Last \u003cemail address\u003e\"","commit_id":"68445bea92c3e8fcf7607f6656691e70d93cf2aa"},{"author":{"_account_id":6637,"name":"Sam Betts","email":"sam@code-smash.net","username":"sambetts"},"change_message_id":"0c5dae3bb8a58aeb3161283f40fffe0bf349e804","unresolved":false,"context_lines":[{"line_number":4,"context_line":"Commit:     Vasyl Saienko \u003cvsaienko@mirantis.com\u003e"},{"line_number":5,"context_line":"CommitDate: 2016-08-30 12:15:31 +0300"},{"line_number":6,"context_line":""},{"line_number":7,"context_line":"Add classes for Portgroups API enablement"},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"This patch adds the portgroups API object and REST controller"},{"line_number":10,"context_line":"to Ironic. Additionally this patch provides a PortgroupsCollection"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":30,"id":"fa7ab95a_d22efea3","line":7,"updated":"2016-08-30 12:34:01.000000000","message":"Add PortGroups API","commit_id":"8a078b101299d20c884402cee8127432ffb2b560"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"5a7c00981dc1226cb44457019dc777af386d867e","unresolved":false,"context_lines":[{"line_number":4,"context_line":"Commit:     Vasyl Saienko \u003cvsaienko@mirantis.com\u003e"},{"line_number":5,"context_line":"CommitDate: 2016-08-30 12:15:31 +0300"},{"line_number":6,"context_line":""},{"line_number":7,"context_line":"Add classes for Portgroups API enablement"},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"This patch adds the portgroups API object and REST controller"},{"line_number":10,"context_line":"to Ironic. Additionally this patch provides a PortgroupsCollection"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":30,"id":"fa7ab95a_a68f7273","line":7,"in_reply_to":"fa7ab95a_d22efea3","updated":"2016-08-30 14:42:00.000000000","message":"Done","commit_id":"8a078b101299d20c884402cee8127432ffb2b560"}],"etc/ironic/policy.json.sample":[{"author":{"_account_id":2889,"name":"Aeva Black","email":"aeva.online@gmail.com","username":"tenbrae"},"change_message_id":"a8914c0537f122190e7343205f275cd4720ad092","unresolved":false,"context_lines":[{"line_number":27,"context_line":"# Set maintenance flag, taking a Node out of service"},{"line_number":28,"context_line":"\"baremetal:node:set_maintenance\": \"rule:is_admin\""},{"line_number":29,"context_line":"# Clear maintenance flag, placing the Node into service again"},{"line_number":30,"context_line":"\"baremetal:node:clear_maintenance\": \"role:is_admin\""},{"line_number":31,"context_line":"# Change Node boot device"},{"line_number":32,"context_line":"\"baremetal:node:set_boot_device\": \"rule:is_admin\""},{"line_number":33,"context_line":"# Change Node power status"}],"source_content_type":"application/octet-stream","patch_set":15,"id":"3ac371cc_148f042b","line":30,"updated":"2016-08-16 23:00:39.000000000","message":"unrelated to your patch, but I just noticed a typo that snuck in here somewhere else in my patches... s/role/rule/ ...","commit_id":"68445bea92c3e8fcf7607f6656691e70d93cf2aa"},{"author":{"_account_id":2889,"name":"Aeva Black","email":"aeva.online@gmail.com","username":"tenbrae"},"change_message_id":"a8914c0537f122190e7343205f275cd4720ad092","unresolved":false,"context_lines":[{"line_number":48,"context_line":"\"baremetal:port:delete\": \"rule:is_admin\""},{"line_number":49,"context_line":"# Update Port records"},{"line_number":50,"context_line":"\"baremetal:port:update\": \"rule:is_admin\""},{"line_number":51,"context_line":"#Retrieve Portgroup records"},{"line_number":52,"context_line":"\"baremetal:portgroup:get\": \"rule:is_admin or rule:is_observer\""},{"line_number":53,"context_line":"# Create Portgroup records"},{"line_number":54,"context_line":"\"baremetal:portgroup:create\": \"rule:is_admin\""}],"source_content_type":"application/octet-stream","patch_set":15,"id":"3ac371cc_7480f8f7","line":51,"updated":"2016-08-16 23:00:39.000000000","message":"missing space here, though I don\u0027t know why...","commit_id":"68445bea92c3e8fcf7607f6656691e70d93cf2aa"},{"author":{"_account_id":12356,"name":"Vladyslav Drok","email":"vdrok@mirantis.com","username":"vdrok"},"change_message_id":"e8aa3beb2d3a2915d1fed481ac0f3670703da02f","unresolved":false,"context_lines":[{"line_number":27,"context_line":"# Set maintenance flag, taking a Node out of service"},{"line_number":28,"context_line":"\"baremetal:node:set_maintenance\": \"rule:is_admin\""},{"line_number":29,"context_line":"# Clear maintenance flag, placing the Node into service again"},{"line_number":30,"context_line":"\"baremetal:node:clear_maintenance\": \"rule:is_admin\""},{"line_number":31,"context_line":"# Change Node boot device"},{"line_number":32,"context_line":"\"baremetal:node:set_boot_device\": \"rule:is_admin\""},{"line_number":33,"context_line":"# Change Node power status"}],"source_content_type":"application/octet-stream","patch_set":19,"id":"1ac06dbe_1daab9d2","line":30,"updated":"2016-08-25 11:59:15.000000000","message":"unrelated change","commit_id":"3b1cda9c75e2b5b53b78b2876131b43351d9952a"}],"ironic/api/controllers/v1/portgroup.py":[{"author":{"_account_id":12356,"name":"Vladyslav Drok","email":"vdrok@mirantis.com","username":"vdrok"},"change_message_id":"d73ccc5472b85eb83e77a267d51683a2ed2338c1","unresolved":false,"context_lines":[{"line_number":219,"context_line":"        subcontroller \u003d self._subcontroller_map.get(subres)"},{"line_number":220,"context_line":"        if subcontroller:"},{"line_number":221,"context_line":"            if api_utils.allow_portgroups():"},{"line_number":222,"context_line":"                return subcontroller(portgroup_id\u003dident), remainder"},{"line_number":223,"context_line":"            pecan.abort(http_client.NOT_FOUND)"},{"line_number":224,"context_line":""},{"line_number":225,"context_line":"    def __init__(self, node_id\u003dNone):"}],"source_content_type":"text/x-python","patch_set":7,"id":"9ad45d7e_2c1180ad","line":222,"range":{"start_line":222,"start_character":37,"end_line":222,"end_character":55},"updated":"2016-08-08 18:01:09.000000000","message":"This is introduced in the next patch in chain :(","commit_id":"02d603109e429c58d6a2721e762e1431ac28a6f4"},{"author":{"_account_id":12356,"name":"Vladyslav Drok","email":"vdrok@mirantis.com","username":"vdrok"},"change_message_id":"bd02c0ea25b470a930031c60f1346269408a534d","unresolved":false,"context_lines":[{"line_number":224,"context_line":""},{"line_number":225,"context_line":"    def __init__(self, node_id\u003dNone):"},{"line_number":226,"context_line":"        super(PortgroupsController, self).__init__()"},{"line_number":227,"context_line":"        self.node_id \u003d node_id"},{"line_number":228,"context_line":""},{"line_number":229,"context_line":"    def _get_portgroups_collection(self, node_ident, address,"},{"line_number":230,"context_line":"                                   marker, limit, sort_key, sort_dir,"}],"source_content_type":"text/x-python","patch_set":7,"id":"9ad45d7e_1b183484","line":227,"updated":"2016-08-08 17:56:40.000000000","message":"As you\u0027re changing it in ports controller, might be worth to rename it here too.","commit_id":"02d603109e429c58d6a2721e762e1431ac28a6f4"},{"author":{"_account_id":13689,"name":"Hironori Shiina","email":"Hironori.Shiina@fujitsu.com","username":"shiina"},"change_message_id":"e481b92a58c08566a74437d5c62dcbd78988b811","unresolved":false,"context_lines":[{"line_number":286,"context_line":"        \"\"\""},{"line_number":287,"context_line":"        if not api_utils.allow_portgroups():"},{"line_number":288,"context_line":"            raise exception.NotFound()"},{"line_number":289,"context_line":""},{"line_number":290,"context_line":"        if fields is None:"},{"line_number":291,"context_line":"            fields \u003d _DEFAULT_RETURN_FIELDS"},{"line_number":292,"context_line":""}],"source_content_type":"text/x-python","patch_set":9,"id":"9ad45d7e_7446ec7b","line":289,"updated":"2016-08-11 15:06:25.000000000","message":"Do we need to add policy.authorize?\nA patch[1] to support keystone policy was merged recently.\n\n[1] https://review.openstack.org/#/c/325599/","commit_id":"e2995a58376263292e05ae14851979faea0ea5a4"},{"author":{"_account_id":11929,"name":"Michael Turek","email":"mjturek@linux.vnet.ibm.com","username":"mjturek"},"change_message_id":"5b8f472e40e27b09c86d9c0880be0680f13e46e9","unresolved":false,"context_lines":[{"line_number":286,"context_line":"        \"\"\""},{"line_number":287,"context_line":"        if not api_utils.allow_portgroups():"},{"line_number":288,"context_line":"            raise exception.NotFound()"},{"line_number":289,"context_line":""},{"line_number":290,"context_line":"        if fields is None:"},{"line_number":291,"context_line":"            fields \u003d _DEFAULT_RETURN_FIELDS"},{"line_number":292,"context_line":""}],"source_content_type":"text/x-python","patch_set":9,"id":"9ad45d7e_5d9b0418","line":289,"in_reply_to":"9ad45d7e_7446ec7b","updated":"2016-08-11 16:36:03.000000000","message":"done","commit_id":"e2995a58376263292e05ae14851979faea0ea5a4"},{"author":{"_account_id":13689,"name":"Hironori Shiina","email":"Hironori.Shiina@fujitsu.com","username":"shiina"},"change_message_id":"fd517ac9be5398b8b2c3815ca9356e912032e092","unresolved":false,"context_lines":[{"line_number":288,"context_line":"        :param fields: Optional, a list with a specified set of fields"},{"line_number":289,"context_line":"                       of the resource to be returned."},{"line_number":290,"context_line":"        \"\"\""},{"line_number":291,"context_line":"        cdict \u003d pecan.request.context.to_dict()"},{"line_number":292,"context_line":"        policy.authorize(\u0027baremetal:portgroup:get\u0027, cdict, cdict)"},{"line_number":293,"context_line":""},{"line_number":294,"context_line":"        if not api_utils.allow_portgroups():"}],"source_content_type":"text/x-python","patch_set":12,"id":"9ad45d7e_0c8140fb","line":291,"updated":"2016-08-12 07:11:39.000000000","message":"Referring to another class[1], it would be better to move policy check to behind api_utils.allow_portgroups for consistensy.\n\n[1] https://github.com/openstack/ironic/blob/master/ironic/api/controllers/v1/ramdisk.py#L94","commit_id":"e55c5f8be7b26ea77c66eb97b396742e0166b3e1"},{"author":{"_account_id":12356,"name":"Vladyslav Drok","email":"vdrok@mirantis.com","username":"vdrok"},"change_message_id":"e8aa3beb2d3a2915d1fed481ac0f3670703da02f","unresolved":false,"context_lines":[{"line_number":90,"context_line":"    links \u003d wsme.wsattr([link.Link], readonly\u003dTrue)"},{"line_number":91,"context_line":"    \"\"\"A list containing a self link and associated portgroup links\"\"\""},{"line_number":92,"context_line":""},{"line_number":93,"context_line":"    ports \u003d wsme.wsattr([link.Link], readonly\u003dTrue)"},{"line_number":94,"context_line":"    \"\"\"Links to the collection of ports of this portgroup\"\"\""},{"line_number":95,"context_line":""},{"line_number":96,"context_line":"    def __init__(self, **kwargs):"}],"source_content_type":"text/x-python","patch_set":19,"id":"1ac06dbe_c39a04c5","line":93,"range":{"start_line":93,"start_character":4,"end_line":93,"end_character":51},"updated":"2016-08-25 11:59:15.000000000","message":"It is not here yet, it is added in the next patch so should be moved there.","commit_id":"3b1cda9c75e2b5b53b78b2876131b43351d9952a"},{"author":{"_account_id":11929,"name":"Michael Turek","email":"mjturek@linux.vnet.ibm.com","username":"mjturek"},"change_message_id":"028fe93dc468b4e4c3f04c38004714faa03025f5","unresolved":false,"context_lines":[{"line_number":90,"context_line":"    links \u003d wsme.wsattr([link.Link], readonly\u003dTrue)"},{"line_number":91,"context_line":"    \"\"\"A list containing a self link and associated portgroup links\"\"\""},{"line_number":92,"context_line":""},{"line_number":93,"context_line":"    ports \u003d wsme.wsattr([link.Link], readonly\u003dTrue)"},{"line_number":94,"context_line":"    \"\"\"Links to the collection of ports of this portgroup\"\"\""},{"line_number":95,"context_line":""},{"line_number":96,"context_line":"    def __init__(self, **kwargs):"}],"source_content_type":"text/x-python","patch_set":19,"id":"1ac06dbe_e64c6978","line":93,"range":{"start_line":93,"start_character":4,"end_line":93,"end_character":51},"in_reply_to":"1ac06dbe_c39a04c5","updated":"2016-08-25 13:51:08.000000000","message":"whoops! Missed this in last set. Thanks","commit_id":"3b1cda9c75e2b5b53b78b2876131b43351d9952a"},{"author":{"_account_id":12356,"name":"Vladyslav Drok","email":"vdrok@mirantis.com","username":"vdrok"},"change_message_id":"25a45bc9254157e7066a2f8e83a77a355f8067a6","unresolved":false,"context_lines":[{"line_number":211,"context_line":""},{"line_number":212,"context_line":"    invalid_sort_key_list \u003d [\u0027extra\u0027, \u0027internal_info\u0027]"},{"line_number":213,"context_line":""},{"line_number":214,"context_line":"    def __init__(self, node_id\u003dNone):"},{"line_number":215,"context_line":"        super(PortgroupsController, self).__init__()"},{"line_number":216,"context_line":"        self.node_id_from_node \u003d node_id"},{"line_number":217,"context_line":""}],"source_content_type":"text/x-python","patch_set":19,"id":"1ac06dbe_6367d0b7","line":214,"updated":"2016-08-25 12:01:02.000000000","message":"should be node_ident here.","commit_id":"3b1cda9c75e2b5b53b78b2876131b43351d9952a"},{"author":{"_account_id":11929,"name":"Michael Turek","email":"mjturek@linux.vnet.ibm.com","username":"mjturek"},"change_message_id":"028fe93dc468b4e4c3f04c38004714faa03025f5","unresolved":false,"context_lines":[{"line_number":211,"context_line":""},{"line_number":212,"context_line":"    invalid_sort_key_list \u003d [\u0027extra\u0027, \u0027internal_info\u0027]"},{"line_number":213,"context_line":""},{"line_number":214,"context_line":"    def __init__(self, node_id\u003dNone):"},{"line_number":215,"context_line":"        super(PortgroupsController, self).__init__()"},{"line_number":216,"context_line":"        self.node_id_from_node \u003d node_id"},{"line_number":217,"context_line":""}],"source_content_type":"text/x-python","patch_set":19,"id":"1ac06dbe_3c4faebf","line":214,"in_reply_to":"1ac06dbe_6367d0b7","updated":"2016-08-25 13:51:08.000000000","message":"Done","commit_id":"3b1cda9c75e2b5b53b78b2876131b43351d9952a"},{"author":{"_account_id":12356,"name":"Vladyslav Drok","email":"vdrok@mirantis.com","username":"vdrok"},"change_message_id":"513b88161122f5e5a7a434395da14b6bb2d18d4f","unresolved":false,"context_lines":[{"line_number":213,"context_line":""},{"line_number":214,"context_line":"    def __init__(self, node_id\u003dNone):"},{"line_number":215,"context_line":"        super(PortgroupsController, self).__init__()"},{"line_number":216,"context_line":"        self.node_id_from_node \u003d node_id"},{"line_number":217,"context_line":""},{"line_number":218,"context_line":"    def _get_portgroups_collection(self, node_ident, address,"},{"line_number":219,"context_line":"                                   marker, limit, sort_key, sort_dir,"}],"source_content_type":"text/x-python","patch_set":19,"id":"1ac06dbe_0add5614","line":216,"range":{"start_line":216,"start_character":13,"end_line":216,"end_character":30},"updated":"2016-08-25 10:08:44.000000000","message":"please rename to parent_node_ident as is in case of ports.","commit_id":"3b1cda9c75e2b5b53b78b2876131b43351d9952a"},{"author":{"_account_id":11929,"name":"Michael Turek","email":"mjturek@linux.vnet.ibm.com","username":"mjturek"},"change_message_id":"028fe93dc468b4e4c3f04c38004714faa03025f5","unresolved":false,"context_lines":[{"line_number":213,"context_line":""},{"line_number":214,"context_line":"    def __init__(self, node_id\u003dNone):"},{"line_number":215,"context_line":"        super(PortgroupsController, self).__init__()"},{"line_number":216,"context_line":"        self.node_id_from_node \u003d node_id"},{"line_number":217,"context_line":""},{"line_number":218,"context_line":"    def _get_portgroups_collection(self, node_ident, address,"},{"line_number":219,"context_line":"                                   marker, limit, sort_key, sort_dir,"}],"source_content_type":"text/x-python","patch_set":19,"id":"1ac06dbe_9c4ea2bf","line":216,"range":{"start_line":216,"start_character":13,"end_line":216,"end_character":30},"in_reply_to":"1ac06dbe_0add5614","updated":"2016-08-25 13:51:08.000000000","message":"Done","commit_id":"3b1cda9c75e2b5b53b78b2876131b43351d9952a"},{"author":{"_account_id":12356,"name":"Vladyslav Drok","email":"vdrok@mirantis.com","username":"vdrok"},"change_message_id":"e8aa3beb2d3a2915d1fed481ac0f3670703da02f","unresolved":false,"context_lines":[{"line_number":213,"context_line":""},{"line_number":214,"context_line":"    def __init__(self, node_id\u003dNone):"},{"line_number":215,"context_line":"        super(PortgroupsController, self).__init__()"},{"line_number":216,"context_line":"        self.node_id_from_node \u003d node_id"},{"line_number":217,"context_line":""},{"line_number":218,"context_line":"    def _get_portgroups_collection(self, node_ident, address,"},{"line_number":219,"context_line":"                                   marker, limit, sort_key, sort_dir,"}],"source_content_type":"text/x-python","patch_set":19,"id":"1ac06dbe_a0337e12","line":216,"range":{"start_line":216,"start_character":13,"end_line":216,"end_character":30},"in_reply_to":"1ac06dbe_0add5614","updated":"2016-08-25 11:59:15.000000000","message":"It is also not used in any way in this patch, so can be moved to the next patch, along with all the \n\n if self.node_id_from_node:\n   raise exception.OperationNotPermitted()\n\nchecks","commit_id":"3b1cda9c75e2b5b53b78b2876131b43351d9952a"},{"author":{"_account_id":11929,"name":"Michael Turek","email":"mjturek@linux.vnet.ibm.com","username":"mjturek"},"change_message_id":"028fe93dc468b4e4c3f04c38004714faa03025f5","unresolved":false,"context_lines":[{"line_number":213,"context_line":""},{"line_number":214,"context_line":"    def __init__(self, node_id\u003dNone):"},{"line_number":215,"context_line":"        super(PortgroupsController, self).__init__()"},{"line_number":216,"context_line":"        self.node_id_from_node \u003d node_id"},{"line_number":217,"context_line":""},{"line_number":218,"context_line":"    def _get_portgroups_collection(self, node_ident, address,"},{"line_number":219,"context_line":"                                   marker, limit, sort_key, sort_dir,"}],"source_content_type":"text/x-python","patch_set":19,"id":"1ac06dbe_7c4926b7","line":216,"range":{"start_line":216,"start_character":13,"end_line":216,"end_character":30},"in_reply_to":"1ac06dbe_a0337e12","updated":"2016-08-25 13:51:08.000000000","message":"Done","commit_id":"3b1cda9c75e2b5b53b78b2876131b43351d9952a"},{"author":{"_account_id":11929,"name":"Michael Turek","email":"mjturek@linux.vnet.ibm.com","username":"mjturek"},"change_message_id":"69fbc86bea35d1521ee979aaf898303b0ed43a21","unresolved":false,"context_lines":[{"line_number":213,"context_line":""},{"line_number":214,"context_line":"    def __init__(self, node_id\u003dNone):"},{"line_number":215,"context_line":"        super(PortgroupsController, self).__init__()"},{"line_number":216,"context_line":"        self.node_id_from_node \u003d node_id"},{"line_number":217,"context_line":""},{"line_number":218,"context_line":"    def _get_portgroups_collection(self, node_ident, address,"},{"line_number":219,"context_line":"                                   marker, limit, sort_key, sort_dir,"}],"source_content_type":"text/x-python","patch_set":19,"id":"1ac06dbe_7a5da614","line":216,"range":{"start_line":216,"start_character":13,"end_line":216,"end_character":30},"in_reply_to":"1ac06dbe_a0337e12","updated":"2016-08-25 14:11:53.000000000","message":"misunderstood this one. Moving constructor up to next set.","commit_id":"3b1cda9c75e2b5b53b78b2876131b43351d9952a"},{"author":{"_account_id":12356,"name":"Vladyslav Drok","email":"vdrok@mirantis.com","username":"vdrok"},"change_message_id":"fc6b45232df8ce2391b7ccb4cad0de89a24fcb8b","unresolved":false,"context_lines":[{"line_number":229,"context_line":"                _(\"The sort_key value %(key)s is an invalid field for \""},{"line_number":230,"context_line":"                  \"sorting\") % {\u0027key\u0027: sort_key})"},{"line_number":231,"context_line":""},{"line_number":232,"context_line":"        if address:"},{"line_number":233,"context_line":"            portgroups \u003d self._get_portgroups_by_address(address)"},{"line_number":234,"context_line":"        else:"},{"line_number":235,"context_line":"            portgroups \u003d objects.Portgroup.list(pecan.request.context, limit,"}],"source_content_type":"text/x-python","patch_set":27,"id":"fa7ab95a_67a18ba9","line":232,"updated":"2016-08-26 16:16:05.000000000","message":"Hm, why is node_ident case gone? It\u0027s still possible to request a specific node\u0027s portgroups by doing /v1/portgroups/?node\u003dabc. Only self.parent_node_ident should be removed.","commit_id":"c25d222d724ac493129ced91d0fed116162b81ab"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"e4435dd0559793b0a12493d7ba6a0c4d864575d0","unresolved":false,"context_lines":[{"line_number":14,"context_line":""},{"line_number":15,"context_line":"from ironic_lib import metrics_utils"},{"line_number":16,"context_line":"import pecan"},{"line_number":17,"context_line":"from pecan import rest"},{"line_number":18,"context_line":"from six.moves import http_client"},{"line_number":19,"context_line":"import wsme"},{"line_number":20,"context_line":"from wsme import types as wtypes"}],"source_content_type":"text/x-python","patch_set":31,"id":"fa7ab95a_74525b36","line":17,"updated":"2016-08-30 21:16:32.000000000","message":"This seems unneeded. In the one use of this maybe could just do:\n\n pecan.rest.RestController()","commit_id":"e8927d4b363f77cf08b248ed371d9ebdd500e8dd"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"6b4af22e7ee24ad33aa9252e9b65a63960a2af29","unresolved":false,"context_lines":[{"line_number":115,"context_line":"        setattr(self, \u0027node_uuid\u0027, kwargs.get(\u0027node_id\u0027, wtypes.Unset))"},{"line_number":116,"context_line":""},{"line_number":117,"context_line":"    @staticmethod"},{"line_number":118,"context_line":"    def _convert_with_links(portgroup, url, fields\u003dNone):"},{"line_number":119,"context_line":"        # NOTE(lucasagomes): Since we are able to return a specified set of"},{"line_number":120,"context_line":"        # fields the \"uuid\" can be unset, so we need to save it in another"},{"line_number":121,"context_line":"        # variable to use when building the links"}],"source_content_type":"text/x-python","patch_set":31,"id":"fa7ab95a_afa64cbe","line":118,"updated":"2016-08-30 21:34:41.000000000","message":"I realize that this code is mostly cargo-culted from port.py, but I think we should have some docstrings for this function","commit_id":"e8927d4b363f77cf08b248ed371d9ebdd500e8dd"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"6b4af22e7ee24ad33aa9252e9b65a63960a2af29","unresolved":false,"context_lines":[{"line_number":142,"context_line":"        return portgroup"},{"line_number":143,"context_line":""},{"line_number":144,"context_line":"    @classmethod"},{"line_number":145,"context_line":"    def convert_with_links(cls, rpc_portgroup, fields\u003dNone):"},{"line_number":146,"context_line":"        portgroup \u003d Portgroup(**rpc_portgroup.as_dict())"},{"line_number":147,"context_line":""},{"line_number":148,"context_line":"        if fields is not None:"}],"source_content_type":"text/x-python","patch_set":31,"id":"fa7ab95a_efacd4a0","line":145,"updated":"2016-08-30 21:34:41.000000000","message":"I realize that this code is mostly cargo-culted from port.py, but I think we should have some docstrings for this function","commit_id":"e8927d4b363f77cf08b248ed371d9ebdd500e8dd"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"6b4af22e7ee24ad33aa9252e9b65a63960a2af29","unresolved":false,"context_lines":[{"line_number":152,"context_line":"                                       fields\u003dfields)"},{"line_number":153,"context_line":""},{"line_number":154,"context_line":"    @classmethod"},{"line_number":155,"context_line":"    def sample(cls, expand\u003dTrue):"},{"line_number":156,"context_line":"        sample \u003d cls(uuid\u003d\u002727e3153e-d5bf-4b7e-b517-fb518e17f34c\u0027,"},{"line_number":157,"context_line":"                     address\u003d\u0027fe:54:00:77:07:d9\u0027,"},{"line_number":158,"context_line":"                     name\u003d\u0027node1-portgroup-01\u0027,"}],"source_content_type":"text/x-python","patch_set":31,"id":"fa7ab95a_4f9ea063","line":155,"updated":"2016-08-30 21:34:41.000000000","message":"I realize that this code is mostly cargo-culted from port.py, but I think we should have some docstrings for this function","commit_id":"e8927d4b363f77cf08b248ed371d9ebdd500e8dd"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"e4435dd0559793b0a12493d7ba6a0c4d864575d0","unresolved":false,"context_lines":[{"line_number":153,"context_line":""},{"line_number":154,"context_line":"    @classmethod"},{"line_number":155,"context_line":"    def sample(cls, expand\u003dTrue):"},{"line_number":156,"context_line":"        sample \u003d cls(uuid\u003d\u002727e3153e-d5bf-4b7e-b517-fb518e17f34c\u0027,"},{"line_number":157,"context_line":"                     address\u003d\u0027fe:54:00:77:07:d9\u0027,"},{"line_number":158,"context_line":"                     name\u003d\u0027node1-portgroup-01\u0027,"},{"line_number":159,"context_line":"                     extra\u003d{\u0027foo\u0027: \u0027bar\u0027},"}],"source_content_type":"text/x-python","patch_set":31,"id":"fa7ab95a_94335f13","line":156,"updated":"2016-08-30 21:16:32.000000000","message":"Is it okay that this is the same as in port.py?","commit_id":"e8927d4b363f77cf08b248ed371d9ebdd500e8dd"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"e4435dd0559793b0a12493d7ba6a0c4d864575d0","unresolved":false,"context_lines":[{"line_number":163,"context_line":"                     updated_at\u003ddatetime.datetime.utcnow())"},{"line_number":164,"context_line":"        # NOTE(lucasagomes): node_uuid getter() method look at the"},{"line_number":165,"context_line":"        # _node_uuid variable"},{"line_number":166,"context_line":"        sample._node_uuid \u003d \u00277ae81bb3-dec3-4289-8d6c-da80bd8001ae\u0027"},{"line_number":167,"context_line":"        fields \u003d None if expand else _DEFAULT_RETURN_FIELDS"},{"line_number":168,"context_line":"        return cls._convert_with_links(sample, \u0027http://localhost:6385\u0027,"},{"line_number":169,"context_line":"                                       fields\u003dfields)"}],"source_content_type":"text/x-python","patch_set":31,"id":"fa7ab95a_f43cabe2","line":166,"updated":"2016-08-30 21:16:32.000000000","message":"ditto","commit_id":"e8927d4b363f77cf08b248ed371d9ebdd500e8dd"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"6b4af22e7ee24ad33aa9252e9b65a63960a2af29","unresolved":false,"context_lines":[{"line_number":189,"context_line":"        self._type \u003d \u0027portgroups\u0027"},{"line_number":190,"context_line":""},{"line_number":191,"context_line":"    @staticmethod"},{"line_number":192,"context_line":"    def convert_with_links(rpc_portgroups, limit, url\u003dNone, fields\u003dNone,"},{"line_number":193,"context_line":"                           **kwargs):"},{"line_number":194,"context_line":"        collection \u003d PortgroupCollection()"},{"line_number":195,"context_line":"        collection.portgroups \u003d [Portgroup.convert_with_links(p, fields\u003dfields)"}],"source_content_type":"text/x-python","patch_set":31,"id":"fa7ab95a_6f99a478","line":192,"updated":"2016-08-30 21:34:41.000000000","message":"I realize that this code is mostly cargo-culted from port.py, but I think we should have some docstrings for this function","commit_id":"e8927d4b363f77cf08b248ed371d9ebdd500e8dd"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"6b4af22e7ee24ad33aa9252e9b65a63960a2af29","unresolved":false,"context_lines":[{"line_number":198,"context_line":"        return collection"},{"line_number":199,"context_line":""},{"line_number":200,"context_line":"    @classmethod"},{"line_number":201,"context_line":"    def sample(cls):"},{"line_number":202,"context_line":"        sample \u003d cls()"},{"line_number":203,"context_line":"        sample.portgroups \u003d [Portgroup.sample(expand\u003dFalse)]"},{"line_number":204,"context_line":"        return sample"}],"source_content_type":"text/x-python","patch_set":31,"id":"fa7ab95a_8f8a6819","line":201,"updated":"2016-08-30 21:34:41.000000000","message":"I realize that this code is mostly cargo-culted from port.py, but I think we should have some docstrings for this function","commit_id":"e8927d4b363f77cf08b248ed371d9ebdd500e8dd"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"6b4af22e7ee24ad33aa9252e9b65a63960a2af29","unresolved":false,"context_lines":[{"line_number":213,"context_line":""},{"line_number":214,"context_line":"    invalid_sort_key_list \u003d [\u0027extra\u0027, \u0027internal_info\u0027]"},{"line_number":215,"context_line":""},{"line_number":216,"context_line":"    def _get_portgroups_collection(self, node_ident, address,"},{"line_number":217,"context_line":"                                   marker, limit, sort_key, sort_dir,"},{"line_number":218,"context_line":"                                   resource_url\u003dNone, fields\u003dNone):"},{"line_number":219,"context_line":"        limit \u003d api_utils.validate_limit(limit)"}],"source_content_type":"text/x-python","patch_set":31,"id":"fa7ab95a_cf80f0f9","line":216,"updated":"2016-08-30 21:34:41.000000000","message":"I realize that this code is mostly cargo-culted from port.py, but I think we should have some docstrings for this function","commit_id":"e8927d4b363f77cf08b248ed371d9ebdd500e8dd"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":76,"context_line":"    extra \u003d {wtypes.text: types.jsontype}"},{"line_number":77,"context_line":"    \"\"\"This portgroup\u0027s meta data\"\"\""},{"line_number":78,"context_line":""},{"line_number":79,"context_line":"    internal_info \u003d {wtypes.text: types.jsontype}"},{"line_number":80,"context_line":"    \"\"\"This portgroup\u0027s internal info\"\"\""},{"line_number":81,"context_line":""},{"line_number":82,"context_line":"    node_uuid \u003d wsme.wsproperty(types.uuid, _get_node_uuid, _set_node_uuid,"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_6bb1d746","line":79,"updated":"2016-11-02 17:31:53.000000000","message":"I think we should set this to readonly like we do for port.internal_info and node.driver_internal_info","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":76,"context_line":"    extra \u003d {wtypes.text: types.jsontype}"},{"line_number":77,"context_line":"    \"\"\"This portgroup\u0027s meta data\"\"\""},{"line_number":78,"context_line":""},{"line_number":79,"context_line":"    internal_info \u003d {wtypes.text: types.jsontype}"},{"line_number":80,"context_line":"    \"\"\"This portgroup\u0027s internal info\"\"\""},{"line_number":81,"context_line":""},{"line_number":82,"context_line":"    node_uuid \u003d wsme.wsproperty(types.uuid, _get_node_uuid, _set_node_uuid,"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_d6e42aad","line":79,"in_reply_to":"ba5da102_6bb1d746","updated":"2016-11-03 11:38:14.000000000","message":"Done","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":156,"context_line":"    def sample(cls, expand\u003dTrue):"},{"line_number":157,"context_line":"        \"\"\"Return a sample of the portgroup.\"\"\""},{"line_number":158,"context_line":"        sample \u003d cls(uuid\u003d\u002727e3153e-d5bf-4b7e-b517-fb518e17f34c\u0027,"},{"line_number":159,"context_line":"                     address\u003d\u0027fe:54:00:77:07:d9\u0027,"},{"line_number":160,"context_line":"                     name\u003d\u0027node1-portgroup-01\u0027,"},{"line_number":161,"context_line":"                     extra\u003d{\u0027foo\u0027: \u0027bar\u0027},"},{"line_number":162,"context_line":"                     internal_info\u003d{\u0027baz\u0027: \u0027boo\u0027},"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_3df642f9","line":159,"updated":"2016-11-02 17:31:53.000000000","message":"just a nit and i suspect it doesn\u0027t matter because i don\u0027t think we need these sample\u0027s any more (but i\u0027m not sure). this is the same UUID \u0026 address used for the sample port; I hope no one looks and gets confused by that :)","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":156,"context_line":"    def sample(cls, expand\u003dTrue):"},{"line_number":157,"context_line":"        \"\"\"Return a sample of the portgroup.\"\"\""},{"line_number":158,"context_line":"        sample \u003d cls(uuid\u003d\u002727e3153e-d5bf-4b7e-b517-fb518e17f34c\u0027,"},{"line_number":159,"context_line":"                     address\u003d\u0027fe:54:00:77:07:d9\u0027,"},{"line_number":160,"context_line":"                     name\u003d\u0027node1-portgroup-01\u0027,"},{"line_number":161,"context_line":"                     extra\u003d{\u0027foo\u0027: \u0027bar\u0027},"},{"line_number":162,"context_line":"                     internal_info\u003d{\u0027baz\u0027: \u0027boo\u0027},"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_f6292e9c","line":159,"in_reply_to":"ba5da102_3df642f9","updated":"2016-11-03 11:38:14.000000000","message":"port and portgroup may have the same address it is normal. Also portgroup.uuid and port.uuid may be the same. I\u0027ve changed uuid for portgroup to avoid confusion.","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":162,"context_line":"                     internal_info\u003d{\u0027baz\u0027: \u0027boo\u0027},"},{"line_number":163,"context_line":"                     standalone_ports_supported\u003dTrue,"},{"line_number":164,"context_line":"                     created_at\u003ddatetime.datetime.utcnow(),"},{"line_number":165,"context_line":"                     updated_at\u003ddatetime.datetime.utcnow())"},{"line_number":166,"context_line":"        # NOTE(lucasagomes): node_uuid getter() method look at the"},{"line_number":167,"context_line":"        # _node_uuid variable"},{"line_number":168,"context_line":"        sample._node_uuid \u003d \u00277ae81bb3-dec3-4289-8d6c-da80bd8001ae\u0027"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_fdcdaa31","line":165,"updated":"2016-11-02 17:31:53.000000000","message":"we should not be using datetime.datetime.utcnow() for the above two. (Even though port has it; there\u0027s a patch about it [1]). I suggest using what node.py \u0026 chassis.py do:\n    time \u003d datetime.datetime(2000, 1, 1, 12, 0, 0)\n\n[1] https://review.openstack.org/#/c/352963/","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":162,"context_line":"                     internal_info\u003d{\u0027baz\u0027: \u0027boo\u0027},"},{"line_number":163,"context_line":"                     standalone_ports_supported\u003dTrue,"},{"line_number":164,"context_line":"                     created_at\u003ddatetime.datetime.utcnow(),"},{"line_number":165,"context_line":"                     updated_at\u003ddatetime.datetime.utcnow())"},{"line_number":166,"context_line":"        # NOTE(lucasagomes): node_uuid getter() method look at the"},{"line_number":167,"context_line":"        # _node_uuid variable"},{"line_number":168,"context_line":"        sample._node_uuid \u003d \u00277ae81bb3-dec3-4289-8d6c-da80bd8001ae\u0027"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_76b8be75","line":165,"in_reply_to":"ba5da102_fdcdaa31","updated":"2016-11-03 11:38:14.000000000","message":"Done","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":218,"context_line":""},{"line_number":219,"context_line":"    def _get_portgroups_collection(self, node_ident, address,"},{"line_number":220,"context_line":"                                   marker, limit, sort_key, sort_dir,"},{"line_number":221,"context_line":"                                   resource_url\u003dNone, fields\u003dNone):"},{"line_number":222,"context_line":"        \"\"\"Return portgroups collection."},{"line_number":223,"context_line":""},{"line_number":224,"context_line":"        :param node_ident: UUID or name of a node."}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_f30b19d4","line":221,"updated":"2016-11-02 17:31:53.000000000","message":"I realize this is a copy/paste and I don\u0027t really care too much about this, but really, if you think about it, it makes more sense as ..(self, node_ident\u003dNone, address\u003dNone, marker\u003dNone, limit\u003dNone, sort_key\u003did, sort_dir\u003d\u0027asc\u0027 etc...)","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":294,"context_line":"        :param address: MAC address of a portgroup, to get the portgroup which"},{"line_number":295,"context_line":"                        has this MAC address."},{"line_number":296,"context_line":"        :param marker: pagination marker for large data sets."},{"line_number":297,"context_line":"        :param limit: maximum number of resources to return in a single result."},{"line_number":298,"context_line":"        :param sort_key: column to sort results by. Default: id."},{"line_number":299,"context_line":"        :param sort_dir: direction to sort. \"asc\" or \"desc\". Default: asc."},{"line_number":300,"context_line":"        :param fields: Optional, a list with a specified set of fields"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_a04789ba","line":297,"updated":"2016-11-02 17:31:53.000000000","message":"Do we also want to add \u0027This value cannot be larger than the value of max_limit in the [api] section of the ironic configuration, or only max_limit resources will be returned.\u0027\n\n(similar to port \u0026 node)\n\nI don\u0027t know that this is used for documentation; maybe it just needs to be mentioned in the api-ref part.","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":294,"context_line":"        :param address: MAC address of a portgroup, to get the portgroup which"},{"line_number":295,"context_line":"                        has this MAC address."},{"line_number":296,"context_line":"        :param marker: pagination marker for large data sets."},{"line_number":297,"context_line":"        :param limit: maximum number of resources to return in a single result."},{"line_number":298,"context_line":"        :param sort_key: column to sort results by. Default: id."},{"line_number":299,"context_line":"        :param sort_dir: direction to sort. \"asc\" or \"desc\". Default: asc."},{"line_number":300,"context_line":"        :param fields: Optional, a list with a specified set of fields"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_d13354f4","line":297,"in_reply_to":"ba5da102_a04789ba","updated":"2016-11-03 11:38:14.000000000","message":"Done","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":301,"context_line":"                       of the resource to be returned."},{"line_number":302,"context_line":"        \"\"\""},{"line_number":303,"context_line":"        if not api_utils.allow_portgroups():"},{"line_number":304,"context_line":"            raise exception.NotFound()"},{"line_number":305,"context_line":""},{"line_number":306,"context_line":"        cdict \u003d pecan.request.context.to_dict()"},{"line_number":307,"context_line":"        policy.authorize(\u0027baremetal:portgroup:get\u0027, cdict, cdict)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_009cb50d","line":304,"updated":"2016-11-02 17:31:53.000000000","message":"should be exception.NotAcceptable()","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":301,"context_line":"                       of the resource to be returned."},{"line_number":302,"context_line":"        \"\"\""},{"line_number":303,"context_line":"        if not api_utils.allow_portgroups():"},{"line_number":304,"context_line":"            raise exception.NotFound()"},{"line_number":305,"context_line":""},{"line_number":306,"context_line":"        cdict \u003d pecan.request.context.to_dict()"},{"line_number":307,"context_line":"        policy.authorize(\u0027baremetal:portgroup:get\u0027, cdict, cdict)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_31c01050","line":304,"in_reply_to":"ba5da102_009cb50d","updated":"2016-11-03 11:38:14.000000000","message":"when client doing request with older api version (when portgroups are not supported) we assume that /portgroups endpoint doesn\u0027t exist so request to non existed endpoint should return 404.","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"17964fc2f83c4db8293e1c88e8a54230cb31ada0","unresolved":false,"context_lines":[{"line_number":301,"context_line":"                       of the resource to be returned."},{"line_number":302,"context_line":"        \"\"\""},{"line_number":303,"context_line":"        if not api_utils.allow_portgroups():"},{"line_number":304,"context_line":"            raise exception.NotFound()"},{"line_number":305,"context_line":""},{"line_number":306,"context_line":"        cdict \u003d pecan.request.context.to_dict()"},{"line_number":307,"context_line":"        policy.authorize(\u0027baremetal:portgroup:get\u0027, cdict, cdict)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_60a1c645","line":304,"in_reply_to":"ba5da102_31c01050","updated":"2016-11-03 14:21:55.000000000","message":"OMG! if folks say so [1]...\n\n[1] http://eavesdrop.openstack.org/irclogs/%23openstack-ironic/%23openstack-ironic.2016-11-03.log.html#t2016-11-03T14:05:28","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":326,"context_line":"        :param address: MAC address of a portgroup, to get the portgroup which"},{"line_number":327,"context_line":"                        has this MAC address."},{"line_number":328,"context_line":"        :param marker: pagination marker for large data sets."},{"line_number":329,"context_line":"        :param limit: maximum number of resources to return in a single result."},{"line_number":330,"context_line":"        :param sort_key: column to sort results by. Default: id."},{"line_number":331,"context_line":"        :param sort_dir: direction to sort. \"asc\" or \"desc\". Default: asc."},{"line_number":332,"context_line":"        \"\"\""}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_20cff929","line":329,"updated":"2016-11-02 17:31:53.000000000","message":"ditto","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":326,"context_line":"        :param address: MAC address of a portgroup, to get the portgroup which"},{"line_number":327,"context_line":"                        has this MAC address."},{"line_number":328,"context_line":"        :param marker: pagination marker for large data sets."},{"line_number":329,"context_line":"        :param limit: maximum number of resources to return in a single result."},{"line_number":330,"context_line":"        :param sort_key: column to sort results by. Default: id."},{"line_number":331,"context_line":"        :param sort_dir: direction to sort. \"asc\" or \"desc\". Default: asc."},{"line_number":332,"context_line":"        \"\"\""}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_d1ac348e","line":329,"in_reply_to":"ba5da102_20cff929","updated":"2016-11-03 11:38:14.000000000","message":"Done","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":331,"context_line":"        :param sort_dir: direction to sort. \"asc\" or \"desc\". Default: asc."},{"line_number":332,"context_line":"        \"\"\""},{"line_number":333,"context_line":"        if not api_utils.allow_portgroups():"},{"line_number":334,"context_line":"            raise exception.NotFound()"},{"line_number":335,"context_line":""},{"line_number":336,"context_line":"        cdict \u003d pecan.request.context.to_dict()"},{"line_number":337,"context_line":"        policy.authorize(\u0027baremetal:portgroup:get\u0027, cdict, cdict)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_608bb1c3","line":334,"updated":"2016-11-02 17:31:53.000000000","message":"should be exception.NotAcceptable()","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":331,"context_line":"        :param sort_dir: direction to sort. \"asc\" or \"desc\". Default: asc."},{"line_number":332,"context_line":"        \"\"\""},{"line_number":333,"context_line":"        if not api_utils.allow_portgroups():"},{"line_number":334,"context_line":"            raise exception.NotFound()"},{"line_number":335,"context_line":""},{"line_number":336,"context_line":"        cdict \u003d pecan.request.context.to_dict()"},{"line_number":337,"context_line":"        policy.authorize(\u0027baremetal:portgroup:get\u0027, cdict, cdict)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_f1a778a4","line":334,"in_reply_to":"ba5da102_608bb1c3","updated":"2016-11-03 11:38:14.000000000","message":"ditto","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":344,"context_line":"        resource_url \u003d \u0027/\u0027.join([\u0027portgroups\u0027, \u0027detail\u0027])"},{"line_number":345,"context_line":"        return self._get_portgroups_collection(node, address,"},{"line_number":346,"context_line":"                                               marker, limit, sort_key,"},{"line_number":347,"context_line":"                                               sort_dir, resource_url)"},{"line_number":348,"context_line":""},{"line_number":349,"context_line":"    @METRICS.timer(\u0027PortgroupsController.get_one\u0027)"},{"line_number":350,"context_line":"    @expose.expose(Portgroup, types.uuid_or_name, types.listtype)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_73dc6973","line":347,"updated":"2016-11-02 17:31:53.000000000","message":"nit: should be resource_url\u003dresource_url","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":344,"context_line":"        resource_url \u003d \u0027/\u0027.join([\u0027portgroups\u0027, \u0027detail\u0027])"},{"line_number":345,"context_line":"        return self._get_portgroups_collection(node, address,"},{"line_number":346,"context_line":"                                               marker, limit, sort_key,"},{"line_number":347,"context_line":"                                               sort_dir, resource_url)"},{"line_number":348,"context_line":""},{"line_number":349,"context_line":"    @METRICS.timer(\u0027PortgroupsController.get_one\u0027)"},{"line_number":350,"context_line":"    @expose.expose(Portgroup, types.uuid_or_name, types.listtype)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_51e664e8","line":347,"in_reply_to":"ba5da102_73dc6973","updated":"2016-11-03 11:38:14.000000000","message":"Done","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":356,"context_line":"                       of the resource to be returned."},{"line_number":357,"context_line":"        \"\"\""},{"line_number":358,"context_line":"        if not api_utils.allow_portgroups():"},{"line_number":359,"context_line":"            raise exception.NotFound()"},{"line_number":360,"context_line":""},{"line_number":361,"context_line":"        cdict \u003d pecan.request.context.to_dict()"},{"line_number":362,"context_line":"        policy.authorize(\u0027baremetal:portgroup:get\u0027, cdict, cdict)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_53220553","line":359,"updated":"2016-11-02 17:31:53.000000000","message":"should be exception.NotAcceptable()","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":356,"context_line":"                       of the resource to be returned."},{"line_number":357,"context_line":"        \"\"\""},{"line_number":358,"context_line":"        if not api_utils.allow_portgroups():"},{"line_number":359,"context_line":"            raise exception.NotFound()"},{"line_number":360,"context_line":""},{"line_number":361,"context_line":"        cdict \u003d pecan.request.context.to_dict()"},{"line_number":362,"context_line":"        policy.authorize(\u0027baremetal:portgroup:get\u0027, cdict, cdict)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_71e9a8b6","line":359,"in_reply_to":"ba5da102_53220553","updated":"2016-11-03 11:38:14.000000000","message":"same as on L304","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":372,"context_line":"        :param portgroup: a portgroup within the request body."},{"line_number":373,"context_line":"        \"\"\""},{"line_number":374,"context_line":"        if not api_utils.allow_portgroups():"},{"line_number":375,"context_line":"            raise exception.NotFound()"},{"line_number":376,"context_line":""},{"line_number":377,"context_line":"        cdict \u003d pecan.request.context.to_dict()"},{"line_number":378,"context_line":"        policy.authorize(\u0027baremetal:portgroup:create\u0027, cdict, cdict)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_53976547","line":375,"updated":"2016-11-02 17:31:53.000000000","message":"should be exception.NotAcceptable()","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":372,"context_line":"        :param portgroup: a portgroup within the request body."},{"line_number":373,"context_line":"        \"\"\""},{"line_number":374,"context_line":"        if not api_utils.allow_portgroups():"},{"line_number":375,"context_line":"            raise exception.NotFound()"},{"line_number":376,"context_line":""},{"line_number":377,"context_line":"        cdict \u003d pecan.request.context.to_dict()"},{"line_number":378,"context_line":"        policy.authorize(\u0027baremetal:portgroup:create\u0027, cdict, cdict)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_11078c82","line":375,"in_reply_to":"ba5da102_53976547","updated":"2016-11-03 11:38:14.000000000","message":"same as on L304","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":402,"context_line":"        :param patch: a json PATCH document to apply to this portgroup."},{"line_number":403,"context_line":"        \"\"\""},{"line_number":404,"context_line":"        if not api_utils.allow_portgroups():"},{"line_number":405,"context_line":"            raise exception.NotFound()"},{"line_number":406,"context_line":""},{"line_number":407,"context_line":"        cdict \u003d pecan.request.context.to_dict()"},{"line_number":408,"context_line":"        policy.authorize(\u0027baremetal:portgroup:update\u0027, cdict, cdict)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_b31b61c9","line":405,"updated":"2016-11-02 17:31:53.000000000","message":"should be exception.NotAcceptable()","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":402,"context_line":"        :param patch: a json PATCH document to apply to this portgroup."},{"line_number":403,"context_line":"        \"\"\""},{"line_number":404,"context_line":"        if not api_utils.allow_portgroups():"},{"line_number":405,"context_line":"            raise exception.NotFound()"},{"line_number":406,"context_line":""},{"line_number":407,"context_line":"        cdict \u003d pecan.request.context.to_dict()"},{"line_number":408,"context_line":"        policy.authorize(\u0027baremetal:portgroup:update\u0027, cdict, cdict)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_51fd846c","line":405,"in_reply_to":"ba5da102_b31b61c9","updated":"2016-11-03 11:38:14.000000000","message":"same as on L304","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":445,"context_line":"                rpc_portgroup[field] \u003d patch_val"},{"line_number":446,"context_line":""},{"line_number":447,"context_line":"        rpc_node \u003d objects.Node.get_by_id(pecan.request.context,"},{"line_number":448,"context_line":"                                          rpc_portgroup.node_id)"},{"line_number":449,"context_line":"        topic \u003d pecan.request.rpcapi.get_topic_for(rpc_node)"},{"line_number":450,"context_line":""},{"line_number":451,"context_line":"        new_portgroup \u003d pecan.request.rpcapi.update_portgroup("}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_16e5dbda","line":448,"updated":"2016-11-02 17:31:53.000000000","message":"I\u0027ve forgotten (if I ever knew) where in the code it is enforced that a portgroup must have a .node_id. I\u0027ll assume it works and this is always valid.","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":445,"context_line":"                rpc_portgroup[field] \u003d patch_val"},{"line_number":446,"context_line":""},{"line_number":447,"context_line":"        rpc_node \u003d objects.Node.get_by_id(pecan.request.context,"},{"line_number":448,"context_line":"                                          rpc_portgroup.node_id)"},{"line_number":449,"context_line":"        topic \u003d pecan.request.rpcapi.get_topic_for(rpc_node)"},{"line_number":450,"context_line":""},{"line_number":451,"context_line":"        new_portgroup \u003d pecan.request.rpcapi.update_portgroup("}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_317f30e1","line":448,"in_reply_to":"ba5da102_16e5dbda","updated":"2016-11-03 11:38:14.000000000","message":"same as for port, node_uuid is mandatory field.","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":462,"context_line":"        :param portgroup_ident: UUID or logical name of a portgroup."},{"line_number":463,"context_line":"        \"\"\""},{"line_number":464,"context_line":"        if not api_utils.allow_portgroups():"},{"line_number":465,"context_line":"            raise exception.NotFound()"},{"line_number":466,"context_line":""},{"line_number":467,"context_line":"        cdict \u003d pecan.request.context.to_dict()"},{"line_number":468,"context_line":"        policy.authorize(\u0027baremetal:portgroup:delete\u0027, cdict, cdict)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_36381f3d","line":465,"updated":"2016-11-02 17:31:53.000000000","message":"should be exception.NotAcceptable()","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":462,"context_line":"        :param portgroup_ident: UUID or logical name of a portgroup."},{"line_number":463,"context_line":"        \"\"\""},{"line_number":464,"context_line":"        if not api_utils.allow_portgroups():"},{"line_number":465,"context_line":"            raise exception.NotFound()"},{"line_number":466,"context_line":""},{"line_number":467,"context_line":"        cdict \u003d pecan.request.context.to_dict()"},{"line_number":468,"context_line":"        policy.authorize(\u0027baremetal:portgroup:delete\u0027, cdict, cdict)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_31665051","line":465,"in_reply_to":"ba5da102_36381f3d","updated":"2016-11-03 11:38:14.000000000","message":"same as on  L304","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"}],"ironic/api/controllers/v1/utils.py":[{"author":{"_account_id":12356,"name":"Vladyslav Drok","email":"vdrok@mirantis.com","username":"vdrok"},"change_message_id":"bd02c0ea25b470a930031c60f1346269408a534d","unresolved":false,"context_lines":[{"line_number":161,"context_line":"    if utils.is_valid_logical_name(portgroup_ident):"},{"line_number":162,"context_line":"        return objects.Portgroup.get_by_name(pecan.request.context,"},{"line_number":163,"context_line":"                                             portgroup_ident)"},{"line_number":164,"context_line":"    else:"},{"line_number":165,"context_line":"        raise exception.InvalidUuidOrName(name\u003dportgroup_ident)"},{"line_number":166,"context_line":""},{"line_number":167,"context_line":""}],"source_content_type":"text/x-python","patch_set":7,"id":"9ad45d7e_f103c10b","line":164,"range":{"start_line":164,"start_character":4,"end_line":164,"end_character":8},"updated":"2016-08-08 17:56:40.000000000","message":"nit - no need for else here","commit_id":"02d603109e429c58d6a2721e762e1431ac28a6f4"},{"author":{"_account_id":12356,"name":"Vladyslav Drok","email":"vdrok@mirantis.com","username":"vdrok"},"change_message_id":"bd02c0ea25b470a930031c60f1346269408a534d","unresolved":false,"context_lines":[{"line_number":417,"context_line":"def allow_portgroups():"},{"line_number":418,"context_line":"    \"\"\"Check if we should show portgroup info."},{"line_number":419,"context_line":""},{"line_number":420,"context_line":"    Version 1.22 of the API added support for PortGroups."},{"line_number":421,"context_line":"    \"\"\""},{"line_number":422,"context_line":"    return (pecan.request.version.minor \u003e\u003d"},{"line_number":423,"context_line":"            versions.MINOR_23_PORTGROUPS)"}],"source_content_type":"text/x-python","patch_set":7,"id":"9ad45d7e_913a45cc","line":420,"range":{"start_line":420,"start_character":14,"end_line":420,"end_character":16},"updated":"2016-08-08 17:56:40.000000000","message":"1.23","commit_id":"02d603109e429c58d6a2721e762e1431ac28a6f4"},{"author":{"_account_id":12356,"name":"Vladyslav Drok","email":"vdrok@mirantis.com","username":"vdrok"},"change_message_id":"e8aa3beb2d3a2915d1fed481ac0f3670703da02f","unresolved":false,"context_lines":[{"line_number":161,"context_line":"    if utils.is_valid_logical_name(portgroup_ident):"},{"line_number":162,"context_line":"        return objects.Portgroup.get_by_name(pecan.request.context,"},{"line_number":163,"context_line":"                                             portgroup_ident)"},{"line_number":164,"context_line":"        raise exception.InvalidUuidOrName(name\u003dportgroup_ident)"},{"line_number":165,"context_line":""},{"line_number":166,"context_line":""},{"line_number":167,"context_line":"def is_valid_node_name(name):"}],"source_content_type":"text/x-python","patch_set":19,"id":"1ac06dbe_dd6f81fa","line":164,"updated":"2016-08-25 11:59:15.000000000","message":"This is overindented, it needs to be on the same level as ifs.","commit_id":"3b1cda9c75e2b5b53b78b2876131b43351d9952a"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":143,"context_line":""},{"line_number":144,"context_line":""},{"line_number":145,"context_line":"def get_rpc_portgroup(portgroup_ident):"},{"line_number":146,"context_line":"    \"\"\"Get the RPC portgroup from the portgroup uuid or logical name."},{"line_number":147,"context_line":""},{"line_number":148,"context_line":"    :param portgroup_ident: the UUID or logical name of a portgroup."},{"line_number":149,"context_line":""}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_90949643","line":146,"updated":"2016-11-02 17:31:53.000000000","message":"nit s/uuid/UUID/ but yeah, i know, you copy/pasted :)","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":143,"context_line":""},{"line_number":144,"context_line":""},{"line_number":145,"context_line":"def get_rpc_portgroup(portgroup_ident):"},{"line_number":146,"context_line":"    \"\"\"Get the RPC portgroup from the portgroup uuid or logical name."},{"line_number":147,"context_line":""},{"line_number":148,"context_line":"    :param portgroup_ident: the UUID or logical name of a portgroup."},{"line_number":149,"context_line":""}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_b793305a","line":146,"in_reply_to":"ba5da102_90949643","updated":"2016-11-03 11:38:14.000000000","message":"Done","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":414,"context_line":""},{"line_number":415,"context_line":""},{"line_number":416,"context_line":"def allow_portgroups():"},{"line_number":417,"context_line":"    \"\"\"Check if we should show portgroup info."},{"line_number":418,"context_line":""},{"line_number":419,"context_line":"    Version 1.23 of the API added support for PortGroups."},{"line_number":420,"context_line":"    \"\"\""}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_50ebde77","line":417,"updated":"2016-11-02 17:31:53.000000000","message":"nit: it isn\u0027t just showing portgroup info, right? it is any operation related to portgroups. So eg \u0027Check if we should support portgroup operations\u0027 ?","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":414,"context_line":""},{"line_number":415,"context_line":""},{"line_number":416,"context_line":"def allow_portgroups():"},{"line_number":417,"context_line":"    \"\"\"Check if we should show portgroup info."},{"line_number":418,"context_line":""},{"line_number":419,"context_line":"    Version 1.23 of the API added support for PortGroups."},{"line_number":420,"context_line":"    \"\"\""}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_d7ac248e","line":417,"in_reply_to":"ba5da102_50ebde77","updated":"2016-11-03 11:38:14.000000000","message":"Done","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"}],"ironic/api/controllers/v1/versions.py":[{"author":{"_account_id":12356,"name":"Vladyslav Drok","email":"vdrok@mirantis.com","username":"vdrok"},"change_message_id":"bd02c0ea25b470a930031c60f1346269408a534d","unresolved":false,"context_lines":[{"line_number":17,"context_line":"BASE_VERSION \u003d 1"},{"line_number":18,"context_line":""},{"line_number":19,"context_line":"# Here goes a short log of changes in every version."},{"line_number":20,"context_line":"# Refer to doc/source/webapi/v1.rst for a detailed explanation of what"},{"line_number":21,"context_line":"# each version contains."},{"line_number":22,"context_line":"#"},{"line_number":23,"context_line":"# v1.0: corresponds to Juno API, not supported since Kilo"}],"source_content_type":"text/x-python","patch_set":7,"id":"9ad45d7e_d14b1d58","line":20,"range":{"start_line":20,"start_character":11,"end_line":20,"end_character":35},"updated":"2016-08-08 17:56:40.000000000","message":"This change should be here too","commit_id":"02d603109e429c58d6a2721e762e1431ac28a6f4"},{"author":{"_account_id":12356,"name":"Vladyslav Drok","email":"vdrok@mirantis.com","username":"vdrok"},"change_message_id":"e8aa3beb2d3a2915d1fed481ac0f3670703da02f","unresolved":false,"context_lines":[{"line_number":80,"context_line":"MINOR_23_PORTGROUPS \u003d 23"},{"line_number":81,"context_line":""},{"line_number":82,"context_line":"# When adding another version, update MINOR_MAX_VERSION and also update"},{"line_number":83,"context_line":"# doc/source/webapi/v1.rst with a detailed explanation of what the version has"},{"line_number":84,"context_line":"# changed."},{"line_number":85,"context_line":"MINOR_MAX_VERSION \u003d MINOR_23_PORTGROUPS"},{"line_number":86,"context_line":""}],"source_content_type":"text/x-python","patch_set":19,"id":"1ac06dbe_5d539139","line":83,"range":{"start_line":83,"start_character":2,"end_line":83,"end_character":26},"updated":"2016-08-25 11:59:15.000000000","message":"This addition is still missing.","commit_id":"3b1cda9c75e2b5b53b78b2876131b43351d9952a"},{"author":{"_account_id":11929,"name":"Michael Turek","email":"mjturek@linux.vnet.ibm.com","username":"mjturek"},"change_message_id":"028fe93dc468b4e4c3f04c38004714faa03025f5","unresolved":false,"context_lines":[{"line_number":80,"context_line":"MINOR_23_PORTGROUPS \u003d 23"},{"line_number":81,"context_line":""},{"line_number":82,"context_line":"# When adding another version, update MINOR_MAX_VERSION and also update"},{"line_number":83,"context_line":"# doc/source/webapi/v1.rst with a detailed explanation of what the version has"},{"line_number":84,"context_line":"# changed."},{"line_number":85,"context_line":"MINOR_MAX_VERSION \u003d MINOR_23_PORTGROUPS"},{"line_number":86,"context_line":""}],"source_content_type":"text/x-python","patch_set":19,"id":"1ac06dbe_dc03fa74","line":83,"range":{"start_line":83,"start_character":2,"end_line":83,"end_character":26},"in_reply_to":"1ac06dbe_5d539139","updated":"2016-08-25 13:51:08.000000000","message":"v1.rst has been removed. It now points to\n\n../dev/webapi.html\n\nshould it be added there instead? (There doesn\u0027t seem to be any versioning history there yet)","commit_id":"3b1cda9c75e2b5b53b78b2876131b43351d9952a"}],"ironic/tests/unit/api/test_root.py":[{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"6b4af22e7ee24ad33aa9252e9b65a63960a2af29","unresolved":false,"context_lines":[{"line_number":78,"context_line":"        self._test_get_root()"},{"line_number":79,"context_line":""},{"line_number":80,"context_line":"    def test_get_v1_23_root(self):"},{"line_number":81,"context_line":"        self._test_get_root(headers\u003d{\u0027X-OpenStack-Ironic-API-Version\u0027: \u00271.23\u0027},"},{"line_number":82,"context_line":"                            additional_expected_resources\u003d[\u0027heartbeat\u0027,"},{"line_number":83,"context_line":"                                                           \u0027lookup\u0027,"},{"line_number":84,"context_line":"                                                           \u0027portgroups\u0027])"}],"source_content_type":"text/x-python","patch_set":31,"id":"fa7ab95a_8fb8a8c9","line":81,"updated":"2016-08-30 21:34:41.000000000","message":"Seems like there should be a test for version 1.22 of the API also. Make sure that there is no portgroups","commit_id":"e8927d4b363f77cf08b248ed371d9ebdd500e8dd"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"286ae15f8fec21e6a9103f5706c4246a1cd0d95b","unresolved":false,"context_lines":[{"line_number":39,"context_line":"class TestV1Root(base.BaseApiTest):"},{"line_number":40,"context_line":""},{"line_number":41,"context_line":"    def _test_get_root(self, headers\u003dNone, additional_expected_resources\u003dNone):"},{"line_number":42,"context_line":"        if not headers:"},{"line_number":43,"context_line":"            headers \u003d {}"},{"line_number":44,"context_line":"        if not additional_expected_resources:"},{"line_number":45,"context_line":"            additional_expected_resources \u003d []"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_19177b52","line":42,"updated":"2016-09-03 00:00:22.000000000","message":"if headers is None:","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"88862cd728e8298786ed18041ea974f3e81573da","unresolved":false,"context_lines":[{"line_number":39,"context_line":"class TestV1Root(base.BaseApiTest):"},{"line_number":40,"context_line":""},{"line_number":41,"context_line":"    def _test_get_root(self, headers\u003dNone, additional_expected_resources\u003dNone):"},{"line_number":42,"context_line":"        if not headers:"},{"line_number":43,"context_line":"            headers \u003d {}"},{"line_number":44,"context_line":"        if not additional_expected_resources:"},{"line_number":45,"context_line":"            additional_expected_resources \u003d []"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_64ee0424","line":42,"in_reply_to":"9a89bdaa_19177b52","updated":"2016-09-05 08:47:26.000000000","message":"Done","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"286ae15f8fec21e6a9103f5706c4246a1cd0d95b","unresolved":false,"context_lines":[{"line_number":41,"context_line":"    def _test_get_root(self, headers\u003dNone, additional_expected_resources\u003dNone):"},{"line_number":42,"context_line":"        if not headers:"},{"line_number":43,"context_line":"            headers \u003d {}"},{"line_number":44,"context_line":"        if not additional_expected_resources:"},{"line_number":45,"context_line":"            additional_expected_resources \u003d []"},{"line_number":46,"context_line":"        data \u003d self.get_json(\u0027/\u0027, headers\u003dheaders)"},{"line_number":47,"context_line":"        self.assertEqual(\u0027v1\u0027, data[\u0027id\u0027])"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_7906c721","line":44,"updated":"2016-09-03 00:00:22.000000000","message":"If additional_expected_resources is None:","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"88862cd728e8298786ed18041ea974f3e81573da","unresolved":false,"context_lines":[{"line_number":41,"context_line":"    def _test_get_root(self, headers\u003dNone, additional_expected_resources\u003dNone):"},{"line_number":42,"context_line":"        if not headers:"},{"line_number":43,"context_line":"            headers \u003d {}"},{"line_number":44,"context_line":"        if not additional_expected_resources:"},{"line_number":45,"context_line":"            additional_expected_resources \u003d []"},{"line_number":46,"context_line":"        data \u003d self.get_json(\u0027/\u0027, headers\u003dheaders)"},{"line_number":47,"context_line":"        self.assertEqual(\u0027v1\u0027, data[\u0027id\u0027])"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_84f3080a","line":44,"in_reply_to":"9a89bdaa_7906c721","updated":"2016-09-05 08:47:26.000000000","message":"Done","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"}],"ironic/tests/unit/api/utils.py":[{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"6b4af22e7ee24ad33aa9252e9b65a63960a2af29","unresolved":false,"context_lines":[{"line_number":133,"context_line":"    return node"},{"line_number":134,"context_line":""},{"line_number":135,"context_line":""},{"line_number":136,"context_line":"def portgroup_post_data(**kw):"},{"line_number":137,"context_line":"    portgroup \u003d utils.get_test_portgroup(**kw)"},{"line_number":138,"context_line":"    portgroup.pop(\u0027node_id\u0027)"},{"line_number":139,"context_line":"    internal \u003d portgroup_controller.PortgroupPatchType.internal_attrs()"}],"source_content_type":"text/x-python","patch_set":31,"id":"fa7ab95a_af09ec96","line":136,"updated":"2016-08-30 21:34:41.000000000","message":"Docstring please","commit_id":"e8927d4b363f77cf08b248ed371d9ebdd500e8dd"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"6b4af22e7ee24ad33aa9252e9b65a63960a2af29","unresolved":false,"context_lines":[{"line_number":140,"context_line":"    return remove_internal(portgroup, internal)"},{"line_number":141,"context_line":""},{"line_number":142,"context_line":""},{"line_number":143,"context_line":"def post_get_test_portgroup(**kw):"},{"line_number":144,"context_line":"    portgroup \u003d portgroup_post_data(**kw)"},{"line_number":145,"context_line":"    node \u003d utils.get_test_node()"},{"line_number":146,"context_line":"    portgroup[\u0027node_uuid\u0027] \u003d kw.get(\u0027node_uuid\u0027, node[\u0027uuid\u0027])"}],"source_content_type":"text/x-python","patch_set":31,"id":"fa7ab95a_0ffbb879","line":143,"updated":"2016-08-30 21:34:41.000000000","message":"Docstring please","commit_id":"e8927d4b363f77cf08b248ed371d9ebdd500e8dd"}],"ironic/tests/unit/api/v1/test_portgroups.py":[{"author":{"_account_id":13689,"name":"Hironori Shiina","email":"Hironori.Shiina@fujitsu.com","username":"shiina"},"change_message_id":"fd517ac9be5398b8b2c3815ca9356e912032e092","unresolved":false,"context_lines":[{"line_number":120,"context_line":"        self.assertEqual(\u0027application/json\u0027, response.content_type)"},{"line_number":121,"context_line":"        self.assertIn(\u0027spongebob\u0027, response.json[\u0027error_message\u0027])"},{"line_number":122,"context_line":""},{"line_number":123,"context_line":"    def test_get_custom_fields_invalid_api_version(self):"},{"line_number":124,"context_line":"        portgroup \u003d obj_utils.create_test_portgroup(self.context,"},{"line_number":125,"context_line":"                                                    node_id\u003dself.node.id)"},{"line_number":126,"context_line":"        fields \u003d \u0027uuid,extra\u0027"}],"source_content_type":"text/x-python","patch_set":12,"id":"9ad45d7e_2c940489","line":123,"range":{"start_line":123,"start_character":16,"end_line":123,"end_character":31},"updated":"2016-08-12 07:11:39.000000000","message":"It is not necessary to specify fields because custom fields is allowed since microversion 1.8 which is older than 1.23. Portgroup itself is invisible from older microversion than 1.8.","commit_id":"e55c5f8be7b26ea77c66eb97b396742e0166b3e1"},{"author":{"_account_id":13689,"name":"Hironori Shiina","email":"Hironori.Shiina@fujitsu.com","username":"shiina"},"change_message_id":"fd517ac9be5398b8b2c3815ca9356e912032e092","unresolved":false,"context_lines":[{"line_number":125,"context_line":"                                                    node_id\u003dself.node.id)"},{"line_number":126,"context_line":"        fields \u003d \u0027uuid,extra\u0027"},{"line_number":127,"context_line":"        response \u003d self.get_json("},{"line_number":128,"context_line":"            \u0027/portgroups/%s?fields\u003d%s\u0027 % (portgroup.uuid, fields),"},{"line_number":129,"context_line":"            expect_errors\u003dTrue)"},{"line_number":130,"context_line":"        self.assertEqual(http_client.NOT_FOUND, response.status_int)"},{"line_number":131,"context_line":""}],"source_content_type":"text/x-python","patch_set":12,"id":"9ad45d7e_ec42ec0d","line":128,"range":{"start_line":128,"start_character":27,"end_line":128,"end_character":37},"updated":"2016-08-12 07:11:39.000000000","message":"Fields is not necessary to cover api_utils.allow_portgroups in get_one.","commit_id":"e55c5f8be7b26ea77c66eb97b396742e0166b3e1"},{"author":{"_account_id":13689,"name":"Hironori Shiina","email":"Hironori.Shiina@fujitsu.com","username":"shiina"},"change_message_id":"fd517ac9be5398b8b2c3815ca9356e912032e092","unresolved":false,"context_lines":[{"line_number":126,"context_line":"        fields \u003d \u0027uuid,extra\u0027"},{"line_number":127,"context_line":"        response \u003d self.get_json("},{"line_number":128,"context_line":"            \u0027/portgroups/%s?fields\u003d%s\u0027 % (portgroup.uuid, fields),"},{"line_number":129,"context_line":"            expect_errors\u003dTrue)"},{"line_number":130,"context_line":"        self.assertEqual(http_client.NOT_FOUND, response.status_int)"},{"line_number":131,"context_line":""},{"line_number":132,"context_line":"    def test_detail(self):"}],"source_content_type":"text/x-python","patch_set":12,"id":"9ad45d7e_4c75f861","line":129,"updated":"2016-08-12 07:11:39.000000000","message":"I prefer adding the following argument to clarify what is tested.\n\nheaders\u003d{api_base.Version.string: str(api_v1.MIN_VER)}","commit_id":"e55c5f8be7b26ea77c66eb97b396742e0166b3e1"},{"author":{"_account_id":13689,"name":"Hironori Shiina","email":"Hironori.Shiina@fujitsu.com","username":"shiina"},"change_message_id":"fd517ac9be5398b8b2c3815ca9356e912032e092","unresolved":false,"context_lines":[{"line_number":232,"context_line":"        self.assertThat(data[\u0027portgroups\u0027], HasLength(1))"},{"line_number":233,"context_line":"        self.assertEqual(target_address, data[\u0027portgroups\u0027][0][\u0027address\u0027])"},{"line_number":234,"context_line":""},{"line_number":235,"context_line":"    def test_portgroup_by_address_invalid_api_version(self):"},{"line_number":236,"context_line":"        address \u003d \"aa:bb:cc:dd:ee:f1\""},{"line_number":237,"context_line":"        obj_utils.create_test_portgroup("},{"line_number":238,"context_line":"            self.context, node_id\u003dself.node.id, uuid\u003duuidutils.generate_uuid(),"}],"source_content_type":"text/x-python","patch_set":12,"id":"9ad45d7e_aa8d7432","line":235,"updated":"2016-08-12 07:11:39.000000000","message":"This test just covers api_utils.allow_portgroups in get_all. It is not related to specifying address. I prefer not specifying address in order to clarify what is tested.","commit_id":"e55c5f8be7b26ea77c66eb97b396742e0166b3e1"},{"author":{"_account_id":13689,"name":"Hironori Shiina","email":"Hironori.Shiina@fujitsu.com","username":"shiina"},"change_message_id":"fd517ac9be5398b8b2c3815ca9356e912032e092","unresolved":false,"context_lines":[{"line_number":368,"context_line":"        mock_upd.return_value \u003d self.portgroup"},{"line_number":369,"context_line":"        response \u003d self.patch_json(\u0027/portgroups/%s\u0027 % self.portgroup.name,"},{"line_number":370,"context_line":"                                   [{\u0027path\u0027: \u0027/name\u0027,"},{"line_number":371,"context_line":"                                       \u0027value\u0027: \u0027aa:bb_cc\u0027,"},{"line_number":372,"context_line":"                                     \u0027op\u0027: \u0027replace\u0027}],"},{"line_number":373,"context_line":"                                   headers\u003dself.headers,"},{"line_number":374,"context_line":"                                   expect_errors\u003dTrue)"}],"source_content_type":"text/x-python","patch_set":12,"id":"9ad45d7e_4f4e8a3b","line":371,"range":{"start_line":371,"start_character":37,"end_line":371,"end_character":39},"updated":"2016-08-12 07:11:39.000000000","message":"nit: extra whitespces","commit_id":"e55c5f8be7b26ea77c66eb97b396742e0166b3e1"},{"author":{"_account_id":13689,"name":"Hironori Shiina","email":"Hironori.Shiina@fujitsu.com","username":"shiina"},"change_message_id":"d6f3ee3f06e3c7d637ec618bca8fdf49b5379a8d","unresolved":false,"context_lines":[{"line_number":145,"context_line":"        response \u003d self.get_json(\u0027/portgroups/%s/detail\u0027 % portgroup.uuid,"},{"line_number":146,"context_line":"                                 expect_errors\u003dTrue, headers\u003dself.headers)"},{"line_number":147,"context_line":"        self.assertEqual(http_client.NOT_FOUND, response.status_int)"},{"line_number":148,"context_line":""},{"line_number":149,"context_line":"    def test_many(self):"},{"line_number":150,"context_line":"        portgroups \u003d []"},{"line_number":151,"context_line":"        for id_ in range(5):"}],"source_content_type":"text/x-python","patch_set":14,"id":"3ac371cc_c2ba030a","line":148,"updated":"2016-08-16 07:03:57.000000000","message":"It would be better to add test_detail_invalid_api_version.","commit_id":"f491cc63ba89863f765cbc1403c199f174af5918"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"286ae15f8fec21e6a9103f5706c4246a1cd0d95b","unresolved":false,"context_lines":[{"line_number":720,"context_line":"        super(TestPost, self).setUp()"},{"line_number":721,"context_line":"        self.node \u003d obj_utils.create_test_node(self.context)"},{"line_number":722,"context_line":""},{"line_number":723,"context_line":"    @mock.patch.object(timeutils, \u0027utcnow\u0027)"},{"line_number":724,"context_line":"    def test_create_portgroup(self, mock_utcnow):"},{"line_number":725,"context_line":"        pdict \u003d apiutils.post_get_test_portgroup()"},{"line_number":726,"context_line":"        test_time \u003d datetime.datetime(2000, 1, 1, 0, 0)"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_94e4323c","line":723,"updated":"2016-09-03 00:00:22.000000000","message":"I believe could do:\n\n @mock.patch.object(timeutils, \u0027utcnow\u0027, datetime.datetime(2000, 1, 1, 0, 0))","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"88862cd728e8298786ed18041ea974f3e81573da","unresolved":false,"context_lines":[{"line_number":720,"context_line":"        super(TestPost, self).setUp()"},{"line_number":721,"context_line":"        self.node \u003d obj_utils.create_test_node(self.context)"},{"line_number":722,"context_line":""},{"line_number":723,"context_line":"    @mock.patch.object(timeutils, \u0027utcnow\u0027)"},{"line_number":724,"context_line":"    def test_create_portgroup(self, mock_utcnow):"},{"line_number":725,"context_line":"        pdict \u003d apiutils.post_get_test_portgroup()"},{"line_number":726,"context_line":"        test_time \u003d datetime.datetime(2000, 1, 1, 0, 0)"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_8441480e","line":723,"in_reply_to":"9a89bdaa_94e4323c","updated":"2016-09-05 08:47:26.000000000","message":"I\u0027ve added autospec\u003dTrue, as we doing in all other places where mocking \u0027utcnow\u0027\n\nhttps://github.com/openstack/ironic/blob/953f06aefd4a3684b04053a956e594217ff82ece/ironic/tests/unit/db/test_conductor.py#L177","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"286ae15f8fec21e6a9103f5706c4246a1cd0d95b","unresolved":false,"context_lines":[{"line_number":741,"context_line":"        self.assertEqual(urlparse.urlparse(response.location).path,"},{"line_number":742,"context_line":"                         expected_location)"},{"line_number":743,"context_line":""},{"line_number":744,"context_line":"    @mock.patch.object(timeutils, \u0027utcnow\u0027)"},{"line_number":745,"context_line":"    def test_create_portgroup_invalid_api_version(self, mock_utcnow):"},{"line_number":746,"context_line":"        pdict \u003d apiutils.post_get_test_portgroup()"},{"line_number":747,"context_line":"        test_time \u003d datetime.datetime(2000, 1, 1, 0, 0)"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_b4cf76b2","line":744,"updated":"2016-09-03 00:00:22.000000000","message":"See L723","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"88862cd728e8298786ed18041ea974f3e81573da","unresolved":false,"context_lines":[{"line_number":741,"context_line":"        self.assertEqual(urlparse.urlparse(response.location).path,"},{"line_number":742,"context_line":"                         expected_location)"},{"line_number":743,"context_line":""},{"line_number":744,"context_line":"    @mock.patch.object(timeutils, \u0027utcnow\u0027)"},{"line_number":745,"context_line":"    def test_create_portgroup_invalid_api_version(self, mock_utcnow):"},{"line_number":746,"context_line":"        pdict \u003d apiutils.post_get_test_portgroup()"},{"line_number":747,"context_line":"        test_time \u003d datetime.datetime(2000, 1, 1, 0, 0)"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_a4464c21","line":744,"in_reply_to":"9a89bdaa_b4cf76b2","updated":"2016-09-05 08:47:26.000000000","message":"Done","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"286ae15f8fec21e6a9103f5706c4246a1cd0d95b","unresolved":false,"context_lines":[{"line_number":858,"context_line":"        self.assertEqual(http_client.BAD_REQUEST, response.status_int)"},{"line_number":859,"context_line":"        self.assertTrue(response.json[\u0027error_message\u0027])"},{"line_number":860,"context_line":""},{"line_number":861,"context_line":"    def test_create_portgroup_address_already_exist(self):"},{"line_number":862,"context_line":"        address \u003d \u0027AA:AA:AA:11:22:33\u0027"},{"line_number":863,"context_line":"        pdict \u003d apiutils.post_get_test_portgroup(address\u003daddress)"},{"line_number":864,"context_line":"        self.post_json(\u0027/portgroups\u0027, pdict, headers\u003dself.headers)"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_1481024b","line":861,"updated":"2016-09-03 00:00:22.000000000","message":"nit:  s/exist/exists/","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"286ae15f8fec21e6a9103f5706c4246a1cd0d95b","unresolved":false,"context_lines":[{"line_number":938,"context_line":"                    headers\u003dself.headers)"},{"line_number":939,"context_line":"        self.assertTrue(mock_dpt.called)"},{"line_number":940,"context_line":""},{"line_number":941,"context_line":"    def test_delete_portgroup_byname_not_existed(self, mock_dpt):"},{"line_number":942,"context_line":"        res \u003d self.delete(\u0027/portgroups/%s\u0027 % \u0027blah\u0027, expect_errors\u003dTrue,"},{"line_number":943,"context_line":"                          headers\u003dself.headers)"},{"line_number":944,"context_line":"        self.assertEqual(http_client.NOT_FOUND, res.status_code)"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_d486ba64","line":941,"updated":"2016-09-03 00:00:22.000000000","message":"nit:\n\n s/existed/existing/","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":7711,"name":"Yuriy Zveryanskyy","email":"yzveryanskyy@mirantis.com","username":"yuriyz"},"change_message_id":"74af5a2d9807bebfb5e9bbcd6a12958357ea0b9c","unresolved":false,"context_lines":[{"line_number":741,"context_line":"        self.assertEqual(urlparse.urlparse(response.location).path,"},{"line_number":742,"context_line":"                         expected_location)"},{"line_number":743,"context_line":""},{"line_number":744,"context_line":"    @mock.patch.object(timeutils, \u0027utcnow\u0027, autospec\u003dTrue)"},{"line_number":745,"context_line":"    def test_create_portgroup_invalid_api_version(self, mock_utcnow):"},{"line_number":746,"context_line":"        pdict \u003d apiutils.post_get_test_portgroup()"},{"line_number":747,"context_line":"        test_time \u003d datetime.datetime(2000, 1, 1, 0, 0)"}],"source_content_type":"text/x-python","patch_set":33,"id":"9a89bdaa_09bc6404","line":744,"updated":"2016-09-05 10:57:19.000000000","message":"This mock is not needed here.","commit_id":"b9b0aed9346607e313919e74d325d14271a58ca8"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"ad3fabea85082288fb639c4369f7fd9558b6ef93","unresolved":false,"context_lines":[{"line_number":741,"context_line":"        self.assertEqual(urlparse.urlparse(response.location).path,"},{"line_number":742,"context_line":"                         expected_location)"},{"line_number":743,"context_line":""},{"line_number":744,"context_line":"    @mock.patch.object(timeutils, \u0027utcnow\u0027, autospec\u003dTrue)"},{"line_number":745,"context_line":"    def test_create_portgroup_invalid_api_version(self, mock_utcnow):"},{"line_number":746,"context_line":"        pdict \u003d apiutils.post_get_test_portgroup()"},{"line_number":747,"context_line":"        test_time \u003d datetime.datetime(2000, 1, 1, 0, 0)"}],"source_content_type":"text/x-python","patch_set":33,"id":"9a89bdaa_e217524f","line":744,"in_reply_to":"9a89bdaa_09bc6404","updated":"2016-09-05 13:55:48.000000000","message":"Done","commit_id":"b9b0aed9346607e313919e74d325d14271a58ca8"},{"author":{"_account_id":7711,"name":"Yuriy Zveryanskyy","email":"yzveryanskyy@mirantis.com","username":"yuriyz"},"change_message_id":"74af5a2d9807bebfb5e9bbcd6a12958357ea0b9c","unresolved":false,"context_lines":[{"line_number":753,"context_line":""},{"line_number":754,"context_line":"    def test_create_portgroup_invalid_node_uuid_older_version(self):"},{"line_number":755,"context_line":"        pdict \u003d apiutils.post_get_test_portgroup("},{"line_number":756,"context_line":"            node_uuid\u003duuidutils.generate_uuid())"},{"line_number":757,"context_line":"        response \u003d self.post_json("},{"line_number":758,"context_line":"            \u0027/portgroups\u0027, pdict, headers\u003d{api_base.Version.string: \u00271.14\u0027},"},{"line_number":759,"context_line":"            expect_errors\u003dTrue)"}],"source_content_type":"text/x-python","patch_set":33,"id":"9a89bdaa_6926d069","line":756,"updated":"2016-09-05 10:57:19.000000000","message":"This is valid node_uuid but different comparing to previous test. API version check is first in the code. What is purpose of this test?","commit_id":"b9b0aed9346607e313919e74d325d14271a58ca8"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"ad3fabea85082288fb639c4369f7fd9558b6ef93","unresolved":false,"context_lines":[{"line_number":753,"context_line":""},{"line_number":754,"context_line":"    def test_create_portgroup_invalid_node_uuid_older_version(self):"},{"line_number":755,"context_line":"        pdict \u003d apiutils.post_get_test_portgroup("},{"line_number":756,"context_line":"            node_uuid\u003duuidutils.generate_uuid())"},{"line_number":757,"context_line":"        response \u003d self.post_json("},{"line_number":758,"context_line":"            \u0027/portgroups\u0027, pdict, headers\u003d{api_base.Version.string: \u00271.14\u0027},"},{"line_number":759,"context_line":"            expect_errors\u003dTrue)"}],"source_content_type":"text/x-python","patch_set":33,"id":"9a89bdaa_d65ccf27","line":756,"in_reply_to":"9a89bdaa_6926d069","updated":"2016-09-05 13:55:48.000000000","message":"The test should test that we receive http_client.NOT_FOUND when API version is wrong, even if node with specified uuid not found. But we already have such test L745, so this one should be removed.","commit_id":"b9b0aed9346607e313919e74d325d14271a58ca8"}],"ironic/tests/unit/api/v1/test_utils.py":[{"author":{"_account_id":22226,"name":"Varun Gadiraju","email":"varun.gadiraju@intel.com","username":"gadirajv"},"change_message_id":"fba9c75a64b755b17666cb1581b7c60d03b7f063","unresolved":false,"context_lines":[{"line_number":484,"context_line":"        self.invalid_name \u003d \u0027My Portgroup\u0027"},{"line_number":485,"context_line":"        self.portgroup \u003d test_api_utils.post_get_test_portgroup()"},{"line_number":486,"context_line":""},{"line_number":487,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027)"},{"line_number":488,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_name\u0027)"},{"line_number":489,"context_line":"    def test_get_rpc_portgroup_name(self, mock_gbn, mock_pr):"},{"line_number":490,"context_line":"        mock_pr.version.minor \u003d 10"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_ce30eba1","line":487,"updated":"2016-09-02 22:57:42.000000000","message":"how about do spec_set \u003d[\"context\"] similar to L288","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"88862cd728e8298786ed18041ea974f3e81573da","unresolved":false,"context_lines":[{"line_number":484,"context_line":"        self.invalid_name \u003d \u0027My Portgroup\u0027"},{"line_number":485,"context_line":"        self.portgroup \u003d test_api_utils.post_get_test_portgroup()"},{"line_number":486,"context_line":""},{"line_number":487,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027)"},{"line_number":488,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_name\u0027)"},{"line_number":489,"context_line":"    def test_get_rpc_portgroup_name(self, mock_gbn, mock_pr):"},{"line_number":490,"context_line":"        mock_pr.version.minor \u003d 10"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_a4148cf5","line":487,"in_reply_to":"9a89bdaa_ce30eba1","updated":"2016-09-05 08:47:26.000000000","message":"Done","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":22226,"name":"Varun Gadiraju","email":"varun.gadiraju@intel.com","username":"gadirajv"},"change_message_id":"fba9c75a64b755b17666cb1581b7c60d03b7f063","unresolved":false,"context_lines":[{"line_number":485,"context_line":"        self.portgroup \u003d test_api_utils.post_get_test_portgroup()"},{"line_number":486,"context_line":""},{"line_number":487,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027)"},{"line_number":488,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_name\u0027)"},{"line_number":489,"context_line":"    def test_get_rpc_portgroup_name(self, mock_gbn, mock_pr):"},{"line_number":490,"context_line":"        mock_pr.version.minor \u003d 10"},{"line_number":491,"context_line":"        self.portgroup[\u0027name\u0027] \u003d self.valid_name"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_eeb3ef08","line":488,"updated":"2016-09-02 22:57:42.000000000","message":"can we use autospec\u003dTrue ?","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":22226,"name":"Varun Gadiraju","email":"varun.gadiraju@intel.com","username":"gadirajv"},"change_message_id":"fba9c75a64b755b17666cb1581b7c60d03b7f063","unresolved":false,"context_lines":[{"line_number":487,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027)"},{"line_number":488,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_name\u0027)"},{"line_number":489,"context_line":"    def test_get_rpc_portgroup_name(self, mock_gbn, mock_pr):"},{"line_number":490,"context_line":"        mock_pr.version.minor \u003d 10"},{"line_number":491,"context_line":"        self.portgroup[\u0027name\u0027] \u003d self.valid_name"},{"line_number":492,"context_line":"        mock_gbn.return_value \u003d self.portgroup"},{"line_number":493,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_2e6dd732","line":490,"updated":"2016-09-02 22:57:42.000000000","message":"because get_by_name is mocked, there is no need for the code to assign a value to version.minor because it won\u0027t be accessed. Additionally, pecan.request.version isn\u0027t being used in the function that is being tested, it is pecan.request.contest.","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"88862cd728e8298786ed18041ea974f3e81573da","unresolved":false,"context_lines":[{"line_number":487,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027)"},{"line_number":488,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_name\u0027)"},{"line_number":489,"context_line":"    def test_get_rpc_portgroup_name(self, mock_gbn, mock_pr):"},{"line_number":490,"context_line":"        mock_pr.version.minor \u003d 10"},{"line_number":491,"context_line":"        self.portgroup[\u0027name\u0027] \u003d self.valid_name"},{"line_number":492,"context_line":"        mock_gbn.return_value \u003d self.portgroup"},{"line_number":493,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_c4f990ca","line":490,"in_reply_to":"9a89bdaa_2e6dd732","updated":"2016-09-05 08:47:26.000000000","message":"Done","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":22226,"name":"Varun Gadiraju","email":"varun.gadiraju@intel.com","username":"gadirajv"},"change_message_id":"fba9c75a64b755b17666cb1581b7c60d03b7f063","unresolved":false,"context_lines":[{"line_number":489,"context_line":"    def test_get_rpc_portgroup_name(self, mock_gbn, mock_pr):"},{"line_number":490,"context_line":"        mock_pr.version.minor \u003d 10"},{"line_number":491,"context_line":"        self.portgroup[\u0027name\u0027] \u003d self.valid_name"},{"line_number":492,"context_line":"        mock_gbn.return_value \u003d self.portgroup"},{"line_number":493,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("},{"line_number":494,"context_line":"            self.valid_name))"},{"line_number":495,"context_line":"        self.assertEqual(1, mock_gbn.call_count)"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_6e2fdfa1","line":492,"updated":"2016-09-02 22:57:42.000000000","message":"copy.deepcopy(self.portgroup) should be used so if the function modifies the port group, the expected value is not modified as well.","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"88862cd728e8298786ed18041ea974f3e81573da","unresolved":false,"context_lines":[{"line_number":489,"context_line":"    def test_get_rpc_portgroup_name(self, mock_gbn, mock_pr):"},{"line_number":490,"context_line":"        mock_pr.version.minor \u003d 10"},{"line_number":491,"context_line":"        self.portgroup[\u0027name\u0027] \u003d self.valid_name"},{"line_number":492,"context_line":"        mock_gbn.return_value \u003d self.portgroup"},{"line_number":493,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("},{"line_number":494,"context_line":"            self.valid_name))"},{"line_number":495,"context_line":"        self.assertEqual(1, mock_gbn.call_count)"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_e4f694d6","line":492,"in_reply_to":"9a89bdaa_6e2fdfa1","updated":"2016-09-05 08:47:26.000000000","message":"We don\u0027t modify portgroup object in the function.","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":22226,"name":"Varun Gadiraju","email":"varun.gadiraju@intel.com","username":"gadirajv"},"change_message_id":"fba9c75a64b755b17666cb1581b7c60d03b7f063","unresolved":false,"context_lines":[{"line_number":494,"context_line":"            self.valid_name))"},{"line_number":495,"context_line":"        self.assertEqual(1, mock_gbn.call_count)"},{"line_number":496,"context_line":""},{"line_number":497,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027)"},{"line_number":498,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_uuid\u0027)"},{"line_number":499,"context_line":"    def test_get_rpc_portgroup_uuid(self, mock_gbu, mock_pr):"},{"line_number":500,"context_line":"        mock_pr.version.minor \u003d 10"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_ee25af5c","line":497,"updated":"2016-09-02 22:57:42.000000000","message":"how about do spec_set \u003d[\"context\"] similar to L288","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"88862cd728e8298786ed18041ea974f3e81573da","unresolved":false,"context_lines":[{"line_number":494,"context_line":"            self.valid_name))"},{"line_number":495,"context_line":"        self.assertEqual(1, mock_gbn.call_count)"},{"line_number":496,"context_line":""},{"line_number":497,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027)"},{"line_number":498,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_uuid\u0027)"},{"line_number":499,"context_line":"    def test_get_rpc_portgroup_uuid(self, mock_gbu, mock_pr):"},{"line_number":500,"context_line":"        mock_pr.version.minor \u003d 10"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_442ca04a","line":497,"in_reply_to":"9a89bdaa_ee25af5c","updated":"2016-09-05 08:47:26.000000000","message":"Done","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":22226,"name":"Varun Gadiraju","email":"varun.gadiraju@intel.com","username":"gadirajv"},"change_message_id":"fba9c75a64b755b17666cb1581b7c60d03b7f063","unresolved":false,"context_lines":[{"line_number":495,"context_line":"        self.assertEqual(1, mock_gbn.call_count)"},{"line_number":496,"context_line":""},{"line_number":497,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027)"},{"line_number":498,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_uuid\u0027)"},{"line_number":499,"context_line":"    def test_get_rpc_portgroup_uuid(self, mock_gbu, mock_pr):"},{"line_number":500,"context_line":"        mock_pr.version.minor \u003d 10"},{"line_number":501,"context_line":"        self.portgroup[\u0027uuid\u0027] \u003d self.valid_uuid"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_6ec8bf75","line":498,"updated":"2016-09-02 22:57:42.000000000","message":"can we use autospec\u003dTrue ?","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"88862cd728e8298786ed18041ea974f3e81573da","unresolved":false,"context_lines":[{"line_number":495,"context_line":"        self.assertEqual(1, mock_gbn.call_count)"},{"line_number":496,"context_line":""},{"line_number":497,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027)"},{"line_number":498,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_uuid\u0027)"},{"line_number":499,"context_line":"    def test_get_rpc_portgroup_uuid(self, mock_gbu, mock_pr):"},{"line_number":500,"context_line":"        mock_pr.version.minor \u003d 10"},{"line_number":501,"context_line":"        self.portgroup[\u0027uuid\u0027] \u003d self.valid_uuid"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_1091ee99","line":498,"in_reply_to":"9a89bdaa_6ec8bf75","updated":"2016-09-05 08:47:26.000000000","message":"When autospec is True, object is mocked as nonCallable object. It leads to call error. I\u0027ve tried to add autospec\u003dTrue to https://github.com/openstack/ironic/blob/be492c4c2969f50c75695479fe0e9e3c29e5056f/ironic/tests/unit/api/v1/test_nodes.py#L2043 and get the same failure, looks like oslo_versionedobject can\u0027t be mocked with autospec\u003dTrue.\n\nhttp://paste.openstack.org/show/566813/","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":22226,"name":"Varun Gadiraju","email":"varun.gadiraju@intel.com","username":"gadirajv"},"change_message_id":"fba9c75a64b755b17666cb1581b7c60d03b7f063","unresolved":false,"context_lines":[{"line_number":497,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027)"},{"line_number":498,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_uuid\u0027)"},{"line_number":499,"context_line":"    def test_get_rpc_portgroup_uuid(self, mock_gbu, mock_pr):"},{"line_number":500,"context_line":"        mock_pr.version.minor \u003d 10"},{"line_number":501,"context_line":"        self.portgroup[\u0027uuid\u0027] \u003d self.valid_uuid"},{"line_number":502,"context_line":"        mock_gbu.return_value \u003d self.portgroup"},{"line_number":503,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_1925bbaa","line":500,"updated":"2016-09-02 22:57:42.000000000","message":"see comment on L490","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"88862cd728e8298786ed18041ea974f3e81573da","unresolved":false,"context_lines":[{"line_number":497,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027)"},{"line_number":498,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_uuid\u0027)"},{"line_number":499,"context_line":"    def test_get_rpc_portgroup_uuid(self, mock_gbu, mock_pr):"},{"line_number":500,"context_line":"        mock_pr.version.minor \u003d 10"},{"line_number":501,"context_line":"        self.portgroup[\u0027uuid\u0027] \u003d self.valid_uuid"},{"line_number":502,"context_line":"        mock_gbu.return_value \u003d self.portgroup"},{"line_number":503,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_8426a866","line":500,"in_reply_to":"9a89bdaa_1925bbaa","updated":"2016-09-05 08:47:26.000000000","message":"Done","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":22226,"name":"Varun Gadiraju","email":"varun.gadiraju@intel.com","username":"gadirajv"},"change_message_id":"fba9c75a64b755b17666cb1581b7c60d03b7f063","unresolved":false,"context_lines":[{"line_number":499,"context_line":"    def test_get_rpc_portgroup_uuid(self, mock_gbu, mock_pr):"},{"line_number":500,"context_line":"        mock_pr.version.minor \u003d 10"},{"line_number":501,"context_line":"        self.portgroup[\u0027uuid\u0027] \u003d self.valid_uuid"},{"line_number":502,"context_line":"        mock_gbu.return_value \u003d self.portgroup"},{"line_number":503,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("},{"line_number":504,"context_line":"            self.valid_uuid))"},{"line_number":505,"context_line":"        self.assertEqual(1, mock_gbu.call_count)"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_f9565705","line":502,"updated":"2016-09-02 22:57:42.000000000","message":"see comment for L492","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":22226,"name":"Varun Gadiraju","email":"varun.gadiraju@intel.com","username":"gadirajv"},"change_message_id":"fba9c75a64b755b17666cb1581b7c60d03b7f063","unresolved":false,"context_lines":[{"line_number":504,"context_line":"            self.valid_uuid))"},{"line_number":505,"context_line":"        self.assertEqual(1, mock_gbu.call_count)"},{"line_number":506,"context_line":""},{"line_number":507,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027)"},{"line_number":508,"context_line":"    def test_get_rpc_portgroup_invalid_name(self, mock_pr):"},{"line_number":509,"context_line":"        mock_pr.version.minor \u003d 10"},{"line_number":510,"context_line":"        self.assertRaises(exception.InvalidUuidOrName,"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_2e207749","line":507,"updated":"2016-09-02 22:57:42.000000000","message":"this doesn\u0027t seem necessary because pecan.request is not used in the code path when there is an invalid name.","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"88862cd728e8298786ed18041ea974f3e81573da","unresolved":false,"context_lines":[{"line_number":504,"context_line":"            self.valid_uuid))"},{"line_number":505,"context_line":"        self.assertEqual(1, mock_gbu.call_count)"},{"line_number":506,"context_line":""},{"line_number":507,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027)"},{"line_number":508,"context_line":"    def test_get_rpc_portgroup_invalid_name(self, mock_pr):"},{"line_number":509,"context_line":"        mock_pr.version.minor \u003d 10"},{"line_number":510,"context_line":"        self.assertRaises(exception.InvalidUuidOrName,"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_e41db410","line":507,"in_reply_to":"9a89bdaa_2e207749","updated":"2016-09-05 08:47:26.000000000","message":"Done","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":22226,"name":"Varun Gadiraju","email":"varun.gadiraju@intel.com","username":"gadirajv"},"change_message_id":"fba9c75a64b755b17666cb1581b7c60d03b7f063","unresolved":false,"context_lines":[{"line_number":506,"context_line":""},{"line_number":507,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027)"},{"line_number":508,"context_line":"    def test_get_rpc_portgroup_invalid_name(self, mock_pr):"},{"line_number":509,"context_line":"        mock_pr.version.minor \u003d 10"},{"line_number":510,"context_line":"        self.assertRaises(exception.InvalidUuidOrName,"},{"line_number":511,"context_line":"                          utils.get_rpc_portgroup,"},{"line_number":512,"context_line":"                          self.invalid_name)"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_39c43f91","line":509,"updated":"2016-09-02 22:57:42.000000000","message":"pecan.request is never used so this line is not necessary.","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"88862cd728e8298786ed18041ea974f3e81573da","unresolved":false,"context_lines":[{"line_number":506,"context_line":""},{"line_number":507,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027)"},{"line_number":508,"context_line":"    def test_get_rpc_portgroup_invalid_name(self, mock_pr):"},{"line_number":509,"context_line":"        mock_pr.version.minor \u003d 10"},{"line_number":510,"context_line":"        self.assertRaises(exception.InvalidUuidOrName,"},{"line_number":511,"context_line":"                          utils.get_rpc_portgroup,"},{"line_number":512,"context_line":"                          self.invalid_name)"}],"source_content_type":"text/x-python","patch_set":32,"id":"9a89bdaa_c420b04c","line":509,"in_reply_to":"9a89bdaa_39c43f91","updated":"2016-09-05 08:47:26.000000000","message":"Done","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"3caa6c10d2f3d822f16af02e62f4f280c156d4c0","unresolved":false,"context_lines":[{"line_number":487,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027, spec_set\u003d[\"context\"])"},{"line_number":488,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_name\u0027)"},{"line_number":489,"context_line":"    def test_get_rpc_portgroup_name(self, mock_gbn, mock_pr):"},{"line_number":490,"context_line":"        mock_gbn.return_value \u003d self.portgroup"},{"line_number":491,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("},{"line_number":492,"context_line":"            self.valid_name))"},{"line_number":493,"context_line":"        self.assertEqual(1, mock_gbn.call_count)"}],"source_content_type":"text/x-python","patch_set":34,"id":"9a89bdaa_1993c85c","line":490,"updated":"2016-09-05 14:12:49.000000000","message":"I agree with Varun\u0027s comment in patch set 32. A copy.deepcopy() would be good.\n\nYes the portgroup object is not modified in the function, but I can modify the function so that the portgroup object is modified and this test will still pass. So in my mind the idea is that the test should not be giving the expected value to the function as then the function could be modifying it.","commit_id":"cc44ce1b2f1cb6372285340864fd0cbec157dbdc"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"00fe25d58e038adda32a20f73d109714127fe5f5","unresolved":false,"context_lines":[{"line_number":487,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027, spec_set\u003d[\"context\"])"},{"line_number":488,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_name\u0027)"},{"line_number":489,"context_line":"    def test_get_rpc_portgroup_name(self, mock_gbn, mock_pr):"},{"line_number":490,"context_line":"        mock_gbn.return_value \u003d self.portgroup"},{"line_number":491,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("},{"line_number":492,"context_line":"            self.valid_name))"},{"line_number":493,"context_line":"        self.assertEqual(1, mock_gbn.call_count)"}],"source_content_type":"text/x-python","patch_set":34,"id":"9a89bdaa_c549738d","line":490,"in_reply_to":"9a89bdaa_0ad9a8f3","updated":"2016-09-05 15:30:15.000000000","message":"Other tests here use the same logic. For example: https://github.com/openstack/ironic/blob/master/ironic/tests/unit/api/v1/test_utils.py#L363\nEven if we add deepcopy here, we will not detect object modification, since we do not compare objects, we checking only specific field.","commit_id":"cc44ce1b2f1cb6372285340864fd0cbec157dbdc"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"28631cec57982416777660d72919989e6ae42516","unresolved":false,"context_lines":[{"line_number":487,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027, spec_set\u003d[\"context\"])"},{"line_number":488,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_name\u0027)"},{"line_number":489,"context_line":"    def test_get_rpc_portgroup_name(self, mock_gbn, mock_pr):"},{"line_number":490,"context_line":"        mock_gbn.return_value \u003d self.portgroup"},{"line_number":491,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("},{"line_number":492,"context_line":"            self.valid_name))"},{"line_number":493,"context_line":"        self.assertEqual(1, mock_gbn.call_count)"}],"source_content_type":"text/x-python","patch_set":34,"id":"9a89bdaa_ece74410","line":490,"in_reply_to":"9a89bdaa_1993c85c","updated":"2016-09-05 14:25:11.000000000","message":"John, get_* function shouldn\u0027t modify object according to it\u0027s name and meaning. If you are going to update get_rpc_portgroup() to change portgroup, than it would be another function and you have to write a new tests for it.","commit_id":"cc44ce1b2f1cb6372285340864fd0cbec157dbdc"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"e1e2a9eb4c91a191809af26096449a11a5a113a6","unresolved":false,"context_lines":[{"line_number":487,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027, spec_set\u003d[\"context\"])"},{"line_number":488,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_name\u0027)"},{"line_number":489,"context_line":"    def test_get_rpc_portgroup_name(self, mock_gbn, mock_pr):"},{"line_number":490,"context_line":"        mock_gbn.return_value \u003d self.portgroup"},{"line_number":491,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("},{"line_number":492,"context_line":"            self.valid_name))"},{"line_number":493,"context_line":"        self.assertEqual(1, mock_gbn.call_count)"}],"source_content_type":"text/x-python","patch_set":34,"id":"9a89bdaa_0024290b","line":490,"in_reply_to":"9a89bdaa_c549738d","updated":"2016-09-05 15:45:03.000000000","message":"Other tests doing it, in my opinion, incorrectly is still wrong.\n\nI\u0027m not sure I understand comment on only checking specific field. Seems like checking the code compares the whole portgroup object are equal on L491\n\nIt might be enough to do:\n mock_gnb.return_value \u003d self.portgroup.copy()\n\nI\u0027m not -1 over this. I just think the unit test code is better using copy/deepcopy","commit_id":"cc44ce1b2f1cb6372285340864fd0cbec157dbdc"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"7b39c5e90688f73e38cf6916c5501df51e7c19f0","unresolved":false,"context_lines":[{"line_number":487,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027, spec_set\u003d[\"context\"])"},{"line_number":488,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_name\u0027)"},{"line_number":489,"context_line":"    def test_get_rpc_portgroup_name(self, mock_gbn, mock_pr):"},{"line_number":490,"context_line":"        mock_gbn.return_value \u003d self.portgroup"},{"line_number":491,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("},{"line_number":492,"context_line":"            self.valid_name))"},{"line_number":493,"context_line":"        self.assertEqual(1, mock_gbn.call_count)"}],"source_content_type":"text/x-python","patch_set":34,"id":"9a89bdaa_0ad9a8f3","line":490,"in_reply_to":"9a89bdaa_ece74410","updated":"2016-09-05 15:07:29.000000000","message":"Agreed, the function shouldn\u0027t modify the object. And the unit test here won\u0027t detect that it did modify the object :)\n\nBasically if there is an expected return value. That expected return value should not be able to be modified by the function under test. Since that enables the function to do whatever it wants to the expected value.","commit_id":"cc44ce1b2f1cb6372285340864fd0cbec157dbdc"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":485,"context_line":"        self.portgroup \u003d test_api_utils.post_get_test_portgroup()"},{"line_number":486,"context_line":""},{"line_number":487,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027, spec_set\u003d[\"context\"])"},{"line_number":488,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_name\u0027)"},{"line_number":489,"context_line":"    def test_get_rpc_portgroup_name(self, mock_gbn, mock_pr):"},{"line_number":490,"context_line":"        mock_gbn.return_value \u003d self.portgroup"},{"line_number":491,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_f1ef911b","line":488,"updated":"2016-11-02 17:31:53.000000000","message":"I thought we had changed all the mock.patch.objects to have \u0027autospec\u003dTrue\u0027 too but I guess we didn\u0027t do it for the api tests.","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"17964fc2f83c4db8293e1c88e8a54230cb31ada0","unresolved":false,"context_lines":[{"line_number":485,"context_line":"        self.portgroup \u003d test_api_utils.post_get_test_portgroup()"},{"line_number":486,"context_line":""},{"line_number":487,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027, spec_set\u003d[\"context\"])"},{"line_number":488,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_name\u0027)"},{"line_number":489,"context_line":"    def test_get_rpc_portgroup_name(self, mock_gbn, mock_pr):"},{"line_number":490,"context_line":"        mock_gbn.return_value \u003d self.portgroup"},{"line_number":491,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_a0ae7e2b","line":488,"in_reply_to":"ba5da102_7fb32e0a","updated":"2016-11-03 14:21:55.000000000","message":"Oh, that\u0027s interesting/good to know.","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":485,"context_line":"        self.portgroup \u003d test_api_utils.post_get_test_portgroup()"},{"line_number":486,"context_line":""},{"line_number":487,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027, spec_set\u003d[\"context\"])"},{"line_number":488,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_name\u0027)"},{"line_number":489,"context_line":"    def test_get_rpc_portgroup_name(self, mock_gbn, mock_pr):"},{"line_number":490,"context_line":"        mock_gbn.return_value \u003d self.portgroup"},{"line_number":491,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_7fb32e0a","line":488,"in_reply_to":"ba5da102_f1ef911b","updated":"2016-11-03 11:38:14.000000000","message":"adding autospec\u003dTrue to mock of any function from objects leads to: It seems we can\u0027t do autospec\u003dTrue for functions from objects that was inherit from oslo.versionedobjects.\n\nCaptured traceback:\n~~~~~~~~~~~~~~~~~~~\n    Traceback (most recent call last):\n      File \"/tmp/ironic/.tox/py27/local/lib/python2.7/site-packages/mock/mock.py\", line 1305, in patched\n        return func(*args, **keywargs)\n      File \"ironic/tests/unit/api/v1/test_utils.py\", line 501, in test_get_rpc_portgroup_uuid\n        self.valid_uuid))\n      File \"ironic/api/controllers/v1/utils.py\", line 158, in get_rpc_portgroup\n        portgroup_ident)\n    TypeError: \u0027NonCallableMagicMock\u0027 object is not callable","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":490,"context_line":"        mock_gbn.return_value \u003d self.portgroup"},{"line_number":491,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("},{"line_number":492,"context_line":"            self.valid_name))"},{"line_number":493,"context_line":"        self.assertEqual(1, mock_gbn.call_count)"},{"line_number":494,"context_line":""},{"line_number":495,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027, spec_set\u003d[\"context\"])"},{"line_number":496,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_uuid\u0027)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_b146f94c","line":493,"updated":"2016-11-02 17:31:53.000000000","message":"nit: wouldn\u0027t it be more interesting/exact to do something like mock_gbn.assert_called_once_with(.... self.valid_name) ?","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"a01d7b790b36a5a11357c978016e57caba3a6601","unresolved":false,"context_lines":[{"line_number":490,"context_line":"        mock_gbn.return_value \u003d self.portgroup"},{"line_number":491,"context_line":"        self.assertEqual(self.portgroup, utils.get_rpc_portgroup("},{"line_number":492,"context_line":"            self.valid_name))"},{"line_number":493,"context_line":"        self.assertEqual(1, mock_gbn.call_count)"},{"line_number":494,"context_line":""},{"line_number":495,"context_line":"    @mock.patch.object(pecan, \u0027request\u0027, spec_set\u003d[\"context\"])"},{"line_number":496,"context_line":"    @mock.patch.object(objects.Portgroup, \u0027get_by_uuid\u0027)"}],"source_content_type":"text/x-python","patch_set":36,"id":"ba5da102_ffbd7e02","line":493,"in_reply_to":"ba5da102_b146f94c","updated":"2016-11-03 11:38:14.000000000","message":"Done","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"}],"releasenotes/notes/add_portgroup_support-7d5c6663bb00684a.yaml":[{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"6b4af22e7ee24ad33aa9252e9b65a63960a2af29","unresolved":false,"context_lines":[{"line_number":4,"context_line":"    Added portgroup API support. API version was bumped to 1.23. The"},{"line_number":5,"context_line":"    new endpoint `/v1/portgroups/` was added."},{"line_number":6,"context_line":""},{"line_number":7,"context_line":"     Ironic can now combine ports into portgroups to support static"},{"line_number":8,"context_line":"     LAG and MLAG configurations."}],"source_content_type":"text/x-yaml","patch_set":31,"id":"fa7ab95a_afcc8c35","line":7,"range":{"start_line":7,"start_character":4,"end_line":7,"end_character":5},"updated":"2016-08-30 21:34:41.000000000","message":"extra space. Is this intentional. It does causes extra indentation.\n\nhttp://docs-draft.openstack.org/49/347549/31/check/gate-ironic-releasenotes/f302840//releasenotes/build/html/current-series.html","commit_id":"e8927d4b363f77cf08b248ed371d9ebdd500e8dd"},{"author":{"_account_id":14760,"name":"John L. Villalovos","email":"openstack.org@sodarock.com","username":"jlvillal"},"change_message_id":"a497cc7f12a8c7f3039506d96fb51b57efb0f340","unresolved":false,"context_lines":[{"line_number":5,"context_line":"    new endpoint `/v1/portgroups/` was added."},{"line_number":6,"context_line":""},{"line_number":7,"context_line":"    Ironic can now combine ports into portgroups to support static"},{"line_number":8,"context_line":"    LAG and MLAG configurations."}],"source_content_type":"text/x-yaml","patch_set":32,"id":"9a89bdaa_1372fce5","line":8,"updated":"2016-09-02 23:30:26.000000000","message":"LAG is?\n\nMLAG is?\n\nPlease define these terms","commit_id":"cac659177a70358fbe7a506c0fbb1c81bda33d98"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","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":"    Added portgroup API support. API version was bumped to 1.23. The"},{"line_number":5,"context_line":"    new endpoint `/v1/portgroups/` was added."},{"line_number":6,"context_line":""},{"line_number":7,"context_line":"    Ironic can now combine ports into portgroups to support static"}],"source_content_type":"text/x-yaml","patch_set":36,"id":"ba5da102_90401636","line":4,"updated":"2016-11-02 17:31:53.000000000","message":"nit s/Added/Adds/","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"84446bd092ce910c2493dc06b558746e9ffb0b34","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":"    Added portgroup API support. API version was bumped to 1.23. The"},{"line_number":5,"context_line":"    new endpoint `/v1/portgroups/` was added."},{"line_number":6,"context_line":""},{"line_number":7,"context_line":"    Ironic can now combine ports into portgroups to support static"}],"source_content_type":"text/x-yaml","patch_set":36,"id":"ba5da102_3ba45f06","line":4,"in_reply_to":"ba5da102_90401636","updated":"2016-11-03 14:28:02.000000000","message":"Done","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"1b4601d9a03bf999054446fb859f477de2bcbcfe","unresolved":false,"context_lines":[{"line_number":5,"context_line":"    new endpoint `/v1/portgroups/` was added."},{"line_number":6,"context_line":""},{"line_number":7,"context_line":"    Ironic can now combine ports into portgroups to support static"},{"line_number":8,"context_line":"    LAG and MLAG configurations."}],"source_content_type":"text/x-yaml","patch_set":36,"id":"ba5da102_1065e6b3","line":8,"updated":"2016-11-02 17:31:53.000000000","message":"How about\n\nAdds support for portgroups with a new endpoint `/v1/portgroups/` in the REST API version 1.23. Ports can be combined into portgroups to support static LAG and MLAG configurations.\n\nDo we need to spell out what LAG and MLAG are?","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":14525,"name":"Vasyl Saienko","email":"vsaienko@mirantis.com","username":"vsaienko"},"change_message_id":"84446bd092ce910c2493dc06b558746e9ffb0b34","unresolved":false,"context_lines":[{"line_number":5,"context_line":"    new endpoint `/v1/portgroups/` was added."},{"line_number":6,"context_line":""},{"line_number":7,"context_line":"    Ironic can now combine ports into portgroups to support static"},{"line_number":8,"context_line":"    LAG and MLAG configurations."}],"source_content_type":"text/x-yaml","patch_set":36,"id":"ba5da102_db6603ba","line":8,"in_reply_to":"ba5da102_1065e6b3","updated":"2016-11-03 14:28:02.000000000","message":"I don\u0027t think we should mention what is LAG and MLAG, the users who interested in this feature should know because it is well known abbreviation","commit_id":"31251a8658422a209c0e71be277d14f92a2ea98b"},{"author":{"_account_id":6618,"name":"Ruby Loo","email":"opensrloo@gmail.com","username":"rloo"},"change_message_id":"d6764690cf8c641ea8c3bf3ee6ae759cc83ff945","unresolved":false,"context_lines":[{"line_number":5,"context_line":"    new endpoint `/v1/portgroups/` was added."},{"line_number":6,"context_line":""},{"line_number":7,"context_line":"    Ironic can now combine ports into portgroups to support static"},{"line_number":8,"context_line":"    LAG and MLAG configurations."}],"source_content_type":"text/x-yaml","patch_set":37,"id":"ba5da102_80289a9b","line":8,"updated":"2016-11-03 14:21:46.000000000","message":"you didn\u0027t apply any of my suggestions here :-(","commit_id":"8ccad27718d5cab12900305d60600a43ab956534"}]}
