)]}'
{"/COMMIT_MSG":[{"author":{"_account_id":7040,"name":"GuoHui LIu","email":"liuguohui@gmail.com","username":"guohliu"},"change_message_id":"4601713ed70a6a6112edc5315f98042811380952","unresolved":false,"context_lines":[{"line_number":4,"context_line":"Commit:     Debo~ Dutta \u003cdedutta@cisco.com\u003e"},{"line_number":5,"context_line":"CommitDate: 2013-12-16 22:23:28 -0800"},{"line_number":6,"context_line":""},{"line_number":7,"context_line":"Add REST API for instance group api extension"},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"Support the Creation, Read, Update, Delete, and List of instance group"},{"line_number":10,"context_line":""}],"source_content_type":"text/x-gerrit-commit-message","patch_set":1,"id":"AAAATn%2F9D8Q%3D","line":7,"updated":"2013-12-17 07:24:10.000000000","message":"we\u0027d better to make it clear that this patch adds the api for v2","commit_id":"95913e6eb3b03b7577e70e302b0522f2736bb7f6"},{"author":{"_account_id":7040,"name":"GuoHui LIu","email":"liuguohui@gmail.com","username":"guohliu"},"change_message_id":"4601713ed70a6a6112edc5315f98042811380952","unresolved":false,"context_lines":[{"line_number":9,"context_line":"Support the Creation, Read, Update, Delete, and List of instance group"},{"line_number":10,"context_line":""},{"line_number":11,"context_line":"Refactored the code to use objects (https://review.openstack.org/#/c/38979/"},{"line_number":12,"context_line":"Implements: blueprint instance-group-api-extension"},{"line_number":13,"context_line":""},{"line_number":14,"context_line":"Conflicts:"},{"line_number":15,"context_line":"\tnova/tests/integrated/api_samples/all_extensions/extensions-get-resp.json.tpl"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":1,"id":"AAAATn%2F9D8o%3D","line":12,"updated":"2013-12-17 07:24:10.000000000","message":"I assume there would be other patch coming, eg v3? so we better use correct tag to indicate it, Partial implement","commit_id":"95913e6eb3b03b7577e70e302b0522f2736bb7f6"},{"author":{"_account_id":7040,"name":"GuoHui LIu","email":"liuguohui@gmail.com","username":"guohliu"},"change_message_id":"4601713ed70a6a6112edc5315f98042811380952","unresolved":false,"context_lines":[{"line_number":11,"context_line":"Refactored the code to use objects (https://review.openstack.org/#/c/38979/"},{"line_number":12,"context_line":"Implements: blueprint instance-group-api-extension"},{"line_number":13,"context_line":""},{"line_number":14,"context_line":"Conflicts:"},{"line_number":15,"context_line":"\tnova/tests/integrated/api_samples/all_extensions/extensions-get-resp.json.tpl"},{"line_number":16,"context_line":"\tnova/tests/integrated/api_samples/all_extensions/extensions-get-resp.xml.tpl"},{"line_number":17,"context_line":""}],"source_content_type":"text/x-gerrit-commit-message","patch_set":1,"id":"AAAATn%2F9D8k%3D","line":14,"updated":"2013-12-17 07:24:10.000000000","message":"DocImpact tag will be needed here.","commit_id":"95913e6eb3b03b7577e70e302b0522f2736bb7f6"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":9,"context_line":"Support the Creation, Read, Update, Delete, and List of server group."},{"line_number":10,"context_line":"Renamed from \"instance group\" to \"server group\"."},{"line_number":11,"context_line":""},{"line_number":12,"context_line":"Refactored the code to use objects (https://review.openstack.org/#/c/38979/"},{"line_number":13,"context_line":"Implements: blueprint instance-group-api-extension"},{"line_number":14,"context_line":""},{"line_number":15,"context_line":"Change-Id: I650a8f191dea5eab5b4b1828f0b9f65e33edea2a"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":22,"id":"AAAAVX%2F%2FoRM%3D","line":12,"updated":"2014-03-02 12:28:56.000000000","message":"Please add DocImpact flag","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"8616084d496c88d3daac3a142faa7c49b1da3f01","unresolved":false,"context_lines":[{"line_number":4,"context_line":"Commit:     Russell Bryant \u003crbryant@redhat.com\u003e"},{"line_number":5,"context_line":"CommitDate: 2014-03-06 21:05:24 +0000"},{"line_number":6,"context_line":""},{"line_number":7,"context_line":"Add REST API for instance group api extension"},{"line_number":8,"context_line":""},{"line_number":9,"context_line":"Support the Creation, Read, Delete, and List of server groups."},{"line_number":10,"context_line":""}],"source_content_type":"text/x-gerrit-commit-message","patch_set":35,"id":"AAAAVn%2F%2FThA%3D","line":7,"updated":"2014-03-06 23:57:32.000000000","message":"s/instance/server/","commit_id":"8a2aad4ee5b1f40837a5791d936f1945e269d6b1"}],"doc/api_samples/all_extensions/extensions-get-resp.json":[{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"3810dfcb688cc463eb9a824efcdf82de734e24c6","unresolved":false,"context_lines":[{"line_number":421,"context_line":"            \"description\": \"Instance group support.\","},{"line_number":422,"context_line":"            \"links\": [],"},{"line_number":423,"context_line":"            \"name\": \"InstanceGroups\","},{"line_number":424,"context_line":"            \"namespace\": \"http://docs.openstack.org/compute/ext/instancegroups/api/v2.0\","},{"line_number":425,"context_line":"            \"updated\": \"2013-06-01T00:00:00+00:00\""},{"line_number":426,"context_line":"        },"},{"line_number":427,"context_line":"        {"}],"source_content_type":"application/json","patch_set":6,"id":"AAAAUH%2F%2ByFQ%3D","line":424,"updated":"2014-01-22 07:34:39.000000000","message":"why is this not 1.1?","commit_id":"4dc01f4cf9bca2cc1529df93a9bf10a3affbf727"}],"doc/api_samples/all_extensions/extensions-get-resp.xml":[{"author":{"_account_id":7040,"name":"GuoHui LIu","email":"liuguohui@gmail.com","username":"guohliu"},"change_message_id":"4601713ed70a6a6112edc5315f98042811380952","unresolved":false,"context_lines":[{"line_number":1,"context_line":"\u003c?xml version \u003d \u00271.0\u0027 encoding \u003d \u0027UTF-8\u0027?\u003e"},{"line_number":2,"context_line":"\u003cextensions xmlns:atom \u003d \"http://www.w3.org/2005/Atom\" xmlns \u003d \"http://docs.openstack.org/common/api/v1.0\"\u003e"},{"line_number":3,"context_line":"  \u003cextension alias\u003d\"NMN\" updated\u003d\"2011-06-09T00:00:00+00:00\" namespace\u003d\"http://docs.openstack.org/compute/ext/multinic/api/v1.1\" name\u003d\"Multinic\"\u003e"},{"line_number":4,"context_line":"    \u003cdescription\u003eMultiple network support.\u003c/description\u003e"}],"source_content_type":"application/xml","patch_set":1,"id":"AAAATn%2F9D78%3D","line":1,"updated":"2013-12-17 07:24:10.000000000","message":"these are unnecessary change, then should not be made.","commit_id":"95913e6eb3b03b7577e70e302b0522f2736bb7f6"},{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"3810dfcb688cc463eb9a824efcdf82de734e24c6","unresolved":false,"context_lines":[{"line_number":1,"context_line":"\u003c?xml version \u003d \u00271.0\u0027 encoding \u003d \u0027UTF-8\u0027?\u003e"},{"line_number":2,"context_line":"\u003cextensions xmlns:atom \u003d \"http://www.w3.org/2005/Atom\" xmlns \u003d \"http://docs.openstack.org/common/api/v1.0\"\u003e"},{"line_number":3,"context_line":"  \u003cextension alias\u003d\"NMN\" updated\u003d\"2011-06-09T00:00:00+00:00\" namespace\u003d\"http://docs.openstack.org/compute/ext/multinic/api/v1.1\" name\u003d\"Multinic\"\u003e"},{"line_number":4,"context_line":"    \u003cdescription\u003eMultiple network support.\u003c/description\u003e"}],"source_content_type":"application/xml","patch_set":6,"id":"AAAAUH%2F%2ByFc%3D","line":1,"updated":"2014-01-22 07:34:39.000000000","message":"this does not look like it is related to the patch set","commit_id":"4dc01f4cf9bca2cc1529df93a9bf10a3affbf727"},{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"3810dfcb688cc463eb9a824efcdf82de734e24c6","unresolved":false,"context_lines":[{"line_number":176,"context_line":"  \u003cextension alias\u003d\"os-instance-actions\" updated\u003d\"2013-02-08T00:00:00+00:00\" namespace\u003d\"http://docs.openstack.org/compute/ext/instance-actions/api/v1.1\" name\u003d\"InstanceActions\"\u003e"},{"line_number":177,"context_line":"    \u003cdescription\u003eView a log of actions and events taken on an instance.\u003c/description\u003e"},{"line_number":178,"context_line":"  \u003c/extension\u003e"},{"line_number":179,"context_line":"  \u003cextension alias\u003d\"os-instance-groups\" updated\u003d\"2013-06-12T00:00:00+00:00\" namespace\u003d\"http://docs.openstack.org/compute/ext/instancegroups/api/v2.0\" name\u003d\"InstanceGroups\"\u003e"},{"line_number":180,"context_line":"    \u003cdescription\u003eInstance group support.\u003c/description\u003e"},{"line_number":181,"context_line":"  \u003c/extension\u003e"},{"line_number":182,"context_line":"  \u003cextension alias\u003d\"os-instance_usage_audit_log\" updated\u003d\"2012-07-06T01:00:00+00:00\" namespace\u003d\"http://docs.openstack.org/ext/services/api/v1.1\" name\u003d\"OSInstanceUsageAuditLog\"\u003e"}],"source_content_type":"application/xml","patch_set":6,"id":"AAAAUH%2F%2ByFU%3D","line":179,"updated":"2014-01-22 07:34:39.000000000","message":"why is this not 1.1?","commit_id":"4dc01f4cf9bca2cc1529df93a9bf10a3affbf727"}],"doc/api_samples/os-instance-groups/instance-group-add-members-post-req.json":[{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"1cb635d3544a3fb151f7f669bbbc3b14bbbfe86d","unresolved":false,"context_lines":[{"line_number":1,"context_line":"{"},{"line_number":2,"context_line":"  \"add_members\":"},{"line_number":3,"context_line":"    {"},{"line_number":4,"context_line":"        \"members\":"},{"line_number":5,"context_line":"        [\"b8713410-9ba3-e913-901b-13410ca90121\"]"}],"source_content_type":"application/json","patch_set":13,"id":"AAAAUX%2F%2FHrY%3D","line":2,"updated":"2014-02-17 00:27:21.000000000","message":"The indent seems malformed.\n4 spaces are necessary before \"add_members\" and \"{\" should be put just after \"add_members\" like\n\n    \"add_members\": {","commit_id":"90e0e5aa9f586902734efa8ebf0a3f244dbc1997"},{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"1cb635d3544a3fb151f7f669bbbc3b14bbbfe86d","unresolved":false,"context_lines":[{"line_number":2,"context_line":"  \"add_members\":"},{"line_number":3,"context_line":"    {"},{"line_number":4,"context_line":"        \"members\":"},{"line_number":5,"context_line":"        [\"b8713410-9ba3-e913-901b-13410ca90121\"]"},{"line_number":6,"context_line":"    }"},{"line_number":7,"context_line":"}"}],"source_content_type":"application/json","patch_set":13,"id":"AAAAUX%2F%2FHrQ%3D","line":5,"updated":"2014-02-17 00:27:21.000000000","message":"A new line seems unnecessary, just put a list after \"member\":\n\n \"members\": [\"b8713410-9ba3-e913-901b-13410ca90121\"]","commit_id":"90e0e5aa9f586902734efa8ebf0a3f244dbc1997"}],"doc/api_samples/os-instance-groups/instance-group-add-policies-post-req.json":[{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"1cb635d3544a3fb151f7f669bbbc3b14bbbfe86d","unresolved":false,"context_lines":[{"line_number":1,"context_line":"{"},{"line_number":2,"context_line":"  \"add_policies\":"},{"line_number":3,"context_line":"    {"},{"line_number":4,"context_line":"        \"policies\":"},{"line_number":5,"context_line":"        [ \"different-rack\"]"},{"line_number":6,"context_line":"    }"}],"source_content_type":"application/json","patch_set":13,"id":"AAAAUX%2F%2FHrM%3D","line":3,"updated":"2014-02-17 00:27:21.000000000","message":"ditto","commit_id":"90e0e5aa9f586902734efa8ebf0a3f244dbc1997"},{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"1cb635d3544a3fb151f7f669bbbc3b14bbbfe86d","unresolved":false,"context_lines":[{"line_number":2,"context_line":"  \"add_policies\":"},{"line_number":3,"context_line":"    {"},{"line_number":4,"context_line":"        \"policies\":"},{"line_number":5,"context_line":"        [ \"different-rack\"]"},{"line_number":6,"context_line":"    }"},{"line_number":7,"context_line":"}"}],"source_content_type":"application/json","patch_set":13,"id":"AAAAUX%2F%2FHrE%3D","line":5,"updated":"2014-02-17 00:27:21.000000000","message":"ditto","commit_id":"90e0e5aa9f586902734efa8ebf0a3f244dbc1997"}],"doc/api_samples/os-instance-groups/instance-group-metadata-remove-req.json":[{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"3810dfcb688cc463eb9a824efcdf82de734e24c6","unresolved":false,"context_lines":[{"line_number":4,"context_line":"            \"metadata\":"},{"line_number":5,"context_line":"                {"},{"line_number":6,"context_line":"                    \"key1\": \"value1\","},{"line_number":7,"context_line":"                    \"key\": null"},{"line_number":8,"context_line":"               }"},{"line_number":9,"context_line":"        }"},{"line_number":10,"context_line":"}"}],"source_content_type":"application/json","patch_set":6,"id":"AAAAUH%2F%2ByDI%3D","line":7,"updated":"2014-01-22 07:34:39.000000000","message":"not sure, but maybe this should be None. Not sure though","commit_id":"4dc01f4cf9bca2cc1529df93a9bf10a3affbf727"},{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"1cb635d3544a3fb151f7f669bbbc3b14bbbfe86d","unresolved":false,"context_lines":[{"line_number":1,"context_line":"{"},{"line_number":2,"context_line":"    \"set_metadata\":"},{"line_number":3,"context_line":"        {"},{"line_number":4,"context_line":"            \"metadata\":"},{"line_number":5,"context_line":"                {"},{"line_number":6,"context_line":"                    \"key1\": \"value1\","}],"source_content_type":"application/json","patch_set":13,"id":"AAAAUX%2F%2FHq8%3D","line":3,"updated":"2014-02-17 00:27:21.000000000","message":"better to put \"{\" just after \"set_metadata\":\n\n \"set_metadata\": {","commit_id":"90e0e5aa9f586902734efa8ebf0a3f244dbc1997"},{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"1cb635d3544a3fb151f7f669bbbc3b14bbbfe86d","unresolved":false,"context_lines":[{"line_number":2,"context_line":"    \"set_metadata\":"},{"line_number":3,"context_line":"        {"},{"line_number":4,"context_line":"            \"metadata\":"},{"line_number":5,"context_line":"                {"},{"line_number":6,"context_line":"                    \"key1\": \"value1\","},{"line_number":7,"context_line":"                    \"key\": null"},{"line_number":8,"context_line":"               }"}],"source_content_type":"application/json","patch_set":13,"id":"AAAAUX%2F%2FHq4%3D","line":5,"updated":"2014-02-17 00:27:21.000000000","message":"ditto: and the indent is too many.","commit_id":"90e0e5aa9f586902734efa8ebf0a3f244dbc1997"}],"doc/api_samples/os-instance-groups/instance-group-remove-members-post-req.json":[{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"1cb635d3544a3fb151f7f669bbbc3b14bbbfe86d","unresolved":false,"context_lines":[{"line_number":1,"context_line":"{"},{"line_number":2,"context_line":"  \"remove_members\":"},{"line_number":3,"context_line":"    {"},{"line_number":4,"context_line":"        \"members\":"},{"line_number":5,"context_line":"        [\"a00456d5-6f1b-44e6-8467-af28f0f6cd4f\"]"},{"line_number":6,"context_line":"    }"}],"source_content_type":"application/json","patch_set":13,"id":"AAAAUX%2F%2FHqw%3D","line":3,"updated":"2014-02-17 00:27:21.000000000","message":"ditto","commit_id":"90e0e5aa9f586902734efa8ebf0a3f244dbc1997"},{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"1cb635d3544a3fb151f7f669bbbc3b14bbbfe86d","unresolved":false,"context_lines":[{"line_number":2,"context_line":"  \"remove_members\":"},{"line_number":3,"context_line":"    {"},{"line_number":4,"context_line":"        \"members\":"},{"line_number":5,"context_line":"        [\"a00456d5-6f1b-44e6-8467-af28f0f6cd4f\"]"},{"line_number":6,"context_line":"    }"},{"line_number":7,"context_line":"}"}],"source_content_type":"application/json","patch_set":13,"id":"AAAAUX%2F%2FHqo%3D","line":5,"updated":"2014-02-17 00:27:21.000000000","message":"ditto","commit_id":"90e0e5aa9f586902734efa8ebf0a3f244dbc1997"}],"doc/api_samples/os-instance-groups/instance-group-remove-policies-post-req.json":[{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"1cb635d3544a3fb151f7f669bbbc3b14bbbfe86d","unresolved":false,"context_lines":[{"line_number":1,"context_line":"{"},{"line_number":2,"context_line":"  \"add_policies\":"},{"line_number":3,"context_line":"    {"},{"line_number":4,"context_line":"        \"policies\":"},{"line_number":5,"context_line":"        [\"anti-affinity\"]"},{"line_number":6,"context_line":"    }"}],"source_content_type":"application/json","patch_set":13,"id":"AAAAUX%2F%2FHqg%3D","line":3,"updated":"2014-02-17 00:27:21.000000000","message":"ditto","commit_id":"90e0e5aa9f586902734efa8ebf0a3f244dbc1997"},{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"1cb635d3544a3fb151f7f669bbbc3b14bbbfe86d","unresolved":false,"context_lines":[{"line_number":2,"context_line":"  \"add_policies\":"},{"line_number":3,"context_line":"    {"},{"line_number":4,"context_line":"        \"policies\":"},{"line_number":5,"context_line":"        [\"anti-affinity\"]"},{"line_number":6,"context_line":"    }"},{"line_number":7,"context_line":"}"}],"source_content_type":"application/json","patch_set":13,"id":"AAAAUX%2F%2FHqc%3D","line":5,"updated":"2014-02-17 00:27:21.000000000","message":"ditto","commit_id":"90e0e5aa9f586902734efa8ebf0a3f244dbc1997"}],"doc/api_samples/os-instance-groups/instance-groups-post-resp.json":[{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"1cb635d3544a3fb151f7f669bbbc3b14bbbfe86d","unresolved":false,"context_lines":[{"line_number":1,"context_line":"{   \"instance_group\": {"},{"line_number":2,"context_line":"        \"id\": \"5bbcc3c4-1da2-4437-a48a-66f15b1b13f9\","},{"line_number":3,"context_line":"        \"name\": \"test\","},{"line_number":4,"context_line":"        \"policies\": [\"anti-affinity\"],"}],"source_content_type":"application/json","patch_set":13,"id":"AAAAUX%2F%2FHqQ%3D","line":1,"updated":"2014-02-17 00:27:21.000000000","message":"A new line is necessary after the first \"{\".","commit_id":"90e0e5aa9f586902734efa8ebf0a3f244dbc1997"}],"doc/api_samples/os-instance-groups/instance-groups-update-req.xml":[{"author":{"_account_id":7040,"name":"GuoHui LIu","email":"liuguohui@gmail.com","username":"guohliu"},"change_message_id":"4601713ed70a6a6112edc5315f98042811380952","unresolved":false,"context_lines":[{"line_number":1,"context_line":"  \u003cinstance_group name\u003d\"new_name\"\u003e"},{"line_number":2,"context_line":"  \u003c/instance_group\u003e"}],"source_content_type":"application/xml","patch_set":1,"id":"AAAATn%2F9D5c%3D","line":1,"updated":"2013-12-17 07:24:10.000000000","message":"I think we need id here.","commit_id":"95913e6eb3b03b7577e70e302b0522f2736bb7f6"}],"doc/api_samples/os-server-groups/server-group-add-policies-post-req.json":[{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"b15ba83f96f9da1bca55f21856d1b10e045bf343","unresolved":false,"context_lines":[{"line_number":1,"context_line":"{"},{"line_number":2,"context_line":"    \"add_policies\": {"},{"line_number":3,"context_line":"        \"policies\": [ \"different-rack\"]"},{"line_number":4,"context_line":"    }"},{"line_number":5,"context_line":"}"}],"source_content_type":"application/json","patch_set":18,"id":"AAAAU3%2F%2Fdg4%3D","line":3,"updated":"2014-02-26 13:59:53.000000000","message":"[ \"different-rack\"] \u003d\u003e [\"different-rack\"]","commit_id":"9fb67661d60488717d66fd3a5655b9455e25bddf"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"facdc0fdd3bab851ca33ae07dec751aff7b6eedf","unresolved":false,"context_lines":[{"line_number":1,"context_line":"{"},{"line_number":2,"context_line":"    \"add_policies\": {"},{"line_number":3,"context_line":"        \"policies\": [\"different-rack\"]"},{"line_number":4,"context_line":"    }"},{"line_number":5,"context_line":"}"}],"source_content_type":"application/json","patch_set":29,"id":"AAAAVn%2F%2FkCE%3D","line":3,"updated":"2014-03-05 13:45:41.000000000","message":"Since this policy isn\u0027t implemented, I think it should be removed from the samples","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"}],"etc/nova/policy.json":[{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"facdc0fdd3bab851ca33ae07dec751aff7b6eedf","unresolved":false,"context_lines":[{"line_number":212,"context_line":"    \"compute_extension:v3:os-server-diagnostics\": \"rule:admin_api\","},{"line_number":213,"context_line":"    \"compute_extension:v3:os-server-diagnostics:discoverable\": \"\","},{"line_number":214,"context_line":"    \"compute_extension:server_groups\": \"\","},{"line_number":215,"context_line":"    \"compute_extension:server_groups:all_projects_search\": \"is_admin:True\","},{"line_number":216,"context_line":"    \"compute_extension:server_password\": \"\","},{"line_number":217,"context_line":"    \"compute_extension:v3:os-server-password\": \"\","},{"line_number":218,"context_line":"    \"compute_extension:v3:os-server-password:discoverable\": \"\","}],"source_content_type":"application/json","patch_set":29,"id":"AAAAVn%2F%2FjtU%3D","line":215,"updated":"2014-03-05 13:45:41.000000000","message":"This policy doesn\u0027t exist for any other API extensions.\n\nChris, what would be the most consistent thing to do here?","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"}],"nova/api/openstack/compute/contrib/instance_groups.py":[{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"3810dfcb688cc463eb9a824efcdf82de734e24c6","unresolved":false,"context_lines":[{"line_number":1,"context_line":"# vim: tabstop\u003d4 shiftwidth\u003d4 softtabstop\u003d4"},{"line_number":2,"context_line":""},{"line_number":3,"context_line":"#    Licensed under the Apache License, Version 2.0 (the \"License\"); you may"},{"line_number":4,"context_line":"#    not use this file except in compliance with the License. You may obtain"}],"source_content_type":"text/x-python","patch_set":6,"id":"AAAAUH%2F%2ByEY%3D","line":1,"updated":"2014-01-22 07:34:39.000000000","message":"this is not needed any more you can remove lines 1 and 2","commit_id":"4dc01f4cf9bca2cc1529df93a9bf10a3affbf727"},{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"3810dfcb688cc463eb9a824efcdf82de734e24c6","unresolved":false,"context_lines":[{"line_number":16,"context_line":""},{"line_number":17,"context_line":"import re"},{"line_number":18,"context_line":"import uuid"},{"line_number":19,"context_line":"import webob"},{"line_number":20,"context_line":"from webob import exc"},{"line_number":21,"context_line":""},{"line_number":22,"context_line":"from nova.api.openstack import common"}],"source_content_type":"text/x-python","patch_set":6,"id":"AAAAUH%2F%2ByC0%3D","line":19,"updated":"2014-01-22 07:34:39.000000000","message":"webob is a third part import. it should be in its own section here","commit_id":"4dc01f4cf9bca2cc1529df93a9bf10a3affbf727"},{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"3810dfcb688cc463eb9a824efcdf82de734e24c6","unresolved":false,"context_lines":[{"line_number":146,"context_line":"            # [{\u0027name\u0027: \u0027policy1\u0027}, {\u0027name\u0027: \u0027policy2\u0027}, ...]"},{"line_number":147,"context_line":"            if policy_nodes is not None:"},{"line_number":148,"context_line":"                for node in policy_nodes:"},{"line_number":149,"context_line":"                    policyDict \u003d dict({\u0027name\u0027: node.getAttribute(\u0027name\u0027)})"},{"line_number":150,"context_line":"                    policies.append(policyDict)"},{"line_number":151,"context_line":"            return policies"},{"line_number":152,"context_line":""}],"source_content_type":"text/x-python","patch_set":6,"id":"AAAAUH%2F%2ByCM%3D","line":149,"updated":"2014-01-22 07:34:39.000000000","message":"consider using {} instead of dict here (http://doughellmann.com/2012/11/the-performance-impact-of-using-dict-instead-of-in-cpython-2-7-2.html)","commit_id":"4dc01f4cf9bca2cc1529df93a9bf10a3affbf727"},{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"3810dfcb688cc463eb9a824efcdf82de734e24c6","unresolved":false,"context_lines":[{"line_number":162,"context_line":"            # [{\u0027instance_id\u0027: \u0027member1\u0027}, {\u0027instance_id\u0027: \u0027member2\u0027}, ...]"},{"line_number":163,"context_line":"            if member_nodes is not None:"},{"line_number":164,"context_line":"                for node in member_nodes:"},{"line_number":165,"context_line":"                    memberDict \u003d dict({\u0027instance_id\u0027:"},{"line_number":166,"context_line":"                                      node.getAttribute(\u0027instance_id\u0027)})"},{"line_number":167,"context_line":"                    members.append(memberDict)"},{"line_number":168,"context_line":"            return members"}],"source_content_type":"text/x-python","patch_set":6,"id":"AAAAUH%2F%2ByCI%3D","line":165,"updated":"2014-01-22 07:34:39.000000000","message":"ditto","commit_id":"4dc01f4cf9bca2cc1529df93a9bf10a3affbf727"},{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"b0a27b3b8e9f0a5bb0a867e40a52a8ac75bf2e14","unresolved":false,"context_lines":[{"line_number":244,"context_line":"        instance_group[\u0027name\u0027] \u003d group[\u0027name\u0027]"},{"line_number":245,"context_line":"        return instance_group"},{"line_number":246,"context_line":""},{"line_number":247,"context_line":"    def _from_body(self, body, key):"},{"line_number":248,"context_line":"        if not body:"},{"line_number":249,"context_line":"            raise exc.HTTPBadRequest()"},{"line_number":250,"context_line":"        value \u003d body.get(key, None)"}],"source_content_type":"text/x-python","patch_set":12,"id":"AAAAUX%2F%2FliQ%3D","line":247,"updated":"2014-02-12 07:26:19.000000000","message":"self.is_valid_body() can be used instead of _from_body().","commit_id":"ae4597a2053324c2262c3bbc0ea817d418a24e54"},{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"b0a27b3b8e9f0a5bb0a867e40a52a8ac75bf2e14","unresolved":false,"context_lines":[{"line_number":324,"context_line":"        in_policies \u003d vals.pop(\u0027policies\u0027, None)"},{"line_number":325,"context_line":"        if in_policies is not None:"},{"line_number":326,"context_line":"            for policy in in_policies:"},{"line_number":327,"context_line":"                policies.append(policy[\u0027name\u0027])"},{"line_number":328,"context_line":""},{"line_number":329,"context_line":"        members \u003d []"},{"line_number":330,"context_line":"        in_members \u003d vals.pop(\u0027members\u0027, None)"}],"source_content_type":"text/x-python","patch_set":12,"id":"AAAAUX%2F%2FlWE%3D","line":327,"updated":"2014-02-12 07:26:19.000000000","message":"Will you add the other attribute to \u0027policies\u0027 parameter in the future?\nor is the attribute \u0027name\u0027 only enough?\n\nCurrent code does not validate whether \u0027policies\u0027 parameter contains \u0027name\u0027 attribute or not. and if passing the attribute, an internal error happens at line372. so if removing the attribute and just defining list of policy name in \u0027policies\u0027 parameter, we would avoid the internal error.","commit_id":"ae4597a2053324c2262c3bbc0ea817d418a24e54"},{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"b0a27b3b8e9f0a5bb0a867e40a52a8ac75bf2e14","unresolved":false,"context_lines":[{"line_number":330,"context_line":"        in_members \u003d vals.pop(\u0027members\u0027, None)"},{"line_number":331,"context_line":"        if in_members is not None:"},{"line_number":332,"context_line":"            for member in in_members:"},{"line_number":333,"context_line":"                members.append(member[\u0027instance_id\u0027])"},{"line_number":334,"context_line":""},{"line_number":335,"context_line":"        metadata \u003d vals.pop(\u0027metadata\u0027, {})"},{"line_number":336,"context_line":"        vals[\u0027project_id\u0027] \u003d context.project_id"}],"source_content_type":"text/x-python","patch_set":12,"id":"AAAAUX%2F%2FlVg%3D","line":333,"updated":"2014-02-12 07:26:19.000000000","message":"ditto: the same internal error would happen if passing without \u0027instance_id\u0027 attribute.","commit_id":"ae4597a2053324c2262c3bbc0ea817d418a24e54"},{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"b0a27b3b8e9f0a5bb0a867e40a52a8ac75bf2e14","unresolved":false,"context_lines":[{"line_number":365,"context_line":"        # called \"id\", which will cause error if passed to update()."},{"line_number":366,"context_line":"        # Also note the difference of the param list from create()."},{"line_number":367,"context_line":"        vals \u003d {}"},{"line_number":368,"context_line":"        vals[\u0027name\u0027] \u003d instance_group_data.get(\u0027name\u0027)"},{"line_number":369,"context_line":"        vals[\u0027project_id\u0027] \u003d context.project_id"},{"line_number":370,"context_line":"        vals[\u0027user_id\u0027] \u003d context.user_id"},{"line_number":371,"context_line":"        ig \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, id)"}],"source_content_type":"text/x-python","patch_set":12,"id":"AAAAUX%2F%2Fll4%3D","line":368,"updated":"2014-02-12 07:26:19.000000000","message":"Why don\u0027t you validate the updated name with _validate_name()?","commit_id":"ae4597a2053324c2262c3bbc0ea817d418a24e54"},{"author":{"_account_id":782,"name":"John Garbutt","email":"john@johngarbutt.com","username":"johngarbutt"},"change_message_id":"246e00eecf6b0da723e64b4564b393c581ed22c1","unresolved":false,"context_lines":[{"line_number":30,"context_line":""},{"line_number":31,"context_line":"LOG \u003d logging.getLogger(__name__)"},{"line_number":32,"context_line":""},{"line_number":33,"context_line":"authorize \u003d extensions.extension_authorizer(\u0027compute\u0027, \u0027instance_groups\u0027)"},{"line_number":34,"context_line":""},{"line_number":35,"context_line":"# TODO(debo) We need to add extension to nova\u0027s server API so that tenants"},{"line_number":36,"context_line":"# could addInstanceGroup/removeInstanceGroup to/from a server."}],"source_content_type":"text/x-python","patch_set":15,"id":"AAAAU3%2F%2F1Ro%3D","line":33,"updated":"2014-02-24 15:43:57.000000000","message":"This should be called server_groups","commit_id":"591fc6fda1604f1b82aa876640575b7a81720e71"},{"author":{"_account_id":782,"name":"John Garbutt","email":"john@johngarbutt.com","username":"johngarbutt"},"change_message_id":"246e00eecf6b0da723e64b4564b393c581ed22c1","unresolved":false,"context_lines":[{"line_number":32,"context_line":""},{"line_number":33,"context_line":"authorize \u003d extensions.extension_authorizer(\u0027compute\u0027, \u0027instance_groups\u0027)"},{"line_number":34,"context_line":""},{"line_number":35,"context_line":"# TODO(debo) We need to add extension to nova\u0027s server API so that tenants"},{"line_number":36,"context_line":"# could addInstanceGroup/removeInstanceGroup to/from a server."},{"line_number":37,"context_line":""},{"line_number":38,"context_line":"# TODO(debo) Need to get a bunch of error checks done at the API layer. Right"}],"source_content_type":"text/x-python","patch_set":15,"id":"AAAAU3%2F%2F1R8%3D","line":35,"updated":"2014-02-24 15:43:57.000000000","message":"do you have code for this already up?","commit_id":"591fc6fda1604f1b82aa876640575b7a81720e71"},{"author":{"_account_id":782,"name":"John Garbutt","email":"john@johngarbutt.com","username":"johngarbutt"},"change_message_id":"246e00eecf6b0da723e64b4564b393c581ed22c1","unresolved":false,"context_lines":[{"line_number":35,"context_line":"# TODO(debo) We need to add extension to nova\u0027s server API so that tenants"},{"line_number":36,"context_line":"# could addInstanceGroup/removeInstanceGroup to/from a server."},{"line_number":37,"context_line":""},{"line_number":38,"context_line":"# TODO(debo) Need to get a bunch of error checks done at the API layer. Right"},{"line_number":39,"context_line":"# now they are all done at the db layer. For example, we need to check if"},{"line_number":40,"context_line":"# the correct authorizaton is present (e.g. admin) when calling the controller."},{"line_number":41,"context_line":""}],"source_content_type":"text/x-python","patch_set":15,"id":"AAAAU3%2F%2F1S0%3D","line":38,"updated":"2014-02-24 15:43:57.000000000","message":"It looks like the policy checks are mostly in place, what is missing?","commit_id":"591fc6fda1604f1b82aa876640575b7a81720e71"}],"nova/api/openstack/compute/contrib/server_groups.py":[{"author":{"_account_id":5511,"name":"Nikola Dipanov","email":"ndipanov@redhat.com","username":"ndipanov"},"change_message_id":"5ee796875ae3d2aa505d3aa322f892ed24f09339","unresolved":false,"context_lines":[{"line_number":293,"context_line":"        \"\"\"Returns a list of server groups.\"\"\""},{"line_number":294,"context_line":"        context \u003d _authorize_context(req)"},{"line_number":295,"context_line":"        project_id \u003d context.project_id"},{"line_number":296,"context_line":"        if \u0027all_projects_search\u0027 in req.GET and \\"},{"line_number":297,"context_line":"                    authorize_all_projects_search(context):"},{"line_number":298,"context_line":"            sgs \u003d server_group_obj.InstanceGroupList.get_all(context)"},{"line_number":299,"context_line":"        else:"}],"source_content_type":"text/x-python","patch_set":18,"id":"AAAAU3%2F%2Fbdg%3D","line":296,"updated":"2014-02-26 18:23:59.000000000","message":"We should really use () over / but not a huge deal, however can we add this to one of the tests - it\u0027s not excercised as is.","commit_id":"9fb67661d60488717d66fd3a5655b9455e25bddf"},{"author":{"_account_id":5511,"name":"Nikola Dipanov","email":"ndipanov@redhat.com","username":"ndipanov"},"change_message_id":"5ee796875ae3d2aa505d3aa322f892ed24f09339","unresolved":false,"context_lines":[{"line_number":355,"context_line":""},{"line_number":356,"context_line":"    @wsgi.serializers(xml\u003dServerGroupTemplate)"},{"line_number":357,"context_line":"    @wsgi.deserializers(xml\u003dServerGroupXMLDeserializer)"},{"line_number":358,"context_line":"    def update(self, req, id, body):"},{"line_number":359,"context_line":"        \"\"\"Update an server group\u0027s name, project_id, and user_id.\"\"\""},{"line_number":360,"context_line":"        context \u003d _authorize_context(req)"},{"line_number":361,"context_line":""}],"source_content_type":"text/x-python","patch_set":18,"id":"AAAAU3%2F%2FbME%3D","line":358,"updated":"2014-02-26 18:23:59.000000000","message":"can we do something like\n  \n  sg_uuid \u003d id\n\nand then use sg_uuid in the rest of the method. This is just asking for trouble :)\n\nThis applies to some below as well/","commit_id":"9fb67661d60488717d66fd3a5655b9455e25bddf"},{"author":{"_account_id":5511,"name":"Nikola Dipanov","email":"ndipanov@redhat.com","username":"ndipanov"},"change_message_id":"5ee796875ae3d2aa505d3aa322f892ed24f09339","unresolved":false,"context_lines":[{"line_number":426,"context_line":""},{"line_number":427,"context_line":"        try:"},{"line_number":428,"context_line":"            for policy in policies:"},{"line_number":429,"context_line":"                sg \u003d server_group_obj.InstanceGroup.get_by_uuid("},{"line_number":430,"context_line":"                                                context, id)"},{"line_number":431,"context_line":"                p \u003d sg.policies"},{"line_number":432,"context_line":"                if p:"}],"source_content_type":"text/x-python","patch_set":18,"id":"AAAAU3%2F%2FbFc%3D","line":429,"updated":"2014-02-26 18:23:59.000000000","message":"See below... similar question","commit_id":"9fb67661d60488717d66fd3a5655b9455e25bddf"},{"author":{"_account_id":5511,"name":"Nikola Dipanov","email":"ndipanov@redhat.com","username":"ndipanov"},"change_message_id":"5ee796875ae3d2aa505d3aa322f892ed24f09339","unresolved":false,"context_lines":[{"line_number":456,"context_line":"        in_members \u003d body[\u0027add_members\u0027][\u0027members\u0027]"},{"line_number":457,"context_line":"        members \u003d []"},{"line_number":458,"context_line":"        if in_members is not None:"},{"line_number":459,"context_line":"            members \u003d in_members"},{"line_number":460,"context_line":""},{"line_number":461,"context_line":"        try:"},{"line_number":462,"context_line":"            sg \u003d server_group_obj.InstanceGroup.get_by_uuid(context, id)"}],"source_content_type":"text/x-python","patch_set":18,"id":"AAAAU3%2F%2FbLA%3D","line":459,"updated":"2014-02-26 18:23:59.000000000","message":"Could be nicer as \n  \n  members \u003d in_members or []\n\nbut meh...","commit_id":"9fb67661d60488717d66fd3a5655b9455e25bddf"},{"author":{"_account_id":5511,"name":"Nikola Dipanov","email":"ndipanov@redhat.com","username":"ndipanov"},"change_message_id":"5ee796875ae3d2aa505d3aa322f892ed24f09339","unresolved":false,"context_lines":[{"line_number":471,"context_line":"    @wsgi.serializers(xml\u003dServerGroupTemplate)"},{"line_number":472,"context_line":"    @wsgi.deserializers(xml\u003dServerGroupActionXMLDeserializer)"},{"line_number":473,"context_line":"    @wsgi.action(\"remove_members\")"},{"line_number":474,"context_line":"    def _remove_members(self, req, id, body):"},{"line_number":475,"context_line":"        \"\"\"Remove members from the specified server group.\"\"\""},{"line_number":476,"context_line":"        context \u003d _authorize_context(req)"},{"line_number":477,"context_line":"        if not self._is_valid_body(body.get(\u0027remove_members\u0027, None),"}],"source_content_type":"text/x-python","patch_set":18,"id":"AAAAU3%2F%2FbKE%3D","line":474,"updated":"2014-02-26 18:23:59.000000000","message":"Same thing about the id vs sg_uuid","commit_id":"9fb67661d60488717d66fd3a5655b9455e25bddf"},{"author":{"_account_id":5511,"name":"Nikola Dipanov","email":"ndipanov@redhat.com","username":"ndipanov"},"change_message_id":"5ee796875ae3d2aa505d3aa322f892ed24f09339","unresolved":false,"context_lines":[{"line_number":483,"context_line":"            members \u003d in_members"},{"line_number":484,"context_line":"        try:"},{"line_number":485,"context_line":"            for member in members:"},{"line_number":486,"context_line":"                sg \u003d server_group_obj.InstanceGroup.get_by_uuid(context, id)"},{"line_number":487,"context_line":"                m \u003d sg.members"},{"line_number":488,"context_line":"                if m:"},{"line_number":489,"context_line":"                    try:"}],"source_content_type":"text/x-python","patch_set":18,"id":"AAAAU3%2F%2FbHA%3D","line":486,"updated":"2014-02-26 18:23:59.000000000","message":"Why do we have to get the *same* instance group for every member?\n\nI would do:\n\n  members_rm \u003d in_members or []\n  sg \u003d server_group_obj.InstanceGroup.get_by_uuid(context, id)\n\n  if any(member for member in members_rm if member not in sg.members):\n    raise InstanceGroupMemberNotFound(...)\n  sg.members \u003d [member for member in sg.members if member not in memebrs_rm]\n  sg.save()\n\nCleaner no?","commit_id":"9fb67661d60488717d66fd3a5655b9455e25bddf"},{"author":{"_account_id":5511,"name":"Nikola Dipanov","email":"ndipanov@redhat.com","username":"ndipanov"},"change_message_id":"5ee796875ae3d2aa505d3aa322f892ed24f09339","unresolved":false,"context_lines":[{"line_number":516,"context_line":"            for key in in_metadata:"},{"line_number":517,"context_line":"                # None is used to indicate the removal of a key"},{"line_number":518,"context_line":"                if in_metadata[key] is None or in_metadata[key] \u003d\u003d \u0027\u0027:"},{"line_number":519,"context_line":"                    sg \u003d server_group_obj.InstanceGroup.get_by_uuid("},{"line_number":520,"context_line":"                            context, id)"},{"line_number":521,"context_line":"                    if key:"},{"line_number":522,"context_line":"                        md \u003d sg.metadetails"}],"source_content_type":"text/x-python","patch_set":18,"id":"AAAAU3%2F%2FbGY%3D","line":519,"updated":"2014-02-26 18:23:59.000000000","message":"Similar question like the above... you get the idea","commit_id":"9fb67661d60488717d66fd3a5655b9455e25bddf"},{"author":{"_account_id":5511,"name":"Nikola Dipanov","email":"ndipanov@redhat.com","username":"ndipanov"},"change_message_id":"faf80f29953787a20366fa2b74bd248146d0f784","unresolved":false,"context_lines":[{"line_number":295,"context_line":"        \"\"\"Returns a list of server groups.\"\"\""},{"line_number":296,"context_line":"        context \u003d _authorize_context(req)"},{"line_number":297,"context_line":"        project_id \u003d context.project_id"},{"line_number":298,"context_line":"        if (\u0027all_projects_search\u0027 in req.GET) and ("},{"line_number":299,"context_line":"                    authorize_all_projects_search(context)):"},{"line_number":300,"context_line":"            sgs \u003d instance_group_obj.InstanceGroupList.get_all(context)"},{"line_number":301,"context_line":"        else:"}],"source_content_type":"text/x-python","patch_set":20,"id":"AAAAVX%2F%2F6kM%3D","line":298,"updated":"2014-02-27 12:21:55.000000000","message":"COuld have been just one parenthesis but this works too. Thanks!","commit_id":"90679a73f067bb41353c6dc613b972b8f7c98a96"},{"author":{"_account_id":5511,"name":"Nikola Dipanov","email":"ndipanov@redhat.com","username":"ndipanov"},"change_message_id":"faf80f29953787a20366fa2b74bd248146d0f784","unresolved":false,"context_lines":[{"line_number":335,"context_line":"            sg.project_id \u003d vals.get(\u0027project_id\u0027)"},{"line_number":336,"context_line":"            sg.policies \u003d policies"},{"line_number":337,"context_line":"            sg.metadetails \u003d metadata"},{"line_number":338,"context_line":"            sg.members \u003d members"},{"line_number":339,"context_line":"            sg.create(context)"},{"line_number":340,"context_line":"        except nova.exception.InvalidInput as e:"},{"line_number":341,"context_line":"            raise exc.HTTPBadRequest(explanation\u003de.format_message())"}],"source_content_type":"text/x-python","patch_set":20,"id":"AAAAVX%2F%2F6eg%3D","line":338,"updated":"2014-02-27 12:21:55.000000000","message":"Maybe validate that members exist here as well... see comment below","commit_id":"90679a73f067bb41353c6dc613b972b8f7c98a96"},{"author":{"_account_id":5511,"name":"Nikola Dipanov","email":"ndipanov@redhat.com","username":"ndipanov"},"change_message_id":"faf80f29953787a20366fa2b74bd248146d0f784","unresolved":false,"context_lines":[{"line_number":427,"context_line":"        sg_uuid \u003d id"},{"line_number":428,"context_line":"        if not self._is_valid_body(body.get(\u0027add_members\u0027, None), \u0027members\u0027):"},{"line_number":429,"context_line":"            raise exc.HTTPBadRequest()"},{"line_number":430,"context_line":"        members_to_add \u003d body[\u0027add_members\u0027][\u0027members\u0027] or []"},{"line_number":431,"context_line":"        try:"},{"line_number":432,"context_line":"            sg \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, sg_uuid)"},{"line_number":433,"context_line":"            sg.members +\u003d members_to_add"}],"source_content_type":"text/x-python","patch_set":20,"id":"AAAAVX%2F%2F6gw%3D","line":430,"updated":"2014-02-27 12:21:55.000000000","message":"We should probably check that these are actual instances here and raise if they are nto... it\u0027s an easy thing to add and makes the experience much more consistent...","commit_id":"90679a73f067bb41353c6dc613b972b8f7c98a96"},{"author":{"_account_id":5511,"name":"Nikola Dipanov","email":"ndipanov@redhat.com","username":"ndipanov"},"change_message_id":"faf80f29953787a20366fa2b74bd248146d0f784","unresolved":false,"context_lines":[{"line_number":452,"context_line":"            members_now \u003d set(sg.members or [])"},{"line_number":453,"context_line":"            sg.members \u003d list(members_now.difference(members_to_remove))"},{"line_number":454,"context_line":"            sg.save()"},{"line_number":455,"context_line":"            unknown_members \u003d list(members_to_remove.difference(members_now))"},{"line_number":456,"context_line":"            if unknown_members:"},{"line_number":457,"context_line":"                raise nova.exception.InstanceGroupMemberNotFound("},{"line_number":458,"context_line":"                            group_uuid\u003dsg_uuid, instance_id\u003dunknown_members)"}],"source_content_type":"text/x-python","patch_set":20,"id":"AAAAVX%2F%2F6iQ%3D","line":455,"updated":"2014-02-27 12:21:55.000000000","message":"Niiiice touch with the sets :)... but we should check and raise first before we actually do the database update. This way we would BOTH update and return an error - this is not good!","commit_id":"90679a73f067bb41353c6dc613b972b8f7c98a96"},{"author":{"_account_id":5511,"name":"Nikola Dipanov","email":"ndipanov@redhat.com","username":"ndipanov"},"change_message_id":"faf80f29953787a20366fa2b74bd248146d0f784","unresolved":false,"context_lines":[{"line_number":494,"context_line":"                    unknown_keys +\u003d key"},{"line_number":495,"context_line":"            sg.metadetails \u003d metadetails"},{"line_number":496,"context_line":"            sg.save()"},{"line_number":497,"context_line":"            if unknown_keys:"},{"line_number":498,"context_line":"                raise nova.exception.InstanceGroupMetadataNotFound("},{"line_number":499,"context_line":"                                group_uuid\u003dsg_uuid, metadata_key\u003dunknown_keys)"},{"line_number":500,"context_line":"        except nova.exception.InstanceGroupNotFound as e:"}],"source_content_type":"text/x-python","patch_set":20,"id":"AAAAVX%2F%2F6hk%3D","line":497,"updated":"2014-02-27 12:21:55.000000000","message":"Same here - should go before the save...","commit_id":"90679a73f067bb41353c6dc613b972b8f7c98a96"},{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"189bda3c050bc15c812b39d431a1c6c135386cee","unresolved":false,"context_lines":[{"line_number":214,"context_line":""},{"line_number":215,"context_line":"        members \u003d []"},{"line_number":216,"context_line":"        if group[\u0027members\u0027] is not None:"},{"line_number":217,"context_line":"            server_group[\u0027members\u0027] \u003d members"},{"line_number":218,"context_line":"            for member in group[\u0027members\u0027]:"},{"line_number":219,"context_line":"                members.append(member)"},{"line_number":220,"context_line":"        server_group[\u0027members\u0027] \u003d members"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2Fn%2BQ%3D","line":217,"updated":"2014-03-02 16:24:49.000000000","message":"line 217 is unnecessary","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":233,"context_line":"        server_group[\u0027name\u0027] \u003d group[\u0027name\u0027]"},{"line_number":234,"context_line":"        return server_group"},{"line_number":235,"context_line":""},{"line_number":236,"context_line":"    def _is_valid_body(self, body, key):"},{"line_number":237,"context_line":"        if not body:"},{"line_number":238,"context_line":"            return False"},{"line_number":239,"context_line":"        value \u003d body.get(key, None)"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoT8%3D","line":236,"updated":"2014-03-02 12:28:56.000000000","message":"is_valid_body is already defined in wsgi.py - can\u0027t you use that one?","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":267,"context_line":"    def show(self, req, id):"},{"line_number":268,"context_line":"        \"\"\"Return data about the given server group.\"\"\""},{"line_number":269,"context_line":"        context \u003d _authorize_context(req)"},{"line_number":270,"context_line":"        sg_uuid \u003d id"},{"line_number":271,"context_line":"        try:"},{"line_number":272,"context_line":"            sg \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, sg_uuid)"},{"line_number":273,"context_line":"        except nova.exception.InstanceGroupNotFound as e:"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoU8%3D","line":270,"updated":"2014-03-02 12:28:56.000000000","message":"why the temp sg_uuid?","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":277,"context_line":"    def delete(self, req, id):"},{"line_number":278,"context_line":"        \"\"\"Delete an server group.\"\"\""},{"line_number":279,"context_line":"        context \u003d _authorize_context(req)"},{"line_number":280,"context_line":"        sg_uuid \u003d id"},{"line_number":281,"context_line":"        try:"},{"line_number":282,"context_line":"            sg \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, sg_uuid)"},{"line_number":283,"context_line":"            sg.destroy(context)"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoU4%3D","line":280,"updated":"2014-03-02 12:28:56.000000000","message":"why the temp sg_uuid","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":313,"context_line":"        if not self._is_valid_body(body, \u0027server_group\u0027):"},{"line_number":314,"context_line":"            raise exc.HTTPBadRequest()"},{"line_number":315,"context_line":"        vals \u003d body[\u0027server_group\u0027]"},{"line_number":316,"context_line":"        policies \u003d vals.pop(\u0027policies\u0027, [])"},{"line_number":317,"context_line":"        members \u003d vals.pop(\u0027members\u0027, [])"},{"line_number":318,"context_line":"        metadata \u003d vals.pop(\u0027metadata\u0027, {})"},{"line_number":319,"context_line":"        vals[\u0027project_id\u0027] \u003d context.project_id"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoRY%3D","line":316,"updated":"2014-03-02 12:28:56.000000000","message":"Should you be doing input validation on this policies, members and metadata?","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"189bda3c050bc15c812b39d431a1c6c135386cee","unresolved":false,"context_lines":[{"line_number":313,"context_line":"        if not self._is_valid_body(body, \u0027server_group\u0027):"},{"line_number":314,"context_line":"            raise exc.HTTPBadRequest()"},{"line_number":315,"context_line":"        vals \u003d body[\u0027server_group\u0027]"},{"line_number":316,"context_line":"        policies \u003d vals.pop(\u0027policies\u0027, [])"},{"line_number":317,"context_line":"        members \u003d vals.pop(\u0027members\u0027, [])"},{"line_number":318,"context_line":"        metadata \u003d vals.pop(\u0027metadata\u0027, {})"},{"line_number":319,"context_line":"        vals[\u0027project_id\u0027] \u003d context.project_id"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2Fn%2BU%3D","line":316,"in_reply_to":"AAAAVX%2F%2FoRY%3D","updated":"2014-03-02 16:24:49.000000000","message":"Validation is done in https://review.openstack.org/#/c/77239/","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":317,"context_line":"        members \u003d vals.pop(\u0027members\u0027, [])"},{"line_number":318,"context_line":"        metadata \u003d vals.pop(\u0027metadata\u0027, {})"},{"line_number":319,"context_line":"        vals[\u0027project_id\u0027] \u003d context.project_id"},{"line_number":320,"context_line":"        vals[\u0027user_id\u0027] \u003d context.user_id"},{"line_number":321,"context_line":"        try:"},{"line_number":322,"context_line":"            sg \u003d instance_group_obj.InstanceGroup()"},{"line_number":323,"context_line":"            sg.name \u003d self._validate_name(vals.get(\u0027name\u0027))"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoTc%3D","line":320,"updated":"2014-03-02 12:28:56.000000000","message":"Should probably have better input validation here - eg verify that unexpected parameters are not supplied","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":320,"context_line":"        vals[\u0027user_id\u0027] \u003d context.user_id"},{"line_number":321,"context_line":"        try:"},{"line_number":322,"context_line":"            sg \u003d instance_group_obj.InstanceGroup()"},{"line_number":323,"context_line":"            sg.name \u003d self._validate_name(vals.get(\u0027name\u0027))"},{"line_number":324,"context_line":"            group_uuid \u003d vals.get(\u0027uuid\u0027)"},{"line_number":325,"context_line":"            if group_uuid:"},{"line_number":326,"context_line":"                sg.uuid \u003d group_uuid"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoTs%3D","line":323,"updated":"2014-03-02 12:28:56.000000000","message":"Perhaps the validation of name should be done outside of this try block and keep the try area as small as possible","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":331,"context_line":"            sg.policies \u003d policies"},{"line_number":332,"context_line":"            sg.metadetails \u003d metadata"},{"line_number":333,"context_line":"            sg.members \u003d members"},{"line_number":334,"context_line":"            sg.create(context)"},{"line_number":335,"context_line":"        except nova.exception.InvalidInput as e:"},{"line_number":336,"context_line":"            raise exc.HTTPBadRequest(explanation\u003de.format_message())"},{"line_number":337,"context_line":"        except nova.exception.InstanceGroupNotFound as e:"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoTk%3D","line":334,"updated":"2014-03-02 12:28:56.000000000","message":"Is it possible to get an InstanceGroupIdExists exception here?","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":334,"context_line":"            sg.create(context)"},{"line_number":335,"context_line":"        except nova.exception.InvalidInput as e:"},{"line_number":336,"context_line":"            raise exc.HTTPBadRequest(explanation\u003de.format_message())"},{"line_number":337,"context_line":"        except nova.exception.InstanceGroupNotFound as e:"},{"line_number":338,"context_line":"            raise webob.exc.HTTPNotFound(explanation\u003de.format_message())"},{"line_number":339,"context_line":"        return {\u0027server_group\u0027: self._format_server_group(context, sg)}"},{"line_number":340,"context_line":""}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoTo%3D","line":337,"updated":"2014-03-02 12:28:56.000000000","message":"Does the size of the try block for this exception catching need to be as large as it is?","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":343,"context_line":"    def update(self, req, id, body):"},{"line_number":344,"context_line":"        \"\"\"Update an server group\u0027s name, project_id, and user_id.\"\"\""},{"line_number":345,"context_line":"        context \u003d _authorize_context(req)"},{"line_number":346,"context_line":"        sg_uuid \u003d id"},{"line_number":347,"context_line":"        if not self._is_valid_body(body, \u0027server_group\u0027):"},{"line_number":348,"context_line":"            raise exc.HTTPBadRequest()"},{"line_number":349,"context_line":"        server_group_data \u003d body[\u0027server_group\u0027]"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoTY%3D","line":346,"updated":"2014-03-02 12:28:56.000000000","message":"Do you need to copy the id?","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":374,"context_line":"    def _add_policies(self, req, id, body):"},{"line_number":375,"context_line":"        \"\"\"Add policies to the specified server group.\"\"\""},{"line_number":376,"context_line":"        context \u003d _authorize_context(req)"},{"line_number":377,"context_line":"        sg_uuid \u003d id"},{"line_number":378,"context_line":"        if not self._is_valid_body(body.get(\u0027add_policies\u0027, None), \u0027policies\u0027):"},{"line_number":379,"context_line":"            raise exc.HTTPBadRequest()"},{"line_number":380,"context_line":"        policies_to_add \u003d body[\u0027add_policies\u0027][\u0027policies\u0027] or []"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoTM%3D","line":377,"updated":"2014-03-02 12:28:56.000000000","message":"do you need to copy this?","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":375,"context_line":"        \"\"\"Add policies to the specified server group.\"\"\""},{"line_number":376,"context_line":"        context \u003d _authorize_context(req)"},{"line_number":377,"context_line":"        sg_uuid \u003d id"},{"line_number":378,"context_line":"        if not self._is_valid_body(body.get(\u0027add_policies\u0027, None), \u0027policies\u0027):"},{"line_number":379,"context_line":"            raise exc.HTTPBadRequest()"},{"line_number":380,"context_line":"        policies_to_add \u003d body[\u0027add_policies\u0027][\u0027policies\u0027] or []"},{"line_number":381,"context_line":"        try:"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoTI%3D","line":378,"updated":"2014-03-02 12:28:56.000000000","message":"Don\u0027t need the default None here. add_policies is guaranteed to be in the body if routed here by wsgi.action(\u0027add_policies\u0027)","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":377,"context_line":"        sg_uuid \u003d id"},{"line_number":378,"context_line":"        if not self._is_valid_body(body.get(\u0027add_policies\u0027, None), \u0027policies\u0027):"},{"line_number":379,"context_line":"            raise exc.HTTPBadRequest()"},{"line_number":380,"context_line":"        policies_to_add \u003d body[\u0027add_policies\u0027][\u0027policies\u0027] or []"},{"line_number":381,"context_line":"        try:"},{"line_number":382,"context_line":"            sg \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, sg_uuid)"},{"line_number":383,"context_line":"            sg.policies +\u003d policies_to_add"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoTA%3D","line":380,"updated":"2014-03-02 12:28:56.000000000","message":"isn\u0027t something wrong with the user input if body[\u0027add_policies\u0027][\u0027policies\u0027] is not a list?","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":393,"context_line":"        \"\"\"Removes policies from the specified server group.\"\"\""},{"line_number":394,"context_line":"        context \u003d _authorize_context(req)"},{"line_number":395,"context_line":"        sg_uuid \u003d id"},{"line_number":396,"context_line":"        if not self._is_valid_body(body.get(\u0027remove_policies\u0027, None),"},{"line_number":397,"context_line":"                                            \u0027policies\u0027):"},{"line_number":398,"context_line":"            raise exc.HTTPBadRequest()"},{"line_number":399,"context_line":"        policies_to_remove \u003d set(body[\u0027remove_policies\u0027][\u0027policies\u0027] or [])"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoS4%3D","line":396,"updated":"2014-03-02 12:28:56.000000000","message":"similar comment as to add_policies above","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":396,"context_line":"        if not self._is_valid_body(body.get(\u0027remove_policies\u0027, None),"},{"line_number":397,"context_line":"                                            \u0027policies\u0027):"},{"line_number":398,"context_line":"            raise exc.HTTPBadRequest()"},{"line_number":399,"context_line":"        policies_to_remove \u003d set(body[\u0027remove_policies\u0027][\u0027policies\u0027] or [])"},{"line_number":400,"context_line":"        try:"},{"line_number":401,"context_line":"            sg \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, sg_uuid)"},{"line_number":402,"context_line":"            policies_now \u003d set(sg.policies or [])"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoS0%3D","line":399,"updated":"2014-03-02 12:28:56.000000000","message":"as with add_policies, should raise an error if the user input is not correct, not fallback to an empty list and process that.","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":420,"context_line":"        \"\"\"Add members to the specified server group.\"\"\""},{"line_number":421,"context_line":"        context \u003d _authorize_context(req)"},{"line_number":422,"context_line":"        sg_uuid \u003d id"},{"line_number":423,"context_line":"        if not self._is_valid_body(body.get(\u0027add_members\u0027, None), \u0027members\u0027):"},{"line_number":424,"context_line":"            raise exc.HTTPBadRequest()"},{"line_number":425,"context_line":"        members_to_add \u003d body[\u0027add_members\u0027][\u0027members\u0027] or []"},{"line_number":426,"context_line":"        try:"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoSg%3D","line":423,"updated":"2014-03-02 12:28:56.000000000","message":"same issue around add_members existing in body","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"c443e2bdedc84920ce128a9b7859987f67b5286a","unresolved":false,"context_lines":[{"line_number":509,"context_line":"    name \u003d \"ServerGroups\""},{"line_number":510,"context_line":"    alias \u003d \"os-server-groups\""},{"line_number":511,"context_line":"    namespace \u003d (\"http://docs.openstack.org/compute/ext/\""},{"line_number":512,"context_line":"                 \"servergroups/api/v1.1\")"},{"line_number":513,"context_line":"    updated \u003d \"2013-06-20T00:00:00+00:00\""},{"line_number":514,"context_line":""},{"line_number":515,"context_line":"    def get_resources(self):"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2FoRs%3D","line":512,"updated":"2014-03-02 12:28:56.000000000","message":"v2?","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"8b523ee42ebc08d73c86ce769b398625300fe18f","unresolved":false,"context_lines":[{"line_number":268,"context_line":"        :param name:     the given name of the server_group"},{"line_number":269,"context_line":"        \"\"\""},{"line_number":270,"context_line":"        if name is None or name \u003d\u003d \u0027\u0027:"},{"line_number":271,"context_line":"            msg \u003d _(\"names are invalid.\")"},{"line_number":272,"context_line":"            raise nova.exception.InvalidInput(reason\u003dmsg)"},{"line_number":273,"context_line":""},{"line_number":274,"context_line":"        VALID_NAME_REGEX \u003d re.compile(\"^(?! )[a-zA-Z0-9. _-]+(?\u003c! )$\")"}],"source_content_type":"text/x-python","patch_set":23,"id":"AAAAVn%2F%2Fu4Y%3D","line":271,"updated":"2014-03-04 13:07:56.000000000","message":"nit - \"Name is invalid\" would be better, preferably passing back the value which is invalid","commit_id":"cdcf56d6b3dd17f24ef2382ca12e4b93ec650b16"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"8b523ee42ebc08d73c86ce769b398625300fe18f","unresolved":false,"context_lines":[{"line_number":354,"context_line":""},{"line_number":355,"context_line":"        vals \u003d body[\u0027server_group\u0027]"},{"line_number":356,"context_line":"        sg \u003d instance_group_obj.InstanceGroup()"},{"line_number":357,"context_line":"        sg.uuid \u003d vals.get(\u0027id\u0027, uuid.uuid1())"},{"line_number":358,"context_line":"        sg.name \u003d vals.get(\u0027name\u0027, None)"},{"line_number":359,"context_line":"        sg.policies \u003d vals.get(\u0027policies\u0027, [])"},{"line_number":360,"context_line":"        sg.members \u003d vals.get(\u0027members\u0027, [])"}],"source_content_type":"text/x-python","patch_set":23,"id":"AAAAVn%2F%2FuyI%3D","line":357,"updated":"2014-03-04 13:07:56.000000000","message":"So I don\u0027t really understand why its useful to be able to set the uuid - its just a handle right? Is there some reason that its useful to be able to set it? \n\nThe problem here is that if we do allow a user to set it, then you need to handle InstnaceGroupIdExists exception coming up through sg.create","commit_id":"cdcf56d6b3dd17f24ef2382ca12e4b93ec650b16"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"8b523ee42ebc08d73c86ce769b398625300fe18f","unresolved":false,"context_lines":[{"line_number":355,"context_line":"        vals \u003d body[\u0027server_group\u0027]"},{"line_number":356,"context_line":"        sg \u003d instance_group_obj.InstanceGroup()"},{"line_number":357,"context_line":"        sg.uuid \u003d vals.get(\u0027id\u0027, uuid.uuid1())"},{"line_number":358,"context_line":"        sg.name \u003d vals.get(\u0027name\u0027, None)"},{"line_number":359,"context_line":"        sg.policies \u003d vals.get(\u0027policies\u0027, [])"},{"line_number":360,"context_line":"        sg.members \u003d vals.get(\u0027members\u0027, [])"},{"line_number":361,"context_line":"        sg.metadetails \u003d vals.get(\u0027metadata\u0027, {})"}],"source_content_type":"text/x-python","patch_set":23,"id":"AAAAVn%2F%2Fu44%3D","line":358,"updated":"2014-03-04 13:07:56.000000000","message":"nit, don\u0027t need the None","commit_id":"cdcf56d6b3dd17f24ef2382ca12e4b93ec650b16"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"8b523ee42ebc08d73c86ce769b398625300fe18f","unresolved":false,"context_lines":[{"line_number":382,"context_line":"        context \u003d _authorize_context(req)"},{"line_number":383,"context_line":""},{"line_number":384,"context_line":"        try:"},{"line_number":385,"context_line":"            self._validate_input_body(body, \u0027server_group\u0027)"},{"line_number":386,"context_line":"        except nova.exception.InvalidInput as e:"},{"line_number":387,"context_line":"            raise exc.HTTPBadRequest(explanation\u003de.format_message())"},{"line_number":388,"context_line":""}],"source_content_type":"text/x-python","patch_set":23,"id":"AAAAVn%2F%2FutU%3D","line":385,"updated":"2014-03-04 13:07:56.000000000","message":"so I like how the input validation is much better than average here, but some fields such id aren\u0027t actually valid in this context. It would be nice if they could be rejected correctly.","commit_id":"cdcf56d6b3dd17f24ef2382ca12e4b93ec650b16"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"8b523ee42ebc08d73c86ce769b398625300fe18f","unresolved":false,"context_lines":[{"line_number":442,"context_line":"        except nova.exception.InvalidInput as e:"},{"line_number":443,"context_line":"            raise exc.HTTPBadRequest(explanation\u003de.format_message())"},{"line_number":444,"context_line":""},{"line_number":445,"context_line":"        policies_to_remove \u003d set(body[\u0027remove_policies\u0027][\u0027policies\u0027] or [])"},{"line_number":446,"context_line":""},{"line_number":447,"context_line":"        try:"},{"line_number":448,"context_line":"            sg \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, id)"}],"source_content_type":"text/x-python","patch_set":23,"id":"AAAAVn%2F%2FulE%3D","line":445,"updated":"2014-03-04 13:07:56.000000000","message":"this is a bit on the side of nittish - but it seems very odd that its valid to call remove_policies and well not specify any policies to remove. Probably better to return an HTTPBadRequest in this case?","commit_id":"cdcf56d6b3dd17f24ef2382ca12e4b93ec650b16"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"8b523ee42ebc08d73c86ce769b398625300fe18f","unresolved":false,"context_lines":[{"line_number":473,"context_line":"        except nova.exception.InvalidInput as e:"},{"line_number":474,"context_line":"            raise exc.HTTPBadRequest(explanation\u003de.format_message())"},{"line_number":475,"context_line":""},{"line_number":476,"context_line":"        members_to_add \u003d body[\u0027add_members\u0027][\u0027members\u0027] or []"},{"line_number":477,"context_line":""},{"line_number":478,"context_line":"        try:"},{"line_number":479,"context_line":"            sg \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, id)"}],"source_content_type":"text/x-python","patch_set":23,"id":"AAAAVn%2F%2Fuks%3D","line":476,"updated":"2014-03-04 13:07:56.000000000","message":"again nittish - seems a bit odd to call add_members and not actually add any","commit_id":"cdcf56d6b3dd17f24ef2382ca12e4b93ec650b16"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"8b523ee42ebc08d73c86ce769b398625300fe18f","unresolved":false,"context_lines":[{"line_number":499,"context_line":"        except nova.exception.InvalidInput as e:"},{"line_number":500,"context_line":"            raise exc.HTTPBadRequest(explanation\u003de.format_message())"},{"line_number":501,"context_line":""},{"line_number":502,"context_line":"        members_to_remove \u003d set(body[\u0027remove_members\u0027][\u0027members\u0027] or [])"},{"line_number":503,"context_line":""},{"line_number":504,"context_line":"        try:"},{"line_number":505,"context_line":"            sg \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, id)"}],"source_content_type":"text/x-python","patch_set":23,"id":"AAAAVn%2F%2FukU%3D","line":502,"updated":"2014-03-04 13:07:56.000000000","message":"nit: see above re: asking the method to do nothing","commit_id":"cdcf56d6b3dd17f24ef2382ca12e4b93ec650b16"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"facdc0fdd3bab851ca33ae07dec751aff7b6eedf","unresolved":false,"context_lines":[{"line_number":207,"context_line":"        server_group \u003d self._format_server_group_brief(context, group)"},{"line_number":208,"context_line":""},{"line_number":209,"context_line":"        policies \u003d []"},{"line_number":210,"context_line":"        if group[\u0027policies\u0027] is not None:"},{"line_number":211,"context_line":"            for policy in group[\u0027policies\u0027]:"},{"line_number":212,"context_line":"                policies.append(policy)"},{"line_number":213,"context_line":"        server_group[\u0027policies\u0027] \u003d policies"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FjQc%3D","line":210,"updated":"2014-03-05 13:45:41.000000000","message":"Note that since group is a NovaObject, you should attribute style access throughout this file.\n\n    group.policies instead of group[\u0027policies\u0027]","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"facdc0fdd3bab851ca33ae07dec751aff7b6eedf","unresolved":false,"context_lines":[{"line_number":216,"context_line":"        if group[\u0027members\u0027] is not None:"},{"line_number":217,"context_line":"            for member in group[\u0027members\u0027]:"},{"line_number":218,"context_line":"                members.append(member)"},{"line_number":219,"context_line":"        server_group[\u0027members\u0027] \u003d members"},{"line_number":220,"context_line":""},{"line_number":221,"context_line":"        metadata \u003d {}"},{"line_number":222,"context_line":"        if group[\u0027metadetails\u0027] is not None:"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FjQo%3D","line":219,"updated":"2014-03-05 13:45:41.000000000","message":"It seems like the above 2 blocks of code could be 2 lines, unless I\u0027m missing something ...\n\n    server_group[\u0027policies\u0027] \u003d group.policies or []\n    server_group[\u0027members\u0027] \u003d group.members or []","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"3b43e436452cece121a2542c115ccdd154dce364","unresolved":false,"context_lines":[{"line_number":222,"context_line":"        if group[\u0027metadetails\u0027] is not None:"},{"line_number":223,"context_line":"            for k, v in group[\u0027metadetails\u0027].items():"},{"line_number":224,"context_line":"                metadata[k] \u003d v"},{"line_number":225,"context_line":"        server_group[\u0027metadata\u0027] \u003d metadata"},{"line_number":226,"context_line":"        return server_group"},{"line_number":227,"context_line":""},{"line_number":228,"context_line":"    def _format_server_group_brief(self, context, group):"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FfeM%3D","line":225,"updated":"2014-03-05 20:08:44.000000000","message":"This too:\n\n  server_group[\u0027metadata\u0027] \u003d group.metadetails or {}","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"92efb0ee403e6bf933c4ee6a5eac49f00cd087ce","unresolved":false,"context_lines":[{"line_number":235,"context_line":"    def _validate_string_value(self, value, field):"},{"line_number":236,"context_line":"        \"\"\"Validate given string value."},{"line_number":237,"context_line":""},{"line_number":238,"context_line":"        :param name:     the given name of the string"},{"line_number":239,"context_line":"        \"\"\""},{"line_number":240,"context_line":"        VALID_REGEX \u003d re.compile(\"^(?! )[a-zA-Z0-9. _-]+(?\u003c! )$\")"},{"line_number":241,"context_line":""}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2Fj5c%3D","line":238,"updated":"2014-03-05 12:46:50.000000000","message":"nit - so this doc string is out of date now","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"facdc0fdd3bab851ca33ae07dec751aff7b6eedf","unresolved":false,"context_lines":[{"line_number":237,"context_line":""},{"line_number":238,"context_line":"        :param name:     the given name of the string"},{"line_number":239,"context_line":"        \"\"\""},{"line_number":240,"context_line":"        VALID_REGEX \u003d re.compile(\"^(?! )[a-zA-Z0-9. _-]+(?\u003c! )$\")"},{"line_number":241,"context_line":""},{"line_number":242,"context_line":"        # ensure name does not exceed 255 characters"},{"line_number":243,"context_line":"        utils.check_string_length(value, field,"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FjOg%3D","line":240,"updated":"2014-03-05 13:45:41.000000000","message":"Why this regex?  I can\u0027t find this check being done on names anywhere else.  We need to be consistent on what is a valid name.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"92efb0ee403e6bf933c4ee6a5eac49f00cd087ce","unresolved":false,"context_lines":[{"line_number":239,"context_line":"        \"\"\""},{"line_number":240,"context_line":"        VALID_REGEX \u003d re.compile(\"^(?! )[a-zA-Z0-9. _-]+(?\u003c! )$\")"},{"line_number":241,"context_line":""},{"line_number":242,"context_line":"        # ensure name does not exceed 255 characters"},{"line_number":243,"context_line":"        utils.check_string_length(value, field,"},{"line_number":244,"context_line":"                                    min_length\u003d1, max_length\u003d255)"},{"line_number":245,"context_line":""}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2Fj2U%3D","line":242,"updated":"2014-03-05 12:46:50.000000000","message":"nit - comment out of date","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"92efb0ee403e6bf933c4ee6a5eac49f00cd087ce","unresolved":false,"context_lines":[{"line_number":243,"context_line":"        utils.check_string_length(value, field,"},{"line_number":244,"context_line":"                                    min_length\u003d1, max_length\u003d255)"},{"line_number":245,"context_line":""},{"line_number":246,"context_line":"        # ensure name does not contain any special characters"},{"line_number":247,"context_line":"        valid_val \u003d VALID_REGEX.search(value)"},{"line_number":248,"context_line":"        if not valid_val:"},{"line_number":249,"context_line":"            msg \u003d _(\"\u0027%(field)s\u0027: %(value)s is invalid.\") % {"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2Fj18%3D","line":246,"updated":"2014-03-05 12:46:50.000000000","message":"nit - comment out of date","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"92efb0ee403e6bf933c4ee6a5eac49f00cd087ce","unresolved":false,"context_lines":[{"line_number":253,"context_line":"    def _validate_input_body(self, body, entity_name,"},{"line_number":254,"context_line":"                            expected_fields\u003dNone, exclusive\u003dFalse):"},{"line_number":255,"context_line":"        if not self.is_valid_body(body, entity_name):"},{"line_number":256,"context_line":"            msg \u003d _(\"the input body is invalid.\")"},{"line_number":257,"context_line":"            raise nova.exception.InvalidInput(reason\u003dmsg)"},{"line_number":258,"context_line":""},{"line_number":259,"context_line":"        subbody \u003d dict(body[entity_name])"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2Fj1Y%3D","line":256,"updated":"2014-03-05 12:46:50.000000000","message":"really small nit - \"The body is invalid\" is probably better.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"facdc0fdd3bab851ca33ae07dec751aff7b6eedf","unresolved":false,"context_lines":[{"line_number":256,"context_line":"            msg \u003d _(\"the input body is invalid.\")"},{"line_number":257,"context_line":"            raise nova.exception.InvalidInput(reason\u003dmsg)"},{"line_number":258,"context_line":""},{"line_number":259,"context_line":"        subbody \u003d dict(body[entity_name])"},{"line_number":260,"context_line":""},{"line_number":261,"context_line":"        expected_fields \u003d expected_fields or []"},{"line_number":262,"context_line":"        if expected_fields and exclusive:"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FjOI%3D","line":259,"updated":"2014-03-05 13:45:41.000000000","message":"why is dict() needed around this?  Isn\u0027t it already a dict?","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"3b43e436452cece121a2542c115ccdd154dce364","unresolved":false,"context_lines":[{"line_number":256,"context_line":"            msg \u003d _(\"the input body is invalid.\")"},{"line_number":257,"context_line":"            raise nova.exception.InvalidInput(reason\u003dmsg)"},{"line_number":258,"context_line":""},{"line_number":259,"context_line":"        subbody \u003d dict(body[entity_name])"},{"line_number":260,"context_line":""},{"line_number":261,"context_line":"        expected_fields \u003d expected_fields or []"},{"line_number":262,"context_line":"        if expected_fields and exclusive:"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FfdQ%3D","line":259,"in_reply_to":"AAAAVn%2F%2FjOI%3D","updated":"2014-03-05 20:08:44.000000000","message":"It\u0027s this method modifying something that was passed into it (i.e. this method doesn\u0027t own body[entity_name]). Not sure it\u0027s really necessary though, unless that chunk of the body is re-used elsewhere.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"3b43e436452cece121a2542c115ccdd154dce364","unresolved":false,"context_lines":[{"line_number":261,"context_line":"        expected_fields \u003d expected_fields or []"},{"line_number":262,"context_line":"        if expected_fields and exclusive:"},{"line_number":263,"context_line":"            unexpected_fields \u003d list("},{"line_number":264,"context_line":"                        set(subbody.keys()).difference(set(expected_fields)))"},{"line_number":265,"context_line":"            if unexpected_fields:"},{"line_number":266,"context_line":"                msg \u003d _(\"unexpected fields: %s\") % \u0027,\u0027.join(unexpected_fields)"},{"line_number":267,"context_line":"                raise nova.exception.InvalidInput(reason\u003dmsg)"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FfTI%3D","line":264,"updated":"2014-03-05 20:08:44.000000000","message":"This can go away...","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"3b43e436452cece121a2542c115ccdd154dce364","unresolved":false,"context_lines":[{"line_number":273,"context_line":""},{"line_number":274,"context_line":"        if subbody:"},{"line_number":275,"context_line":"            msg \u003d _(\"unsupported fields: %s\") % subbody.keys()"},{"line_number":276,"context_line":"            raise nova.exception.InvalidInput(reason\u003dmsg)"},{"line_number":277,"context_line":""},{"line_number":278,"context_line":"        if name is not None and not isinstance(name, basestring):"},{"line_number":279,"context_line":"            msg \u003d _(\"\u0027name\u0027 should be a string.\")"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FfRo%3D","line":276,"updated":"2014-03-05 20:08:44.000000000","message":"This duplicates the more complicated check above. I think this one is better, so I propose you remove the top one.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"3b43e436452cece121a2542c115ccdd154dce364","unresolved":false,"context_lines":[{"line_number":275,"context_line":"            msg \u003d _(\"unsupported fields: %s\") % subbody.keys()"},{"line_number":276,"context_line":"            raise nova.exception.InvalidInput(reason\u003dmsg)"},{"line_number":277,"context_line":""},{"line_number":278,"context_line":"        if name is not None and not isinstance(name, basestring):"},{"line_number":279,"context_line":"            msg \u003d _(\"\u0027name\u0027 should be a string.\")"},{"line_number":280,"context_line":"            raise nova.exception.InvalidInput(reason\u003dmsg)"},{"line_number":281,"context_line":"        elif \u0027name\u0027 in expected_fields and not name:"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FfRA%3D","line":278,"updated":"2014-03-05 20:08:44.000000000","message":"is not None and not isinstance(thing, type)\n\n...is redundant","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"3b43e436452cece121a2542c115ccdd154dce364","unresolved":false,"context_lines":[{"line_number":306,"context_line":"            raise nova.exception.InvalidInput(reason\u003dmsg)"},{"line_number":307,"context_line":"        elif \u0027metadata\u0027 in expected_fields and not metadata:"},{"line_number":308,"context_line":"            msg \u003d _(\"\u0027metadata\u0027 is either missing or empty.\")"},{"line_number":309,"context_line":"            raise nova.exception.InvalidInput(reason\u003dmsg)"},{"line_number":310,"context_line":"        elif metadata:"},{"line_number":311,"context_line":"            for (key, val) in metadata.items():"},{"line_number":312,"context_line":"                self._validate_string_value(key, \u0027metadata key\u0027)"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FfQ4%3D","line":309,"updated":"2014-03-05 20:08:44.000000000","message":"Everything above this point could be replaced by a pretty tight loop, something like:\n\n types \u003d {\u0027name\u0027: str, \u0027members\u0027: list, ...}\n for key in expected_fields:\n     if not isinstance(subbody.pop(key, None), types[key]):\n        raise ....\n\nOtherwise it\u0027s a lot of duplicated code. Then after this loop, you put your:\n\n if subbody:\n    raise # Extra things provided","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"3b43e436452cece121a2542c115ccdd154dce364","unresolved":false,"context_lines":[{"line_number":322,"context_line":"            filters \u003d {\u0027uuid\u0027: members}"},{"line_number":323,"context_line":"            try:"},{"line_number":324,"context_line":"                valid_members \u003d instance_obj.InstanceList.get_by_filters("},{"line_number":325,"context_line":"                                                            context, filters)"},{"line_number":326,"context_line":"            except nova.exception.InstanceNotFound:"},{"line_number":327,"context_line":"                raise nova.exception.InstanceNotFound(instance_id\u003dmembers)"},{"line_number":328,"context_line":"            valid_uuids \u003d [member.uuid for member in valid_members]"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FfF8%3D","line":325,"updated":"2014-03-05 20:08:44.000000000","message":"You can\u0027t do this, as you race with InstanceGroup.save(). The group\u0027s save method should do this checking and raise a NotFound if appropriate, and then you should handle it then. This is really just wasted DB traffic.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"facdc0fdd3bab851ca33ae07dec751aff7b6eedf","unresolved":false,"context_lines":[{"line_number":324,"context_line":"                valid_members \u003d instance_obj.InstanceList.get_by_filters("},{"line_number":325,"context_line":"                                                            context, filters)"},{"line_number":326,"context_line":"            except nova.exception.InstanceNotFound:"},{"line_number":327,"context_line":"                raise nova.exception.InstanceNotFound(instance_id\u003dmembers)"},{"line_number":328,"context_line":"            valid_uuids \u003d [member.uuid for member in valid_members]"},{"line_number":329,"context_line":"            unknown_members \u003d list(set(members).difference(set(valid_uuids)))"},{"line_number":330,"context_line":"            if unknown_members:"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FjJw%3D","line":327,"updated":"2014-03-05 13:45:41.000000000","message":"this catch and raise seems unnecessary, given that it raises the same thing","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"facdc0fdd3bab851ca33ae07dec751aff7b6eedf","unresolved":false,"context_lines":[{"line_number":356,"context_line":"        \"\"\"Returns a list of server groups.\"\"\""},{"line_number":357,"context_line":"        context \u003d _authorize_context(req)"},{"line_number":358,"context_line":"        project_id \u003d context.project_id"},{"line_number":359,"context_line":"        if (\u0027all_projects_search\u0027 in req.GET) and ("},{"line_number":360,"context_line":"                    authorize_all_projects_search(context)):"},{"line_number":361,"context_line":"            sgs \u003d instance_group_obj.InstanceGroupList.get_all(context)"},{"line_number":362,"context_line":"        else:"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2Fjss%3D","line":359,"updated":"2014-03-05 13:45:41.000000000","message":"This query parameter doesn\u0027t exist anywhere else in the API.  I think it\u0027s important to be consistent here.\n\nWhat *does* exist is \u0027all_tenants\u0027.  However, that\u0027s being changed to \u0027all_projects\u0027 in the v3 API, so perhaps \u0027all_projects\u0027 is what should be used here.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"92efb0ee403e6bf933c4ee6a5eac49f00cd087ce","unresolved":false,"context_lines":[{"line_number":368,"context_line":"        result \u003d [self._format_server_group(context, group)"},{"line_number":369,"context_line":"                  for group in limited_list]"},{"line_number":370,"context_line":"        return {\u0027server_groups\u0027:"},{"line_number":371,"context_line":"                list(sorted(result, key\u003dlambda k: (k[\u0027name\u0027])))}"},{"line_number":372,"context_line":""},{"line_number":373,"context_line":"    @wsgi.serializers(xml\u003dServerGroupTemplate)"},{"line_number":374,"context_line":"    @wsgi.deserializers(xml\u003dServerGroupXMLDeserializer)"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2Fjzo%3D","line":371,"updated":"2014-03-05 12:46:50.000000000","message":"so just a thought, but should we really be sorting the output by default here? IIRC its not something we do unless a sort parameter is passed and that allows clients to sort on a field of their choosing.\n\nA sort parameter is something we can add later in a backwards compatible manner if it really is needed.\n\nAnd I think the other issue is if we\u0027re sorting we really want to sort before limiting the list. Otherwise we can get really weird output.\n\neg. we return the first 100 items as it comes out of the db sorted by name. And then the next 100 items as they come out of the db separately sorted by name. Most likely thats not what people want :-)","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"facdc0fdd3bab851ca33ae07dec751aff7b6eedf","unresolved":false,"context_lines":[{"line_number":385,"context_line":"        vals \u003d body[\u0027server_group\u0027]"},{"line_number":386,"context_line":"        sg \u003d instance_group_obj.InstanceGroup()"},{"line_number":387,"context_line":"        sg.name \u003d vals.get(\u0027name\u0027)"},{"line_number":388,"context_line":"        sg.policies \u003d vals.get(\u0027policies\u0027, [])"},{"line_number":389,"context_line":"        sg.members \u003d vals.get(\u0027members\u0027, [])"},{"line_number":390,"context_line":"        sg.metadetails \u003d vals.get(\u0027metadata\u0027, {})"},{"line_number":391,"context_line":"        sg.project_id \u003d context.project_id"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FjHw%3D","line":388,"updated":"2014-03-05 13:45:41.000000000","message":"definitely need policy validation, but looks like that\u0027s in a followup patch","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"3b43e436452cece121a2542c115ccdd154dce364","unresolved":false,"context_lines":[{"line_number":389,"context_line":"        sg.members \u003d vals.get(\u0027members\u0027, [])"},{"line_number":390,"context_line":"        sg.metadetails \u003d vals.get(\u0027metadata\u0027, {})"},{"line_number":391,"context_line":"        sg.project_id \u003d context.project_id"},{"line_number":392,"context_line":"        sg.user_id \u003d context.user_id"},{"line_number":393,"context_line":""},{"line_number":394,"context_line":"        try:"},{"line_number":395,"context_line":"            self._validate_members(context, sg.members)"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FfMs%3D","line":392,"updated":"2014-03-05 20:08:44.000000000","message":"Setting these fields on the object will already validate string-ness, dict-ness, and list-ness. It pretty much means that all the validation you do above for basic type checking is redundant and unnecessary.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"3b43e436452cece121a2542c115ccdd154dce364","unresolved":false,"context_lines":[{"line_number":392,"context_line":"        sg.user_id \u003d context.user_id"},{"line_number":393,"context_line":""},{"line_number":394,"context_line":"        try:"},{"line_number":395,"context_line":"            self._validate_members(context, sg.members)"},{"line_number":396,"context_line":"            sg.create(context)"},{"line_number":397,"context_line":"        except nova.exception.InvalidInput as e:"},{"line_number":398,"context_line":"            raise exc.HTTPBadRequest(explanation\u003de.format_message())"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FfLo%3D","line":395,"updated":"2014-03-05 20:08:44.000000000","message":"This should be in its own try:except block and raise its own exceptions, IMHO. It\u0027s a different thing from the create below.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"92efb0ee403e6bf933c4ee6a5eac49f00cd087ce","unresolved":false,"context_lines":[{"line_number":401,"context_line":"        except nova.exception.InstanceNotFound as e:"},{"line_number":402,"context_line":"            raise exc.HTTPNotFound(explanation\u003de.format_message())"},{"line_number":403,"context_line":""},{"line_number":404,"context_line":"        return {\u0027server_group\u0027: self._format_server_group(context, sg)}"},{"line_number":405,"context_line":""},{"line_number":406,"context_line":"    @wsgi.serializers(xml\u003dServerGroupTemplate)"},{"line_number":407,"context_line":"    @wsgi.deserializers(xml\u003dServerGroupXMLDeserializer)"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2Fjy0%3D","line":404,"updated":"2014-03-05 12:46:50.000000000","message":"probably should be returning a 201 instead of a 200","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"facdc0fdd3bab851ca33ae07dec751aff7b6eedf","unresolved":false,"context_lines":[{"line_number":421,"context_line":"        vals \u003d {}"},{"line_number":422,"context_line":"        vals[\u0027name\u0027] \u003d server_group_data.get(\u0027name\u0027)"},{"line_number":423,"context_line":"        vals[\u0027project_id\u0027] \u003d context.project_id"},{"line_number":424,"context_line":"        vals[\u0027user_id\u0027] \u003d context.user_id"},{"line_number":425,"context_line":""},{"line_number":426,"context_line":"        try:"},{"line_number":427,"context_line":"            sg \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, id)"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FjGA%3D","line":424,"updated":"2014-03-05 13:45:41.000000000","message":"Does it make sense to support updating these fields and not others like members or policies?\n\nWhy have actions for the other things?\n\nAlso, it looks like members and policies would just get silently ignored here.\n\nAnother issue is it looks like the user_id is going to get randomly changed based on the last caller to this update.  I\u0027m not sure if that makes sense.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"3b43e436452cece121a2542c115ccdd154dce364","unresolved":false,"context_lines":[{"line_number":425,"context_line":""},{"line_number":426,"context_line":"        try:"},{"line_number":427,"context_line":"            sg \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, id)"},{"line_number":428,"context_line":"            sg.update(vals)"},{"line_number":429,"context_line":"            sg.save()"},{"line_number":430,"context_line":"        except nova.exception.InvalidInput as e:"},{"line_number":431,"context_line":"            raise exc.HTTPBadRequest(explanation\u003de.format_message())"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FfK8%3D","line":428,"updated":"2014-03-05 20:08:44.000000000","message":"Really? We\u0027re letting users give their instance groups to other users? And just by calling update() on it?  Huh?","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"facdc0fdd3bab851ca33ae07dec751aff7b6eedf","unresolved":false,"context_lines":[{"line_number":452,"context_line":"        try:"},{"line_number":453,"context_line":"            sg \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, id)"},{"line_number":454,"context_line":"            sg.policies +\u003d policies_to_add"},{"line_number":455,"context_line":"            sg.save()"},{"line_number":456,"context_line":"        except nova.exception.InstanceGroupNotFound as e:"},{"line_number":457,"context_line":"            raise webob.exc.HTTPNotFound(explanation\u003de.format_message())"},{"line_number":458,"context_line":""}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FjFc%3D","line":455,"updated":"2014-03-05 13:45:41.000000000","message":"This is not safe.  There is a race condition here in the retrieve / update / save with other updates.\n\nThere are a bunch of these cases.  Fixing all of them is likely going to require some new methods on the InstanceGroup object, as well.  Take a look at the add_members() method on the object as an example of something that is safe.  We need methods like that where we can do an update without basing it on pulling the list from the db first.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"3b43e436452cece121a2542c115ccdd154dce364","unresolved":false,"context_lines":[{"line_number":452,"context_line":"        try:"},{"line_number":453,"context_line":"            sg \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, id)"},{"line_number":454,"context_line":"            sg.policies +\u003d policies_to_add"},{"line_number":455,"context_line":"            sg.save()"},{"line_number":456,"context_line":"        except nova.exception.InstanceGroupNotFound as e:"},{"line_number":457,"context_line":"            raise webob.exc.HTTPNotFound(explanation\u003de.format_message())"},{"line_number":458,"context_line":""}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FfJ0%3D","line":455,"in_reply_to":"AAAAVn%2F%2FjFc%3D","updated":"2014-03-05 20:08:44.000000000","message":"Agreed.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"facdc0fdd3bab851ca33ae07dec751aff7b6eedf","unresolved":false,"context_lines":[{"line_number":482,"context_line":"                raise nova.exception.InstanceGroupPolicyNotFound("},{"line_number":483,"context_line":"                                group_uuid\u003did, policy\u003dunknown_policies)"},{"line_number":484,"context_line":"            sg.policies \u003d list(policies_now.difference(policies_to_remove))"},{"line_number":485,"context_line":"            sg.save()"},{"line_number":486,"context_line":"        except nova.exception.InstanceGroupNotFound as e:"},{"line_number":487,"context_line":"            raise webob.exc.HTTPNotFound(explanation\u003de.format_message())"},{"line_number":488,"context_line":"        except nova.exception.InstanceGroupPolicyNotFound as e:"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FjFU%3D","line":485,"updated":"2014-03-05 13:45:41.000000000","message":"This is not safe.  There is a race condition here in the retrieve / update / save with other updates.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"facdc0fdd3bab851ca33ae07dec751aff7b6eedf","unresolved":false,"context_lines":[{"line_number":509,"context_line":"            sg \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, id)"},{"line_number":510,"context_line":"            self._validate_members(context, members_to_add)"},{"line_number":511,"context_line":"            sg.members +\u003d members_to_add"},{"line_number":512,"context_line":"            sg.save()"},{"line_number":513,"context_line":"        except nova.exception.InstanceNotFound as e:"},{"line_number":514,"context_line":"            raise webob.exc.HTTPNotFound(explanation\u003de.format_message())"},{"line_number":515,"context_line":"        except nova.exception.InstanceGroupNotFound as e:"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FjFM%3D","line":512,"updated":"2014-03-05 13:45:41.000000000","message":"This is not safe.  There is a race condition here in the retrieve / update / save with other updates.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"facdc0fdd3bab851ca33ae07dec751aff7b6eedf","unresolved":false,"context_lines":[{"line_number":540,"context_line":"                raise nova.exception.InstanceGroupMemberNotFound("},{"line_number":541,"context_line":"                            group_uuid\u003did, instance_id\u003dunknown_members)"},{"line_number":542,"context_line":"            sg.members \u003d list(members_now.difference(members_to_remove))"},{"line_number":543,"context_line":"            sg.save()"},{"line_number":544,"context_line":"        except nova.exception.InstanceGroupNotFound as e:"},{"line_number":545,"context_line":"            raise webob.exc.HTTPNotFound(explanation\u003de.format_message())"},{"line_number":546,"context_line":"        except nova.exception.InstanceGroupMemberNotFound as e:"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FjE8%3D","line":543,"updated":"2014-03-05 13:45:41.000000000","message":"This is not safe.  There is a race condition here in the retrieve / update / save with other updates.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"92efb0ee403e6bf933c4ee6a5eac49f00cd087ce","unresolved":false,"context_lines":[{"line_number":550,"context_line":""},{"line_number":551,"context_line":"    @wsgi.serializers(xml\u003dServerGroupTemplate)"},{"line_number":552,"context_line":"    @wsgi.deserializers(xml\u003dServerGroupActionXMLDeserializer)"},{"line_number":553,"context_line":"    @wsgi.action(\"set_metadata\")"},{"line_number":554,"context_line":"    def _set_metadata(self, req, id, body):"},{"line_number":555,"context_line":"        \"\"\"Update metadata for the specified server group.\"\"\""},{"line_number":556,"context_line":"        context \u003d _authorize_context(req)"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2Fjnw%3D","line":553,"updated":"2014-03-05 12:46:50.000000000","message":"so this looks very much like updating specific metadata rather than setting it.\n\nIn other areas of the API set has been used to imply everything currently stored is deleted and only what is supplied now remains.\n\nupdate means that you want to just update certain parts which is what this looks like it is doing.\n\nSo rather than call it set_metadata it should be called update_metadata\n\n(body field should be changed as well)\n\nI guess you want to think about if you want a set_metadata call as well.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"92efb0ee403e6bf933c4ee6a5eac49f00cd087ce","unresolved":false,"context_lines":[{"line_number":579,"context_line":"        try:"},{"line_number":580,"context_line":"            sg \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, id)"},{"line_number":581,"context_line":"            metadetails \u003d dict(sg.metadetails)"},{"line_number":582,"context_line":"            metadetails.update(metadata_to_update)"},{"line_number":583,"context_line":"            for key in keys_to_delete:"},{"line_number":584,"context_line":"                if not metadetails.pop(key, None):"},{"line_number":585,"context_line":"                    unknown_keys +\u003d key"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2Fjls%3D","line":582,"updated":"2014-03-05 12:46:50.000000000","message":"so I guess there is a race here if two calls update the metadata at the same time. Do we care?","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"facdc0fdd3bab851ca33ae07dec751aff7b6eedf","unresolved":false,"context_lines":[{"line_number":587,"context_line":"                raise nova.exception.InstanceGroupMetadataNotFound("},{"line_number":588,"context_line":"                                group_uuid\u003did, metadata_key\u003dunknown_keys)"},{"line_number":589,"context_line":"            sg.metadetails \u003d metadetails"},{"line_number":590,"context_line":"            sg.save()"},{"line_number":591,"context_line":"        except nova.exception.InstanceGroupNotFound as e:"},{"line_number":592,"context_line":"            raise webob.exc.HTTPNotFound(explanation\u003de.format_message())"},{"line_number":593,"context_line":"        except nova.exception.InstanceGroupMetadataNotFound as e:"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FjE0%3D","line":590,"updated":"2014-03-05 13:45:41.000000000","message":"This is not safe.  There is a race condition here in the retrieve / update / save with other updates.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"3b43e436452cece121a2542c115ccdd154dce364","unresolved":false,"context_lines":[{"line_number":587,"context_line":"                raise nova.exception.InstanceGroupMetadataNotFound("},{"line_number":588,"context_line":"                                group_uuid\u003did, metadata_key\u003dunknown_keys)"},{"line_number":589,"context_line":"            sg.metadetails \u003d metadetails"},{"line_number":590,"context_line":"            sg.save()"},{"line_number":591,"context_line":"        except nova.exception.InstanceGroupNotFound as e:"},{"line_number":592,"context_line":"            raise webob.exc.HTTPNotFound(explanation\u003de.format_message())"},{"line_number":593,"context_line":"        except nova.exception.InstanceGroupMetadataNotFound as e:"}],"source_content_type":"text/x-python","patch_set":29,"id":"AAAAVn%2F%2FfEg%3D","line":590,"in_reply_to":"AAAAVn%2F%2FjE0%3D","updated":"2014-03-05 20:08:44.000000000","message":"The point is valid, of course, but I think that we take this hit on other metadata operations, so it\u0027s not critical to fix this, IMHO. It\u0027s only a race with itself, and we pretty much paper over those issues elsewhere.","commit_id":"8ac1bd91f2aafb55191b8552cacd8a99b7996bb9"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"94c875f00f8096a54bc4605ec6743cb8772a8e63","unresolved":false,"context_lines":[{"line_number":172,"context_line":"        :param value:    the given value of the field"},{"line_number":173,"context_line":"        :param field:    the subfield of input body"},{"line_number":174,"context_line":"        \"\"\""},{"line_number":175,"context_line":"        VALID_REGEX \u003d re.compile(\"^(?! )[a-zA-Z0-9. _-]+(?\u003c! )$\")"},{"line_number":176,"context_line":""},{"line_number":177,"context_line":"        # ensure the string does not exceed 255 characters"},{"line_number":178,"context_line":"        utils.check_string_length(value, field,"}],"source_content_type":"text/x-python","patch_set":31,"id":"AAAAVn%2F%2FWpU%3D","line":175,"updated":"2014-03-06 17:11:40.000000000","message":"I had a comment on this in a previous patch.  Where does this come from?  I don\u0027t think we\u0027re doing this for names elsewhere.  Our name validation should be consistent.  IIRC, we *do* allow other characters in names, like UTF-8 ...","commit_id":"82025af0eb1535be8a5c7b923fe1d789c3269317"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"65d6f6cb037a8cfe1e2ed76ac0ca767bb9f9c340","unresolved":false,"context_lines":[{"line_number":235,"context_line":"        context \u003d _authorize_context(req)"},{"line_number":236,"context_line":"        project_id \u003d context.project_id"},{"line_number":237,"context_line":"        if (\u0027all_projects\u0027 in req.GET) and ("},{"line_number":238,"context_line":"                    authorize_all_projects_search(context)):"},{"line_number":239,"context_line":"            sgs \u003d instance_group_obj.InstanceGroupList.get_all(context)"},{"line_number":240,"context_line":"        else:"},{"line_number":241,"context_line":"            sgs \u003d instance_group_obj.InstanceGroupList.get_by_project_id("}],"source_content_type":"text/x-python","patch_set":31,"id":"AAAAVn%2F%2FXMI%3D","line":238,"updated":"2014-03-06 16:16:51.000000000","message":"Since we\u0027re not sure how we want to expose this as a policy in a consistent way, let\u0027s just drop the policy for now and hard code it to admin only.","commit_id":"82025af0eb1535be8a5c7b923fe1d789c3269317"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"0cad825bba66d6612fa49e324214acbe3e1d8f10","unresolved":false,"context_lines":[{"line_number":268,"context_line":"            sg.create(context)"},{"line_number":269,"context_line":"        except ValueError as e:"},{"line_number":270,"context_line":"            raise exc.HTTPBadRequest(explanation\u003de)"},{"line_number":271,"context_line":"        except nova.exception.ObjectActionError as e:"},{"line_number":272,"context_line":"            raise exc.HTTPBadRequest(explanation\u003de.format_message())"},{"line_number":273,"context_line":""},{"line_number":274,"context_line":"        return {\u0027server_group\u0027: self._format_server_group(context, sg)}"}],"source_content_type":"text/x-python","patch_set":31,"id":"AAAAVn%2F%2FXQY%3D","line":271,"updated":"2014-03-06 16:11:19.000000000","message":"This can\u0027t be raised because you don\u0027t set sg.id","commit_id":"82025af0eb1535be8a5c7b923fe1d789c3269317"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"3eec3713cab82b71f975018ce841663250b8adb3","unresolved":false,"context_lines":[{"line_number":57,"context_line":""},{"line_number":58,"context_line":"def make_group_brief(elem):"},{"line_number":59,"context_line":"    elem.set(\u0027name\u0027)"},{"line_number":60,"context_line":"    elem.set(\u0027id\u0027)"},{"line_number":61,"context_line":""},{"line_number":62,"context_line":"server_group_nsmap \u003d {None: xmlutil.XMLNS_V11, \u0027atom\u0027: xmlutil.XMLNS_ATOM}"},{"line_number":63,"context_line":""}],"source_content_type":"text/x-python","patch_set":33,"id":"AAAAVn%2F%2FU8k%3D","line":60,"updated":"2014-03-06 20:05:20.000000000","message":"This function appears to be unused","commit_id":"647bbef6b206cf9e556c2f2c34c97e20c07d1911"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"3eec3713cab82b71f975018ce841663250b8adb3","unresolved":false,"context_lines":[{"line_number":149,"context_line":"        # There is no \u0027uuid\u0027 key in server_group seen by clients."},{"line_number":150,"context_line":"        # In addition, clients see policies as a [\"policy-name\"] list;"},{"line_number":151,"context_line":"        # and they see members as a [\"server-id\"] list."},{"line_number":152,"context_line":"        server_group \u003d self._format_server_group_brief(context, group)"},{"line_number":153,"context_line":"        server_group[\u0027policies\u0027] \u003d group.policies or []"},{"line_number":154,"context_line":"        server_group[\u0027members\u0027] \u003d group.members or []"},{"line_number":155,"context_line":"        server_group[\u0027metadata\u0027] \u003d group.metadetails or {}"}],"source_content_type":"text/x-python","patch_set":33,"id":"AAAAVn%2F%2FU8U%3D","line":152,"updated":"2014-03-06 20:05:20.000000000","message":"Doesn\u0027t seem to be any reason to have this separate function since it\u0027s not used anywhere else","commit_id":"647bbef6b206cf9e556c2f2c34c97e20c07d1911"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"3eec3713cab82b71f975018ce841663250b8adb3","unresolved":false,"context_lines":[{"line_number":167,"context_line":"            msg \u003d _(\"the body is invalid.\")"},{"line_number":168,"context_line":"            raise nova.exception.InvalidInput(reason\u003dmsg)"},{"line_number":169,"context_line":""},{"line_number":170,"context_line":"        subbody \u003d dict(body[entity_name])"},{"line_number":171,"context_line":""},{"line_number":172,"context_line":"        expected_fields \u003d [\u0027name\u0027, \u0027policies\u0027]"},{"line_number":173,"context_line":"        for field in expected_fields:"}],"source_content_type":"text/x-python","patch_set":33,"id":"AAAAVn%2F%2FU8Q%3D","line":170,"updated":"2014-03-06 20:05:20.000000000","message":"I don\u0027t think dict() around this is necessary","commit_id":"647bbef6b206cf9e556c2f2c34c97e20c07d1911"},{"author":{"_account_id":8514,"name":"Yathiraj Udupi","email":"yudupi@cisco.com","username":"yudupi"},"change_message_id":"8a3c73003fda2abcc8f55aec37154c46ee36fb24","unresolved":false,"context_lines":[{"line_number":197,"context_line":"        return {\u0027server_group\u0027: self._format_server_group(context, sg)}"},{"line_number":198,"context_line":""},{"line_number":199,"context_line":"    def delete(self, req, id):"},{"line_number":200,"context_line":"        \"\"\"Delete an server group.\"\"\""},{"line_number":201,"context_line":"        context \u003d _authorize_context(req)"},{"line_number":202,"context_line":"        try:"},{"line_number":203,"context_line":"            sg \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, id)"}],"source_content_type":"text/x-python","patch_set":33,"id":"AAAAVn%2F%2FVXI%3D","line":200,"updated":"2014-03-06 19:19:08.000000000","message":"Minor typo \"a\" instead of \"an\"","commit_id":"647bbef6b206cf9e556c2f2c34c97e20c07d1911"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"126a6fb57ccc39d63ec4630d185fb4d8189b483f","unresolved":false,"context_lines":[{"line_number":239,"context_line":"        try:"},{"line_number":240,"context_line":"            sg.name \u003d vals.get(\u0027name\u0027)"},{"line_number":241,"context_line":"            sg.policies \u003d vals.get(\u0027policies\u0027)"},{"line_number":242,"context_line":"            sg.create(context)"},{"line_number":243,"context_line":"        except ValueError as e:"},{"line_number":244,"context_line":"            raise exc.HTTPBadRequest(explanation\u003de)"},{"line_number":245,"context_line":""}],"source_content_type":"text/x-python","patch_set":33,"id":"AAAAVn%2F%2FVBs%3D","line":242,"updated":"2014-03-06 19:49:42.000000000","message":"AFAICT, the UUID isn\u0027t getting set.  Am I missing something or do we need to add something like:\n\n    sg.uuid \u003d str(uuid.uuid4())\n\n?","commit_id":"647bbef6b206cf9e556c2f2c34c97e20c07d1911"},{"author":{"_account_id":1561,"name":"Russell Bryant","email":"rbryant@redhat.com","username":"russellb"},"change_message_id":"50c108afb8f360fd747c2d0f054a8cffaa488591","unresolved":false,"context_lines":[{"line_number":239,"context_line":"        try:"},{"line_number":240,"context_line":"            sg.name \u003d vals.get(\u0027name\u0027)"},{"line_number":241,"context_line":"            sg.policies \u003d vals.get(\u0027policies\u0027)"},{"line_number":242,"context_line":"            sg.create(context)"},{"line_number":243,"context_line":"        except ValueError as e:"},{"line_number":244,"context_line":"            raise exc.HTTPBadRequest(explanation\u003de)"},{"line_number":245,"context_line":""}],"source_content_type":"text/x-python","patch_set":33,"id":"AAAAVn%2F%2FVAw%3D","line":242,"in_reply_to":"AAAAVn%2F%2FVBs%3D","updated":"2014-03-06 19:51:54.000000000","message":"Nevermind, Dan Smith pointed out where it happens (down in the db API)","commit_id":"647bbef6b206cf9e556c2f2c34c97e20c07d1911"},{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"8616084d496c88d3daac3a142faa7c49b1da3f01","unresolved":false,"context_lines":[{"line_number":171,"context_line":"                            min_length\u003d1, max_length\u003d255)"},{"line_number":172,"context_line":"            elif isinstance(value, list):"},{"line_number":173,"context_line":"                [utils.check_string_length(v, field,"},{"line_number":174,"context_line":"                            min_length\u003d1, max_length\u003d255) for v in value]"},{"line_number":175,"context_line":""},{"line_number":176,"context_line":"        if subbody:"},{"line_number":177,"context_line":"            msg \u003d _(\"unsupported fields: %s\") % subbody.keys()"}],"source_content_type":"text/x-python","patch_set":35,"id":"AAAAVn%2F%2FTJ0%3D","line":174,"updated":"2014-03-06 23:57:32.000000000","message":"This validation(line163-174) seems loose, each field type is not checked completely. Even if \u0027name\u0027 would be list, it cannot catch it.","commit_id":"8a2aad4ee5b1f40837a5791d936f1945e269d6b1"},{"author":{"_account_id":5292,"name":"Christopher Yeoh","email":"cbkyeoh@gmail.com","username":"cyeoh-0"},"change_message_id":"d5a309173d49cf78878bbbd2faa96c4d8ab3492a","unresolved":false,"context_lines":[{"line_number":171,"context_line":"                            min_length\u003d1, max_length\u003d255)"},{"line_number":172,"context_line":"            elif isinstance(value, list):"},{"line_number":173,"context_line":"                [utils.check_string_length(v, field,"},{"line_number":174,"context_line":"                            min_length\u003d1, max_length\u003d255) for v in value]"},{"line_number":175,"context_line":""},{"line_number":176,"context_line":"        if subbody:"},{"line_number":177,"context_line":"            msg \u003d _(\"unsupported fields: %s\") % subbody.keys()"}],"source_content_type":"text/x-python","patch_set":35,"id":"AAAAVn%2F%2FRXw%3D","line":174,"in_reply_to":"AAAAVn%2F%2FSk8%3D","updated":"2014-03-07 05:55:23.000000000","message":"I think the object checking only checks that its a small enough string though?\n\nI think it makes sense to put some reasonable additional constraints on what a valid name is like we do for other areas such as keypairs or flavors. Things like leading and trailing whitespace I don\u0027t think we need consider valid. And I think we should be trying to be consistent about what we consider is a valid name across our APIs.\n\nSo if you don\u0027t have any problems with it, I\u0027ll create a dependent patch  which tightens the validation on the name field (I think its near enough to a \"bug\")","commit_id":"8a2aad4ee5b1f40837a5791d936f1945e269d6b1"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"b2303446bdc68831705d14a9e6b5d1f738649c14","unresolved":false,"context_lines":[{"line_number":171,"context_line":"                            min_length\u003d1, max_length\u003d255)"},{"line_number":172,"context_line":"            elif isinstance(value, list):"},{"line_number":173,"context_line":"                [utils.check_string_length(v, field,"},{"line_number":174,"context_line":"                            min_length\u003d1, max_length\u003d255) for v in value]"},{"line_number":175,"context_line":""},{"line_number":176,"context_line":"        if subbody:"},{"line_number":177,"context_line":"            msg \u003d _(\"unsupported fields: %s\") % subbody.keys()"}],"source_content_type":"text/x-python","patch_set":35,"id":"AAAAVn%2F%2FSk8%3D","line":174,"in_reply_to":"AAAAVn%2F%2FTJ0%3D","updated":"2014-03-07 01:18:53.000000000","message":"We do more validation of this when it\u0027s actually shoved into the object, so I think this is fine.","commit_id":"8a2aad4ee5b1f40837a5791d936f1945e269d6b1"}],"nova/api/openstack/compute/plugins/v3/instance_groups.py":[{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"3810dfcb688cc463eb9a824efcdf82de734e24c6","unresolved":false,"context_lines":[{"line_number":1,"context_line":"# vim: tabstop\u003d4 shiftwidth\u003d4 softtabstop\u003d4"},{"line_number":2,"context_line":""},{"line_number":3,"context_line":"#    Licensed under the Apache License, Version 2.0 (the \"License\"); you may"},{"line_number":4,"context_line":"#    not use this file except in compliance with the License. You may obtain"}],"source_content_type":"text/x-python","patch_set":6,"id":"AAAAUH%2F%2ByEM%3D","line":1,"updated":"2014-01-22 07:34:39.000000000","message":"ditto - please remove lines 1 and 2","commit_id":"4dc01f4cf9bca2cc1529df93a9bf10a3affbf727"},{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"3810dfcb688cc463eb9a824efcdf82de734e24c6","unresolved":false,"context_lines":[{"line_number":16,"context_line":""},{"line_number":17,"context_line":"import re"},{"line_number":18,"context_line":"import uuid"},{"line_number":19,"context_line":"import webob"},{"line_number":20,"context_line":"from webob import exc"},{"line_number":21,"context_line":""},{"line_number":22,"context_line":"from nova.api.openstack import common"}],"source_content_type":"text/x-python","patch_set":6,"id":"AAAAUH%2F%2ByB8%3D","line":19,"updated":"2014-01-22 07:34:39.000000000","message":"webob should be in its own group here","commit_id":"4dc01f4cf9bca2cc1529df93a9bf10a3affbf727"},{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"3810dfcb688cc463eb9a824efcdf82de734e24c6","unresolved":false,"context_lines":[{"line_number":534,"context_line":"        # Add new key-value pairs and update existing keys with new values"},{"line_number":535,"context_line":"        try:"},{"line_number":536,"context_line":"            ig \u003d instance_group_obj.InstanceGroup.get_by_uuid(context, id)"},{"line_number":537,"context_line":"            md \u003d ig.metadetails"},{"line_number":538,"context_line":"            md.update(metadataToAdd)"},{"line_number":539,"context_line":"            ig.metadetails \u003d md"},{"line_number":540,"context_line":"            ig.save()"}],"source_content_type":"text/x-python","patch_set":6,"id":"AAAAUH%2F%2ByEI%3D","line":537,"updated":"2014-01-22 07:34:39.000000000","message":"lines 537 - 540 should be outside of the try","commit_id":"4dc01f4cf9bca2cc1529df93a9bf10a3affbf727"}],"nova/objects/instance_group.py":[{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"3810dfcb688cc463eb9a824efcdf82de734e24c6","unresolved":false,"context_lines":[{"line_number":50,"context_line":"        # Most of the field names match right now, so be quick"},{"line_number":51,"context_line":"        for field in instance_group.fields:"},{"line_number":52,"context_line":"            if field \u003d\u003d \u0027deleted\u0027:"},{"line_number":53,"context_line":"                flag \u003d db_inst[\u0027deleted\u0027] \u003d\u003d db_inst[\u0027id\u0027]"},{"line_number":54,"context_line":"                instance_group.deleted \u003d flag"},{"line_number":55,"context_line":"            else:"},{"line_number":56,"context_line":"                instance_group[field] \u003d db_inst[field]"}],"source_content_type":"text/x-python","patch_set":6,"id":"AAAAUH%2F%2ByEA%3D","line":53,"updated":"2014-01-22 07:34:39.000000000","message":"not sure why we need this change","commit_id":"4dc01f4cf9bca2cc1529df93a9bf10a3affbf727"}],"nova/tests/api/openstack/compute/contrib/test_instance_groups.py":[{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"3810dfcb688cc463eb9a824efcdf82de734e24c6","unresolved":false,"context_lines":[{"line_number":1,"context_line":"# vim: tabstop\u003d4 shiftwidth\u003d4 softtabstop\u003d4"},{"line_number":2,"context_line":""},{"line_number":3,"context_line":"#    Licensed under the Apache License, Version 2.0 (the \"License\"); you may"},{"line_number":4,"context_line":"#    not use this file except in compliance with the License. You may obtain"}],"source_content_type":"text/x-python","patch_set":6,"id":"AAAAUH%2F%2ByD8%3D","line":1,"updated":"2014-01-22 07:34:39.000000000","message":"please remove 1 and 2","commit_id":"4dc01f4cf9bca2cc1529df93a9bf10a3affbf727"},{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"b0a27b3b8e9f0a5bb0a867e40a52a8ac75bf2e14","unresolved":false,"context_lines":[{"line_number":27,"context_line":""},{"line_number":28,"context_line":""},{"line_number":29,"context_line":"CONF \u003d cfg.CONF"},{"line_number":30,"context_line":"LOG \u003d logging.getLogger(__name__)"},{"line_number":31,"context_line":""},{"line_number":32,"context_line":"FAKE_UUID1 \u003d \u0027a47ae74e-ab08-447f-8eee-ffd43fc46c16\u0027"},{"line_number":33,"context_line":"FAKE_UUID2 \u003d \u0027c6e6430a-6563-4efa-9542-5e93c9e97d18\u0027"}],"source_content_type":"text/x-python","patch_set":12,"id":"AAAAUX%2F%2Flag%3D","line":30,"updated":"2014-02-12 07:26:19.000000000","message":"CONF and LOG seem unused in this test file.","commit_id":"ae4597a2053324c2262c3bbc0ea817d418a24e54"}],"nova/tests/api/openstack/compute/contrib/test_server_groups.py":[{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"189bda3c050bc15c812b39d431a1c6c135386cee","unresolved":false,"context_lines":[{"line_number":100,"context_line":"        self.assertEqual(res_dict[\u0027server_group\u0027][\u0027members\u0027], [])"},{"line_number":101,"context_line":"        self.assertEqual(res_dict[\u0027server_group\u0027][\u0027metadata\u0027], {})"},{"line_number":102,"context_line":""},{"line_number":103,"context_line":"    def test_create_server_group_with_polcies_members_meta(self):"},{"line_number":104,"context_line":"        sgroup \u003d server_group_template()"},{"line_number":105,"context_line":"        policies \u003d [\u0027anti-affinity\u0027]"},{"line_number":106,"context_line":"        sgroup[\u0027policies\u0027] \u003d policies"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2Fn%2BE%3D","line":103,"updated":"2014-03-02 16:24:49.000000000","message":"polcies \u003d\u003e policies","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"},{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"189bda3c050bc15c812b39d431a1c6c135386cee","unresolved":false,"context_lines":[{"line_number":117,"context_line":"        self.assertEqual(res_dict[\u0027server_group\u0027][\u0027members\u0027], members)"},{"line_number":118,"context_line":"        self.assertEqual(res_dict[\u0027server_group\u0027][\u0027metadata\u0027], metadata)"},{"line_number":119,"context_line":""},{"line_number":120,"context_line":"    def test_create_server_group_with_ilegal_name(self):"},{"line_number":121,"context_line":"        # blank name"},{"line_number":122,"context_line":"        sgroup \u003d server_group_template(name\u003d\u0027\u0027)"},{"line_number":123,"context_line":"        req \u003d fakes.HTTPRequest.blank(\u0027/v2/fake/os-server-groups\u0027)"}],"source_content_type":"text/x-python","patch_set":22,"id":"AAAAVX%2F%2Fn%2BI%3D","line":120,"updated":"2014-03-02 16:24:49.000000000","message":"ilegal \u003d\u003e illegal","commit_id":"febf6e0559e2614ea8ed51322d0587b9c109f74d"}],"nova/tests/integrated/api_samples/all_extensions/extensions-get-resp.xml.tpl":[{"author":{"_account_id":1653,"name":"garyk","email":"gkotton@vmware.com","username":"garyk"},"change_message_id":"3810dfcb688cc463eb9a824efcdf82de734e24c6","unresolved":false,"context_lines":[{"line_number":1,"context_line":"\u003c?xml version\u003d\u00271.0\u0027 encoding\u003d\u0027UTF-8\u0027?\u003e"},{"line_number":2,"context_line":"\u003cextensions xmlns:atom\u003d\"http://www.w3.org/2005/Atom\" xmlns\u003d\"http://docs.openstack.org/common/api/v1.0\"\u003e"},{"line_number":3,"context_line":"\u003cextension alias\u003d\"NMN\" updated\u003d\"%(timestamp)s\" namespace\u003d\"http://docs.openstack.org/compute/ext/multinic/api/v1.1\" name\u003d\"Multinic\"\u003e"},{"line_number":4,"context_line":"\u003cdescription\u003e%(text)s\u003c/description\u003e"},{"line_number":5,"context_line":"\u003c/extension\u003e"},{"line_number":6,"context_line":"\u003cextension alias\u003d\"OS-DCF\" updated\u003d\"%(timestamp)s\" namespace\u003d\"http://docs.openstack.org/compute/ext/disk_config/api/v1.1\" name\u003d\"DiskConfig\"\u003e"}],"source_content_type":"text/x-smarty","patch_set":6,"id":"AAAAUH%2F%2ByD4%3D","line":3,"updated":"2014-01-22 07:34:39.000000000","message":"not sure why all of the indentations here are changed - it is not related to the patch set","commit_id":"4dc01f4cf9bca2cc1529df93a9bf10a3affbf727"}],"nova/tests/integrated/api_samples/os-instance-groups/instance-group-metadata-post-req.json.tpl":[{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"462bf216b0c28977515d46d3410fd2614fe70562","unresolved":false,"context_lines":[{"line_number":1,"context_line":"{"},{"line_number":2,"context_line":"    \"set_metadata\":"},{"line_number":3,"context_line":"        {"},{"line_number":4,"context_line":"            \"metadata\":"},{"line_number":5,"context_line":"                {"}],"source_content_type":"text/x-smarty","patch_set":14,"id":"AAAAUX%2F%2B5yw%3D","line":2,"updated":"2014-02-18 09:56:35.000000000","message":"The same changes between patchset13 and 14 are necessary for template files also. The changes of other template files are necessary.","commit_id":"2b315e9b8186c479c08f74bf19a31c64dab4c173"}],"nova/tests/integrated/api_samples/os-instance-groups/instance-group-metadata-update-req.json.tpl":[{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"462bf216b0c28977515d46d3410fd2614fe70562","unresolved":false,"context_lines":[{"line_number":1,"context_line":"{"},{"line_number":2,"context_line":"    \"set_metadata\":"},{"line_number":3,"context_line":"        {"},{"line_number":4,"context_line":"            \"metadata\":"},{"line_number":5,"context_line":"                {"}],"source_content_type":"text/x-smarty","patch_set":14,"id":"AAAAUX%2F%2B5x4%3D","line":2,"updated":"2014-02-18 09:56:35.000000000","message":"ditto","commit_id":"2b315e9b8186c479c08f74bf19a31c64dab4c173"}],"nova/tests/integrated/api_samples/os-instance-groups/instance-groups-add-policies-post-req.json.tpl":[{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"462bf216b0c28977515d46d3410fd2614fe70562","unresolved":false,"context_lines":[{"line_number":1,"context_line":"{"},{"line_number":2,"context_line":"  \"add_policies\":"},{"line_number":3,"context_line":"    {"},{"line_number":4,"context_line":"        \"policies\":"},{"line_number":5,"context_line":"        [\"anti-affinity\"]"}],"source_content_type":"text/x-smarty","patch_set":14,"id":"AAAAUX%2F%2B5wQ%3D","line":2,"updated":"2014-02-18 09:56:35.000000000","message":"ditto","commit_id":"2b315e9b8186c479c08f74bf19a31c64dab4c173"}],"nova/tests/integrated/api_samples/os-server-groups/server-groups-list-resp.json.tpl":[{"author":{"_account_id":6167,"name":"Ken\u0027ichi Ohmichi","email":"ken1ohmichi@gmail.com","username":"oomichi"},"change_message_id":"8616084d496c88d3daac3a142faa7c49b1da3f01","unresolved":false,"context_lines":[{"line_number":7,"context_line":"            \"members\": [],"},{"line_number":8,"context_line":"            \"metadata\": {}"},{"line_number":9,"context_line":"        }"},{"line_number":10,"context_line":"   ]"},{"line_number":11,"context_line":"}"}],"source_content_type":"text/x-smarty","patch_set":35,"id":"AAAAVn%2F%2FTmQ%3D","line":10,"updated":"2014-03-06 23:57:32.000000000","message":"need one more space.","commit_id":"8a2aad4ee5b1f40837a5791d936f1945e269d6b1"}],"nova/tests/integrated/test_api_samples.py":[{"author":{"_account_id":7494,"name":"Guangya Liu","email":"gyliu513@gmail.com","username":"JayLau"},"change_message_id":"f1a2735c692690f80a06f759db2a018d13dc07cc","unresolved":false,"context_lines":[{"line_number":4048,"context_line":"    def _get_create_subs(self):"},{"line_number":4049,"context_line":"        return {"},{"line_number":4050,"context_line":"                \u0027name\u0027: \u0027test\u0027"},{"line_number":4051,"context_line":"        }"},{"line_number":4052,"context_line":""},{"line_number":4053,"context_line":"    def _post_instance_group(self):"},{"line_number":4054,"context_line":"        \"\"\"Verify the response status and returns the UUID of the"}],"source_content_type":"text/x-python","patch_set":10,"id":"AAAAUH%2F9jHw%3D","line":4051,"updated":"2014-02-06 05:12:11.000000000","message":"This can be merged to one line.","commit_id":"eb79b6658cd797ff05d85da12ace5ba44e275a64"},{"author":{"_account_id":7494,"name":"Guangya Liu","email":"gyliu513@gmail.com","username":"JayLau"},"change_message_id":"f1a2735c692690f80a06f759db2a018d13dc07cc","unresolved":false,"context_lines":[{"line_number":4088,"context_line":"        # Get api sample of instance groups get request."},{"line_number":4089,"context_line":"        subs \u003d {"},{"line_number":4090,"context_line":"                \u0027name\u0027: \u0027test\u0027,"},{"line_number":4091,"context_line":"                }"},{"line_number":4092,"context_line":"        uuid \u003d self._post_instance_group()"},{"line_number":4093,"context_line":"        subs[\u0027id\u0027] \u003d uuid"},{"line_number":4094,"context_line":"        response \u003d self._do_get(\u0027os-instance-groups/%s\u0027 % uuid)"}],"source_content_type":"text/x-python","patch_set":10,"id":"AAAAUH%2F9jHs%3D","line":4091,"updated":"2014-02-06 05:12:11.000000000","message":"ditto","commit_id":"eb79b6658cd797ff05d85da12ace5ba44e275a64"},{"author":{"_account_id":7494,"name":"Guangya Liu","email":"gyliu513@gmail.com","username":"JayLau"},"change_message_id":"f1a2735c692690f80a06f759db2a018d13dc07cc","unresolved":false,"context_lines":[{"line_number":4100,"context_line":"        uuid \u003d self._post_instance_group()"},{"line_number":4101,"context_line":"        subs \u003d {"},{"line_number":4102,"context_line":"                \u0027name\u0027: \u0027new_name\u0027"},{"line_number":4103,"context_line":"                }"},{"line_number":4104,"context_line":""},{"line_number":4105,"context_line":"        response \u003d self._do_put(\u0027os-instance-groups/%s\u0027 % uuid,"},{"line_number":4106,"context_line":"                                \u0027instance-groups-update-req\u0027,"}],"source_content_type":"text/x-python","patch_set":10,"id":"AAAAUH%2F9jHo%3D","line":4103,"updated":"2014-02-06 05:12:11.000000000","message":"ditto","commit_id":"eb79b6658cd797ff05d85da12ace5ba44e275a64"},{"author":{"_account_id":7494,"name":"Guangya Liu","email":"gyliu513@gmail.com","username":"JayLau"},"change_message_id":"f1a2735c692690f80a06f759db2a018d13dc07cc","unresolved":false,"context_lines":[{"line_number":4107,"context_line":"                                subs)"},{"line_number":4108,"context_line":"        subs \u003d {"},{"line_number":4109,"context_line":"                \u0027id\u0027: uuid,"},{"line_number":4110,"context_line":"                }"},{"line_number":4111,"context_line":""},{"line_number":4112,"context_line":"        self._verify_response(\u0027instance-groups-update-resp\u0027,"},{"line_number":4113,"context_line":"                              subs,"}],"source_content_type":"text/x-python","patch_set":10,"id":"AAAAUH%2F9jHk%3D","line":4110,"updated":"2014-02-06 05:12:11.000000000","message":"ditto","commit_id":"eb79b6658cd797ff05d85da12ace5ba44e275a64"},{"author":{"_account_id":7494,"name":"Guangya Liu","email":"gyliu513@gmail.com","username":"JayLau"},"change_message_id":"f1a2735c692690f80a06f759db2a018d13dc07cc","unresolved":false,"context_lines":[{"line_number":4121,"context_line":"                                 {\u0027action\u0027: \u0027set_metadata\u0027})"},{"line_number":4122,"context_line":"        subs \u003d {"},{"line_number":4123,"context_line":"                \u0027id\u0027: uuid,"},{"line_number":4124,"context_line":"                }"},{"line_number":4125,"context_line":""},{"line_number":4126,"context_line":"        self._verify_response(\u0027instance-group-metadata-post-resp\u0027, subs,"},{"line_number":4127,"context_line":"                              response, 200)"}],"source_content_type":"text/x-python","patch_set":10,"id":"AAAAUH%2F9jHg%3D","line":4124,"updated":"2014-02-06 05:12:11.000000000","message":"ditto and the following.","commit_id":"eb79b6658cd797ff05d85da12ace5ba44e275a64"}]}
