)]}'
{"nova/objects/__init__.py":[{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"b1fb552628691d68d297a08dcde442d5e1880ddc","unresolved":false,"context_lines":[{"line_number":53,"context_line":"    __import__(\u0027nova.objects.monitor_metric\u0027)"},{"line_number":54,"context_line":"    __import__(\u0027nova.objects.network\u0027)"},{"line_number":55,"context_line":"    __import__(\u0027nova.objects.network_request\u0027)"},{"line_number":56,"context_line":"    __import__(\u0027nova.objects.notification\u0027)"},{"line_number":57,"context_line":"    __import__(\u0027nova.objects.numa\u0027)"},{"line_number":58,"context_line":"    __import__(\u0027nova.objects.pci_device\u0027)"},{"line_number":59,"context_line":"    __import__(\u0027nova.objects.pci_device_pool\u0027)"}],"source_content_type":"text/x-python","patch_set":3,"id":"ba8a016a_b875fd98","line":56,"updated":"2015-11-17 22:13:28.000000000","message":"Bring this up to a parent patch","commit_id":"25b774c7a60f0400cd69149e496c27bb11cad1b0"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"6a3b68fb410d8c71c29a4c660cf92b86298b6e91","unresolved":false,"context_lines":[{"line_number":53,"context_line":"    __import__(\u0027nova.objects.monitor_metric\u0027)"},{"line_number":54,"context_line":"    __import__(\u0027nova.objects.network\u0027)"},{"line_number":55,"context_line":"    __import__(\u0027nova.objects.network_request\u0027)"},{"line_number":56,"context_line":"    __import__(\u0027nova.objects.notification\u0027)"},{"line_number":57,"context_line":"    __import__(\u0027nova.objects.numa\u0027)"},{"line_number":58,"context_line":"    __import__(\u0027nova.objects.pci_device\u0027)"},{"line_number":59,"context_line":"    __import__(\u0027nova.objects.pci_device_pool\u0027)"}],"source_content_type":"text/x-python","patch_set":3,"id":"ba8a016a_191c1a69","line":56,"in_reply_to":"ba8a016a_b875fd98","updated":"2015-11-18 16:50:44.000000000","message":"Done","commit_id":"25b774c7a60f0400cd69149e496c27bb11cad1b0"}],"nova/objects/fields.py":[{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"b1fb552628691d68d297a08dcde442d5e1880ddc","unresolved":false,"context_lines":[{"line_number":426,"context_line":"            valid_values\u003dPciDeviceType.ALL)"},{"line_number":427,"context_line":""},{"line_number":428,"context_line":""},{"line_number":429,"context_line":"class NotificationPriorityType(Enum):"},{"line_number":430,"context_line":"    AUDIT \u003d \u0027audit\u0027"},{"line_number":431,"context_line":"    CRITICAL \u003d \u0027critical\u0027"},{"line_number":432,"context_line":"    DEBUG \u003d \u0027debug\u0027"}],"source_content_type":"text/x-python","patch_set":3,"id":"ba8a016a_386a6db4","line":429,"updated":"2015-11-17 22:13:28.000000000","message":"These 3 classes are part of the base so they should move up to a parent patch","commit_id":"25b774c7a60f0400cd69149e496c27bb11cad1b0"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"6a3b68fb410d8c71c29a4c660cf92b86298b6e91","unresolved":false,"context_lines":[{"line_number":426,"context_line":"            valid_values\u003dPciDeviceType.ALL)"},{"line_number":427,"context_line":""},{"line_number":428,"context_line":""},{"line_number":429,"context_line":"class NotificationPriorityType(Enum):"},{"line_number":430,"context_line":"    AUDIT \u003d \u0027audit\u0027"},{"line_number":431,"context_line":"    CRITICAL \u003d \u0027critical\u0027"},{"line_number":432,"context_line":"    DEBUG \u003d \u0027debug\u0027"}],"source_content_type":"text/x-python","patch_set":3,"id":"ba8a016a_d928d288","line":429,"in_reply_to":"ba8a016a_386a6db4","updated":"2015-11-18 16:50:44.000000000","message":"Done","commit_id":"25b774c7a60f0400cd69149e496c27bb11cad1b0"},{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"b1fb552628691d68d297a08dcde442d5e1880ddc","unresolved":false,"context_lines":[{"line_number":718,"context_line":"    AUTO_TYPE \u003d PciDeviceType()"},{"line_number":719,"context_line":""},{"line_number":720,"context_line":""},{"line_number":721,"context_line":"class NotificationPriorityTypeField(BaseEnumField):"},{"line_number":722,"context_line":"    AUTO_TYPE \u003d NotificationPriorityType()"},{"line_number":723,"context_line":""},{"line_number":724,"context_line":""}],"source_content_type":"text/x-python","patch_set":3,"id":"ba8a016a_2b8696b9","line":721,"updated":"2015-11-17 22:13:28.000000000","message":"same with these as above","commit_id":"25b774c7a60f0400cd69149e496c27bb11cad1b0"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"6a3b68fb410d8c71c29a4c660cf92b86298b6e91","unresolved":false,"context_lines":[{"line_number":718,"context_line":"    AUTO_TYPE \u003d PciDeviceType()"},{"line_number":719,"context_line":""},{"line_number":720,"context_line":""},{"line_number":721,"context_line":"class NotificationPriorityTypeField(BaseEnumField):"},{"line_number":722,"context_line":"    AUTO_TYPE \u003d NotificationPriorityType()"},{"line_number":723,"context_line":""},{"line_number":724,"context_line":""}],"source_content_type":"text/x-python","patch_set":3,"id":"ba8a016a_593dc2c2","line":721,"in_reply_to":"ba8a016a_2b8696b9","updated":"2015-11-18 16:50:44.000000000","message":"Done","commit_id":"25b774c7a60f0400cd69149e496c27bb11cad1b0"}],"nova/objects/notification.py":[{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"b1fb552628691d68d297a08dcde442d5e1880ddc","unresolved":false,"context_lines":[{"line_number":1,"context_line":"# Copyright 2015 OpenStack Foundation"},{"line_number":2,"context_line":"# All Rights Reserved."},{"line_number":3,"context_line":"#"},{"line_number":4,"context_line":"#    Licensed under the Apache License, Version 2.0 (the \"License\"); you may"}],"source_content_type":"text/x-python","patch_set":3,"id":"ba8a016a_abc046e1","line":1,"updated":"2015-11-17 22:13:28.000000000","message":"This whole file should get moved up to a parent change","commit_id":"25b774c7a60f0400cd69149e496c27bb11cad1b0"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"6a3b68fb410d8c71c29a4c660cf92b86298b6e91","unresolved":false,"context_lines":[{"line_number":1,"context_line":"# Copyright 2015 OpenStack Foundation"},{"line_number":2,"context_line":"# All Rights Reserved."},{"line_number":3,"context_line":"#"},{"line_number":4,"context_line":"#    Licensed under the Apache License, Version 2.0 (the \"License\"); you may"}],"source_content_type":"text/x-python","patch_set":3,"id":"ba8a016a_f954b6ff","line":1,"in_reply_to":"ba8a016a_abc046e1","updated":"2015-11-18 16:50:44.000000000","message":"Done","commit_id":"25b774c7a60f0400cd69149e496c27bb11cad1b0"}],"nova/objects/service.py":[{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"530c0349d3b2e589ae5a5892f7d3d08a6ca08b47","unresolved":false,"context_lines":[{"line_number":274,"context_line":"        db_service \u003d db.service_update(self._context, self.id, updates)"},{"line_number":275,"context_line":"        self._from_db_object(self._context, self, db_service)"},{"line_number":276,"context_line":""},{"line_number":277,"context_line":"        if ({\u0027disabled\u0027, \u0027disabled_reason\u0027, \u0027forced_down\u0027, \u0027version\u0027} \u0026"},{"line_number":278,"context_line":"                set(updates.keys())):"},{"line_number":279,"context_line":"            ServiceStatusNotification("},{"line_number":280,"context_line":"                publisher\u003dself,"}],"source_content_type":"text/x-python","patch_set":2,"id":"ba8a016a_4f55374e","line":277,"updated":"2015-11-17 16:55:11.000000000","message":"I think the style of this will be better if L277-286 is moved to a private function. That way the save method stays slimmed down.","commit_id":"a34f23cc87da5d702a34e0156c22970169e582d6"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"1c6fb3c3685e6c2bf22c9efddf844c9207854cae","unresolved":false,"context_lines":[{"line_number":274,"context_line":"        db_service \u003d db.service_update(self._context, self.id, updates)"},{"line_number":275,"context_line":"        self._from_db_object(self._context, self, db_service)"},{"line_number":276,"context_line":""},{"line_number":277,"context_line":"        if ({\u0027disabled\u0027, \u0027disabled_reason\u0027, \u0027forced_down\u0027, \u0027version\u0027} \u0026"},{"line_number":278,"context_line":"                set(updates.keys())):"},{"line_number":279,"context_line":"            ServiceStatusNotification("},{"line_number":280,"context_line":"                publisher\u003dself,"}],"source_content_type":"text/x-python","patch_set":2,"id":"ba8a016a_a42dde47","line":277,"in_reply_to":"ba8a016a_4f55374e","updated":"2015-11-17 19:33:41.000000000","message":"Done","commit_id":"a34f23cc87da5d702a34e0156c22970169e582d6"},{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"530c0349d3b2e589ae5a5892f7d3d08a6ca08b47","unresolved":false,"context_lines":[{"line_number":383,"context_line":"    fields \u003d {"},{"line_number":384,"context_line":"        # TODO(gibi): this is an object field which means the version of the"},{"line_number":385,"context_line":"        # payload depends on the version of the Service class which is maybe"},{"line_number":386,"context_line":"        # not what we want"},{"line_number":387,"context_line":"        \u0027service\u0027: fields.ObjectField(\u0027Service\u0027)"},{"line_number":388,"context_line":"    }"}],"source_content_type":"text/x-python","patch_set":2,"id":"ba8a016a_8fb6bf88","line":386,"updated":"2015-11-17 16:55:11.000000000","message":"This is definitely an interesting situation. The listener will have no concept of finding out what\u0027s different between versions of the object, it will basically just be getting a dict. I guess they can be guaranteed that what they\u0027re looking for will not be going away. Maybe that\u0027s good enough and we don\u0027t need to worry about locking versions or anything.","commit_id":"a34f23cc87da5d702a34e0156c22970169e582d6"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"1c6fb3c3685e6c2bf22c9efddf844c9207854cae","unresolved":false,"context_lines":[{"line_number":383,"context_line":"    fields \u003d {"},{"line_number":384,"context_line":"        # TODO(gibi): this is an object field which means the version of the"},{"line_number":385,"context_line":"        # payload depends on the version of the Service class which is maybe"},{"line_number":386,"context_line":"        # not what we want"},{"line_number":387,"context_line":"        \u0027service\u0027: fields.ObjectField(\u0027Service\u0027)"},{"line_number":388,"context_line":"    }"}],"source_content_type":"text/x-python","patch_set":2,"id":"ba8a016a_879d3c5b","line":386,"in_reply_to":"ba8a016a_8fb6bf88","updated":"2015-11-17 19:33:41.000000000","message":"I\u0027m hesitant to drop the version dependency. What if in the future we want to support backporting notification payload to an older version? If we don\u0027t have the version dependency then we cannot do that easily. In the other hand having the dependency means that the version of the payload object will be bumped quite frequently. However I feel bumping the version is not a big burden for the developer as it is single  line of code change and a single line of test code change. Also payload objects used to be at the end of the dependency chain so bumping the version of the payload object will not cause a cascade update.","commit_id":"a34f23cc87da5d702a34e0156c22970169e582d6"},{"author":{"_account_id":1063,"name":"Ed Leafe","email":"ed@leafe.com","username":"ed-leafe"},"change_message_id":"2f340dcbe8513a6bccf749a0a085a3a4ec2a6dd2","unresolved":false,"context_lines":[{"line_number":387,"context_line":"        # TODO(gibi): this is an object field which means the version of the"},{"line_number":388,"context_line":"        # payload depends on the version of the Service class which is maybe"},{"line_number":389,"context_line":"        # not what we want"},{"line_number":390,"context_line":"        \u0027service\u0027: fields.ObjectField(\u0027Service\u0027)"},{"line_number":391,"context_line":"    }"}],"source_content_type":"text/x-python","patch_set":7,"id":"ba8a016a_20d836ef","line":390,"updated":"2015-11-20 22:56:45.000000000","message":"Hmmm... do we really need more here than the service binary?","commit_id":"e4c8f3a24efc24faa4055129ac6d71a6cde2e8f4"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"6a292e9118cab97ad54af762fa65083f003803eb","unresolved":false,"context_lines":[{"line_number":387,"context_line":"        # TODO(gibi): this is an object field which means the version of the"},{"line_number":388,"context_line":"        # payload depends on the version of the Service class which is maybe"},{"line_number":389,"context_line":"        # not what we want"},{"line_number":390,"context_line":"        \u0027service\u0027: fields.ObjectField(\u0027Service\u0027)"},{"line_number":391,"context_line":"    }"}],"source_content_type":"text/x-python","patch_set":7,"id":"ba8a016a_041ad817","line":390,"in_reply_to":"ba8a016a_20d836ef","updated":"2015-11-21 21:24:27.000000000","message":"I think we need more. For example consumer might be interested in the new state (service.disabled, service.forced_down) and the reason of the change (service.disabled_reason). We can debate to include only those fields instead of the whole object but as I cannot know every  potential consumers of this notification I feel we should include as much information as possible about the affected service and as we are including a lot of service information it is natural to me to re-use the existing service model as the container for such information.","commit_id":"e4c8f3a24efc24faa4055129ac6d71a6cde2e8f4"},{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"14b2a3e07f1fd20bcdd9bd9fb38b37d5e42d3bf9","unresolved":false,"context_lines":[{"line_number":277,"context_line":"        self._send_status_update_notification(updates)"},{"line_number":278,"context_line":""},{"line_number":279,"context_line":"    def _send_status_update_notification(self, updates):"},{"line_number":280,"context_line":"        if ({\u0027disabled\u0027, \u0027disabled_reason\u0027, \u0027forced_down\u0027, \u0027version\u0027} \u0026"},{"line_number":281,"context_line":"                set(updates.keys())):"},{"line_number":282,"context_line":"            payload \u003d ServiceStatusPayload()"},{"line_number":283,"context_line":"            payload.populate_schema(service\u003dself)"}],"source_content_type":"text/x-python","patch_set":17,"id":"7a740942_2e3dc3dc","line":280,"range":{"start_line":280,"start_character":59,"end_line":280,"end_character":68},"updated":"2015-12-08 22:41:26.000000000","message":"looking at the if check in save(), version is always dirtied, so do we want to be checking for that key here? if the comment above is correct, then if anything in the object is changed (besides version), we will always send a notification (because the updates will be [\u0027version\u0027, \u003csomething_else\u003e]). I understand we want to emit a notification on a real change of the service version, but is there any way we can emit that and know we\u0027re emitting that the version *actually* changed?","commit_id":"e82106f5f1f7317ff8490c2e557442dc4d4bd7da"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"c475d295f2a36453d9fe14f2a143fdc06d771817","unresolved":false,"context_lines":[{"line_number":277,"context_line":"        self._send_status_update_notification(updates)"},{"line_number":278,"context_line":""},{"line_number":279,"context_line":"    def _send_status_update_notification(self, updates):"},{"line_number":280,"context_line":"        if ({\u0027disabled\u0027, \u0027disabled_reason\u0027, \u0027forced_down\u0027, \u0027version\u0027} \u0026"},{"line_number":281,"context_line":"                set(updates.keys())):"},{"line_number":282,"context_line":"            payload \u003d ServiceStatusPayload()"},{"line_number":283,"context_line":"            payload.populate_schema(service\u003dself)"}],"source_content_type":"text/x-python","patch_set":17,"id":"7a740942_50296988","line":280,"range":{"start_line":280,"start_character":59,"end_line":280,"end_character":68},"in_reply_to":"7a740942_2e3dc3dc","updated":"2015-12-10 13:42:04.000000000","message":"Good point. This code now means that if \u003csomething_else\u003e is changed then we always send notification even if something_else is not a notification triggering field because version is dirty. This is not what we want. (Actually version is only dirty until the first noop save() for a given Service object but that is not relevant here)\n\nNow it seems to me that detecting that the version is changed would need an extra db call in save() to read the db value and then compare it to the current value of version before the update_service call. Based on danms\u0027 effort to keep the save() noop regarding the dirty version I feel that it would be too costly to add an extra db query only to be able to send the notification.\n\nAll in all I think we are better off not to push for sending notification regarding version change as the price is too high.","commit_id":"e82106f5f1f7317ff8490c2e557442dc4d4bd7da"},{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"0970fc756a6f6dcd82fbef6cb22145fc9e04761c","unresolved":false,"context_lines":[{"line_number":277,"context_line":"        self._send_status_update_notification(updates)"},{"line_number":278,"context_line":""},{"line_number":279,"context_line":"    def _send_status_update_notification(self, updates):"},{"line_number":280,"context_line":"        if ({\u0027disabled\u0027, \u0027disabled_reason\u0027, \u0027forced_down\u0027} \u0026"},{"line_number":281,"context_line":"                set(updates.keys())):"},{"line_number":282,"context_line":"            payload \u003d ServiceStatusPayload()"},{"line_number":283,"context_line":"            payload.populate_schema(service\u003dself)"}],"source_content_type":"text/x-python","patch_set":18,"id":"7a740942_291b0bcc","line":280,"updated":"2015-12-10 17:03:19.000000000","message":"Will people question why we aren\u0027t sending a notification when the service version changes? If they might, you can put a NOTE here saying since version is always dirty, we will always send a notification when service is changed (basically what we were discussing on the previous patch set).","commit_id":"b84f074bb9725eb5ed3c4c311ccef6f55abb0010"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"ccc7efd986c98d562d4f4339059d63d89de7c112","unresolved":false,"context_lines":[{"line_number":277,"context_line":"        self._send_status_update_notification(updates)"},{"line_number":278,"context_line":""},{"line_number":279,"context_line":"    def _send_status_update_notification(self, updates):"},{"line_number":280,"context_line":"        if ({\u0027disabled\u0027, \u0027disabled_reason\u0027, \u0027forced_down\u0027} \u0026"},{"line_number":281,"context_line":"                set(updates.keys())):"},{"line_number":282,"context_line":"            payload \u003d ServiceStatusPayload()"},{"line_number":283,"context_line":"            payload.populate_schema(service\u003dself)"}],"source_content_type":"text/x-python","patch_set":18,"id":"7a740942_18ae1f81","line":280,"in_reply_to":"7a740942_291b0bcc","updated":"2015-12-14 10:36:50.000000000","message":"Good point!","commit_id":"b84f074bb9725eb5ed3c4c311ccef6f55abb0010"},{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"b1c5574f611b474e4b85729a5f60cef044a83ed2","unresolved":false,"context_lines":[{"line_number":277,"context_line":"        self._send_status_update_notification(updates)"},{"line_number":278,"context_line":""},{"line_number":279,"context_line":"    def _send_status_update_notification(self, updates):"},{"line_number":280,"context_line":"        # Note(gibi): We does not trigger notification on version as that field"},{"line_number":281,"context_line":"        # is always dirty, which would cause that nova sends notification on"},{"line_number":282,"context_line":"        # every other field change. See the comment in save() too."},{"line_number":283,"context_line":"        if ({\u0027disabled\u0027, \u0027disabled_reason\u0027, \u0027forced_down\u0027} \u0026"}],"source_content_type":"text/x-python","patch_set":19,"id":"7a740942_64f0c791","line":280,"range":{"start_line":280,"start_character":25,"end_line":280,"end_character":29},"updated":"2015-12-14 17:37:46.000000000","message":"nit: s/does/do","commit_id":"228d175e41460412a6c748513f3ecac979a1f94c"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"28c23dff707d8ce3a53d3eccdf8d60bce402dd3b","unresolved":false,"context_lines":[{"line_number":277,"context_line":"        self._send_status_update_notification(updates)"},{"line_number":278,"context_line":""},{"line_number":279,"context_line":"    def _send_status_update_notification(self, updates):"},{"line_number":280,"context_line":"        # Note(gibi): We does not trigger notification on version as that field"},{"line_number":281,"context_line":"        # is always dirty, which would cause that nova sends notification on"},{"line_number":282,"context_line":"        # every other field change. See the comment in save() too."},{"line_number":283,"context_line":"        if ({\u0027disabled\u0027, \u0027disabled_reason\u0027, \u0027forced_down\u0027} \u0026"}],"source_content_type":"text/x-python","patch_set":19,"id":"5a710552_5f52f168","line":280,"range":{"start_line":280,"start_character":25,"end_line":280,"end_character":29},"in_reply_to":"7a740942_64f0c791","updated":"2015-12-15 12:23:12.000000000","message":"Done","commit_id":"228d175e41460412a6c748513f3ecac979a1f94c"},{"author":{"_account_id":782,"name":"John Garbutt","email":"john@johngarbutt.com","username":"johngarbutt"},"change_message_id":"728249ba6e3a490733ba0fc3526f5fbf91adda69","unresolved":false,"context_lines":[{"line_number":370,"context_line":""},{"line_number":371,"context_line":""},{"line_number":372,"context_line":"@base.NovaObjectRegistry.register"},{"line_number":373,"context_line":"class ServiceStatusNotification(notification.NotificationBase):"},{"line_number":374,"context_line":"    # Version 1.0: Initial version"},{"line_number":375,"context_line":"    VERSION \u003d \u00271.0\u0027"},{"line_number":376,"context_line":""}],"source_content_type":"text/x-python","patch_set":25,"id":"fa69d971_7b96b295","line":373,"updated":"2016-01-08 13:39:25.000000000","message":"I wonder if we should move this to nova/objects/notifications/service.py\n\nSo its clear where all the notification things are?","commit_id":"36b21df39e8b8014a3443245b9a2e4d46ab32ccd"},{"author":{"_account_id":782,"name":"John Garbutt","email":"john@johngarbutt.com","username":"johngarbutt"},"change_message_id":"a9534c431764b2b41c8979a63a7b64a5b655581f","unresolved":false,"context_lines":[{"line_number":370,"context_line":""},{"line_number":371,"context_line":""},{"line_number":372,"context_line":"@base.NovaObjectRegistry.register"},{"line_number":373,"context_line":"class ServiceStatusNotification(notification.NotificationBase):"},{"line_number":374,"context_line":"    # Version 1.0: Initial version"},{"line_number":375,"context_line":"    VERSION \u003d \u00271.0\u0027"},{"line_number":376,"context_line":""}],"source_content_type":"text/x-python","patch_set":25,"id":"fa69d971_423bb6d1","line":373,"in_reply_to":"fa69d971_7b96b295","updated":"2016-01-08 15:20:51.000000000","message":"Lets scrap that idea for now, its nice that its local to the service object here.","commit_id":"36b21df39e8b8014a3443245b9a2e4d46ab32ccd"},{"author":{"_account_id":782,"name":"John Garbutt","email":"john@johngarbutt.com","username":"johngarbutt"},"change_message_id":"728249ba6e3a490733ba0fc3526f5fbf91adda69","unresolved":false,"context_lines":[{"line_number":406,"context_line":"        \u0027last_seen_up\u0027: fields.DateTimeField(nullable\u003dTrue),"},{"line_number":407,"context_line":"        \u0027forced_down\u0027: fields.BooleanField(),"},{"line_number":408,"context_line":"        \u0027version\u0027: fields.IntegerField(),"},{"line_number":409,"context_line":"    }"}],"source_content_type":"text/x-python","patch_set":25,"id":"fa69d971_fbcf02b1","line":409,"updated":"2016-01-08 13:39:25.000000000","message":"as per the other my previous comment, I think an override here, so its clear where you pass service, would help, I think.","commit_id":"36b21df39e8b8014a3443245b9a2e4d46ab32ccd"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"af1e3aedbfb0bff1f5e97f985cc081fc74290d9a","unresolved":false,"context_lines":[{"line_number":406,"context_line":"        \u0027last_seen_up\u0027: fields.DateTimeField(nullable\u003dTrue),"},{"line_number":407,"context_line":"        \u0027forced_down\u0027: fields.BooleanField(),"},{"line_number":408,"context_line":"        \u0027version\u0027: fields.IntegerField(),"},{"line_number":409,"context_line":"    }"}],"source_content_type":"text/x-python","patch_set":25,"id":"fa69d971_9fba60e0","line":409,"in_reply_to":"fa69d971_fbcf02b1","updated":"2016-01-09 12:42:34.000000000","message":"Done","commit_id":"36b21df39e8b8014a3443245b9a2e4d46ab32ccd"},{"author":{"_account_id":782,"name":"John Garbutt","email":"john@johngarbutt.com","username":"johngarbutt"},"change_message_id":"12fa670aebe89b6ee60d1922c1b7b91564087050","unresolved":false,"context_lines":[{"line_number":285,"context_line":"        if ({\u0027disabled\u0027, \u0027disabled_reason\u0027, \u0027forced_down\u0027} \u0026"},{"line_number":286,"context_line":"                set(updates.keys())):"},{"line_number":287,"context_line":"            payload \u003d ServiceStatusPayload()"},{"line_number":288,"context_line":"            payload.populate_schema(service\u003dself)"},{"line_number":289,"context_line":"            ServiceStatusNotification("},{"line_number":290,"context_line":"                publisher\u003dnotification.NotificationPublisher.from_service_obj("},{"line_number":291,"context_line":"                    self),"}],"source_content_type":"text/x-python","patch_set":30,"id":"da6ed579_2d4a3ac6","line":288,"updated":"2016-01-13 11:51:34.000000000","message":"its tempting to tweak the constructor, or maybe add a from_service_obj call instead?","commit_id":"babfe5b11605c3807627d303b857dc6044ae8219"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"bfd969337b3794aff0045e5b4a8932849b1b7b9d","unresolved":false,"context_lines":[{"line_number":285,"context_line":"        if ({\u0027disabled\u0027, \u0027disabled_reason\u0027, \u0027forced_down\u0027} \u0026"},{"line_number":286,"context_line":"                set(updates.keys())):"},{"line_number":287,"context_line":"            payload \u003d ServiceStatusPayload()"},{"line_number":288,"context_line":"            payload.populate_schema(service\u003dself)"},{"line_number":289,"context_line":"            ServiceStatusNotification("},{"line_number":290,"context_line":"                publisher\u003dnotification.NotificationPublisher.from_service_obj("},{"line_number":291,"context_line":"                    self),"}],"source_content_type":"text/x-python","patch_set":30,"id":"da6ed579_82a68c0e","line":288,"in_reply_to":"da6ed579_2d4a3ac6","updated":"2016-01-13 15:06:04.000000000","message":"I tweaked the constructor.","commit_id":"babfe5b11605c3807627d303b857dc6044ae8219"},{"author":{"_account_id":782,"name":"John Garbutt","email":"john@johngarbutt.com","username":"johngarbutt"},"change_message_id":"12fa670aebe89b6ee60d1922c1b7b91564087050","unresolved":false,"context_lines":[{"line_number":409,"context_line":"        \u0027version\u0027: fields.IntegerField(),"},{"line_number":410,"context_line":"    }"},{"line_number":411,"context_line":""},{"line_number":412,"context_line":"    def populate_schema(self, service):"},{"line_number":413,"context_line":"        super(ServiceStatusPayload, self).populate_schema(service\u003dservice)"}],"source_content_type":"text/x-python","patch_set":30,"id":"da6ed579_edee628a","line":412,"updated":"2016-01-13 11:51:34.000000000","message":"Just had another idea, what if we add this class method instead?\n\n def from_service_obj(self, service):\n    payload \u003d ServiceStatusPayload()\n    payload.populate_schema(service)\n    return payload","commit_id":"babfe5b11605c3807627d303b857dc6044ae8219"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"bfd969337b3794aff0045e5b4a8932849b1b7b9d","unresolved":false,"context_lines":[{"line_number":409,"context_line":"        \u0027version\u0027: fields.IntegerField(),"},{"line_number":410,"context_line":"    }"},{"line_number":411,"context_line":""},{"line_number":412,"context_line":"    def populate_schema(self, service):"},{"line_number":413,"context_line":"        super(ServiceStatusPayload, self).populate_schema(service\u003dservice)"}],"source_content_type":"text/x-python","patch_set":30,"id":"da6ed579_228d607b","line":412,"in_reply_to":"da6ed579_edee628a","updated":"2016-01-13 15:06:04.000000000","message":"I tweaked the constructor.","commit_id":"babfe5b11605c3807627d303b857dc6044ae8219"},{"author":{"_account_id":2271,"name":"Michael Still","email":"mikal@stillhq.com","username":"mikalstill"},"change_message_id":"745dd39af936255f7f1a33476d73b90a64ff1eeb","unresolved":false,"context_lines":[{"line_number":288,"context_line":"        # is always dirty, which would cause that nova sends notification on"},{"line_number":289,"context_line":"        # every other field change. See the comment in save() too."},{"line_number":290,"context_line":"        if ({\u0027disabled\u0027, \u0027disabled_reason\u0027, \u0027forced_down\u0027} \u0026"},{"line_number":291,"context_line":"                set(updates.keys())):"},{"line_number":292,"context_line":"            payload \u003d ServiceStatusPayload(self)"},{"line_number":293,"context_line":"            ServiceStatusNotification("},{"line_number":294,"context_line":"                publisher\u003dnotification.NotificationPublisher.from_service_obj("}],"source_content_type":"text/x-python","patch_set":36,"id":"9a68dd71_81ad8e33","line":291,"updated":"2016-01-20 14:05:02.000000000","message":"This syntax is entirely new to me, and I wonder if that means it will be confusing to others. Are there any other examples in nova of this syntax being used?\n\nHow about using intersection instead? Something like:\n\n set(keys).intersection({\u0027disabled\u0027, \u0027disabled_reason\u0027, \u0027forced_down\u0027})","commit_id":"9d3dcc063de33882527ce4184d89fde24f0ce8dd"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"af5f6d24b12ed4b37ccdf14c9c1a2c009e487d52","unresolved":false,"context_lines":[{"line_number":288,"context_line":"        # is always dirty, which would cause that nova sends notification on"},{"line_number":289,"context_line":"        # every other field change. See the comment in save() too."},{"line_number":290,"context_line":"        if ({\u0027disabled\u0027, \u0027disabled_reason\u0027, \u0027forced_down\u0027} \u0026"},{"line_number":291,"context_line":"                set(updates.keys())):"},{"line_number":292,"context_line":"            payload \u003d ServiceStatusPayload(self)"},{"line_number":293,"context_line":"            ServiceStatusNotification("},{"line_number":294,"context_line":"                publisher\u003dnotification.NotificationPublisher.from_service_obj("}],"source_content_type":"text/x-python","patch_set":36,"id":"9a68dd71_5331a7eb","line":291,"in_reply_to":"9a68dd71_81ad8e33","updated":"2016-01-20 14:33:58.000000000","message":"I changed it to the more chatty version you suggested. For me it is a known syntax but yes I can imagine that it looks confusing to others.","commit_id":"9d3dcc063de33882527ce4184d89fde24f0ce8dd"}],"nova/tests/functional/api_sample_tests/test_services.py":[{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"034ce5b6340227b1386edb1e6cfea355045393af","unresolved":false,"context_lines":[{"line_number":68,"context_line":"        self.assertEqual(1, len(fake_notifier.NOTIFICATIONS))"},{"line_number":69,"context_line":"        payload \u003d fake_notifier.NOTIFICATIONS[0].payload"},{"line_number":70,"context_line":"        service \u003d payload[\u0027nova_object.data\u0027][\u0027service\u0027]"},{"line_number":71,"context_line":"        for key, value in kwargs.items():"},{"line_number":72,"context_line":"            self.assertEqual(value, service[\u0027nova_object.data\u0027][key],"},{"line_number":73,"context_line":"                             \u0027Mismatch in key %s\u0027 % key)"},{"line_number":74,"context_line":""}],"source_content_type":"text/x-python","patch_set":8,"id":"ba8a016a_dff1c0ce","line":71,"updated":"2015-11-23 21:12:26.000000000","message":"Isn\u0027t this the equivalent of an assertDictEqual? (or just an assertEqual?)","commit_id":"de9a80efaffa77b73401a4024d83e04c4c278ad3"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"6853b14a77d9b8b8dabc5e239be147c420a5b826","unresolved":false,"context_lines":[{"line_number":68,"context_line":"        self.assertEqual(1, len(fake_notifier.NOTIFICATIONS))"},{"line_number":69,"context_line":"        payload \u003d fake_notifier.NOTIFICATIONS[0].payload"},{"line_number":70,"context_line":"        service \u003d payload[\u0027nova_object.data\u0027][\u0027service\u0027]"},{"line_number":71,"context_line":"        for key, value in kwargs.items():"},{"line_number":72,"context_line":"            self.assertEqual(value, service[\u0027nova_object.data\u0027][key],"},{"line_number":73,"context_line":"                             \u0027Mismatch in key %s\u0027 % key)"},{"line_number":74,"context_line":""}],"source_content_type":"text/x-python","patch_set":8,"id":"9a8ffd7b_0e54ccc7","line":71,"in_reply_to":"ba8a016a_dff1c0ce","updated":"2015-11-26 17:29:22.000000000","message":"No as it only checks those keys in the payload that are specified in the kwargs. Anyhow as soon as the TODO above solved which is in the next patch of the series this code is replaced with sample file matching which is more complete verification","commit_id":"de9a80efaffa77b73401a4024d83e04c4c278ad3"},{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"034ce5b6340227b1386edb1e6cfea355045393af","unresolved":false,"context_lines":[{"line_number":82,"context_line":"                \u0027status\u0027: \u0027disabled\u0027,"},{"line_number":83,"context_line":"                \u0027state\u0027: \u0027up\u0027}"},{"line_number":84,"context_line":"        subs.update(self._get_regexes())"},{"line_number":85,"context_line":"        self._verify_response(\u0027services-list-get-resp\u0027, subs, response, 200)"},{"line_number":86,"context_line":""},{"line_number":87,"context_line":"    def test_service_enable(self):"},{"line_number":88,"context_line":"        \"\"\"Enable an existing agent build.\"\"\""}],"source_content_type":"text/x-python","patch_set":8,"id":"ba8a016a_15dc07e3","line":85,"updated":"2015-11-23 21:12:26.000000000","message":"Do we want to assert that no notification was sent here? Just to make sure the updates.keys() check works so we know we\u0027re not always sending notifications.","commit_id":"de9a80efaffa77b73401a4024d83e04c4c278ad3"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"6853b14a77d9b8b8dabc5e239be147c420a5b826","unresolved":false,"context_lines":[{"line_number":82,"context_line":"                \u0027status\u0027: \u0027disabled\u0027,"},{"line_number":83,"context_line":"                \u0027state\u0027: \u0027up\u0027}"},{"line_number":84,"context_line":"        subs.update(self._get_regexes())"},{"line_number":85,"context_line":"        self._verify_response(\u0027services-list-get-resp\u0027, subs, response, 200)"},{"line_number":86,"context_line":""},{"line_number":87,"context_line":"    def test_service_enable(self):"},{"line_number":88,"context_line":"        \"\"\"Enable an existing agent build.\"\"\""}],"source_content_type":"text/x-python","patch_set":8,"id":"9a8ffd7b_e4e409e2","line":85,"in_reply_to":"ba8a016a_15dc07e3","updated":"2015-11-26 17:29:22.000000000","message":"Done","commit_id":"de9a80efaffa77b73401a4024d83e04c4c278ad3"},{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"0970fc756a6f6dcd82fbef6cb22145fc9e04761c","unresolved":false,"context_lines":[{"line_number":88,"context_line":"    def test_service_enable(self):"},{"line_number":89,"context_line":"        \"\"\"Enable an existing agent build.\"\"\""},{"line_number":90,"context_line":"        subs \u003d {\"host\": \"host1\","},{"line_number":91,"context_line":"                \u0027binary\u0027: \u0027nova-compute\u0027}"},{"line_number":92,"context_line":"        response \u003d self._do_put(\u0027os-services/enable\u0027,"},{"line_number":93,"context_line":"                                \u0027service-enable-put-req\u0027, subs,"},{"line_number":94,"context_line":"                                api_version\u003dself.request_api_version)"}],"source_content_type":"text/x-python","patch_set":18,"id":"7a740942_88e79dab","line":91,"updated":"2015-12-10 17:03:19.000000000","message":"do we want to verify these are part of the notification payload too? Or do we not want to get too specific with what\u0027s in the payload?","commit_id":"b84f074bb9725eb5ed3c4c311ccef6f55abb0010"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"ccc7efd986c98d562d4f4339059d63d89de7c112","unresolved":false,"context_lines":[{"line_number":88,"context_line":"    def test_service_enable(self):"},{"line_number":89,"context_line":"        \"\"\"Enable an existing agent build.\"\"\""},{"line_number":90,"context_line":"        subs \u003d {\"host\": \"host1\","},{"line_number":91,"context_line":"                \u0027binary\u0027: \u0027nova-compute\u0027}"},{"line_number":92,"context_line":"        response \u003d self._do_put(\u0027os-services/enable\u0027,"},{"line_number":93,"context_line":"                                \u0027service-enable-put-req\u0027, subs,"},{"line_number":94,"context_line":"                                api_version\u003dself.request_api_version)"}],"source_content_type":"text/x-python","patch_set":18,"id":"7a740942_e7ccd26b","line":91,"in_reply_to":"7a740942_88e79dab","updated":"2015-12-14 10:36:50.000000000","message":"Every field will be verified when the TODO on L66 is implemented. Which is actually the next commit in the chain https://review.openstack.org/#/c/248167/","commit_id":"b84f074bb9725eb5ed3c4c311ccef6f55abb0010"}],"nova/tests/unit/api/openstack/compute/test_services.py":[{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"b1c5574f611b474e4b85729a5f60cef044a83ed2","unresolved":false,"context_lines":[{"line_number":146,"context_line":"        if service is None:"},{"line_number":147,"context_line":"            raise exception.ServiceNotFound(service_id\u003dservice_id)"},{"line_number":148,"context_line":"        service \u003d copy.deepcopy(service)"},{"line_number":149,"context_line":"        service.update(values)"},{"line_number":150,"context_line":"        return service"},{"line_number":151,"context_line":"    return service_update"},{"line_number":152,"context_line":""}],"source_content_type":"text/x-python","patch_set":19,"id":"7a740942_178a571b","line":149,"updated":"2015-12-14 17:37:46.000000000","message":"I guess I was kind of ignoring this before, but why does this need to be changed? It looks like values isn\u0027t used anywhere even though it\u0027s passed in, but now you\u0027re starting to use it. Nothing wrong with it if it\u0027s needed, just seems kinda unrelated to me. Also I don\u0027t see you explicitly calling service_update anywhere unless it\u0027s mocked, upon which you\u0027re changing the return value anyways.","commit_id":"228d175e41460412a6c748513f3ecac979a1f94c"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"020b631db8b565a98a413d977321056fc5b07a26","unresolved":false,"context_lines":[{"line_number":146,"context_line":"        if service is None:"},{"line_number":147,"context_line":"            raise exception.ServiceNotFound(service_id\u003dservice_id)"},{"line_number":148,"context_line":"        service \u003d copy.deepcopy(service)"},{"line_number":149,"context_line":"        service.update(values)"},{"line_number":150,"context_line":"        return service"},{"line_number":151,"context_line":"    return service_update"},{"line_number":152,"context_line":""}],"source_content_type":"text/x-python","patch_set":19,"id":"5a710552_b950bf5f","line":149,"in_reply_to":"5a710552_7fb00dde","updated":"2015-12-15 17:34:28.000000000","message":"I was mistaken. This is used not only by the unit test but also the functional test. There the tests are call update on the fake service and expects that the notification are sent with the updated value. We need to update the service dict  here as the Service object refresh its value with the return value of the db call and the notification is send with the refreshed value. \nHowever if we change the service dict here without copying it first then that is changing the global fake_service_list which makes the subsequent test to fail. See the functional test result of the patch set 20 for reference.\nI adding this back in patch set 21 to make have a well behaving fake for testing.","commit_id":"228d175e41460412a6c748513f3ecac979a1f94c"},{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"9aa4b2bfd620ed5abae61aeed399492ee80c2004","unresolved":false,"context_lines":[{"line_number":146,"context_line":"        if service is None:"},{"line_number":147,"context_line":"            raise exception.ServiceNotFound(service_id\u003dservice_id)"},{"line_number":148,"context_line":"        service \u003d copy.deepcopy(service)"},{"line_number":149,"context_line":"        service.update(values)"},{"line_number":150,"context_line":"        return service"},{"line_number":151,"context_line":"    return service_update"},{"line_number":152,"context_line":""}],"source_content_type":"text/x-python","patch_set":19,"id":"5a710552_54f2c2d3","line":149,"in_reply_to":"5a710552_b950bf5f","updated":"2015-12-15 17:42:32.000000000","message":"Got it. So we can\u0027t just make save a noop anymore, we are actually expecting something out of the return. I figured it wasn\u0027t used because you didn\u0027t change any of the unit tests, but I didn\u0027t realize the functional tests used something that was so far down in the unit tests :/.","commit_id":"228d175e41460412a6c748513f3ecac979a1f94c"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"28c23dff707d8ce3a53d3eccdf8d60bce402dd3b","unresolved":false,"context_lines":[{"line_number":146,"context_line":"        if service is None:"},{"line_number":147,"context_line":"            raise exception.ServiceNotFound(service_id\u003dservice_id)"},{"line_number":148,"context_line":"        service \u003d copy.deepcopy(service)"},{"line_number":149,"context_line":"        service.update(values)"},{"line_number":150,"context_line":"        return service"},{"line_number":151,"context_line":"    return service_update"},{"line_number":152,"context_line":""}],"source_content_type":"text/x-python","patch_set":19,"id":"5a710552_7fb00dde","line":149,"in_reply_to":"7a740942_178a571b","updated":"2015-12-15 12:23:12.000000000","message":"You are right. It is not necessary.","commit_id":"228d175e41460412a6c748513f3ecac979a1f94c"}],"nova/tests/unit/objects/test_objects.py":[{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"b1fb552628691d68d297a08dcde442d5e1880ddc","unresolved":false,"context_lines":[{"line_number":1178,"context_line":"    \u0027EC2InstanceMapping\u0027: \u00271.0-a4556eb5c5e94c045fe84f49cf71644f\u0027,"},{"line_number":1179,"context_line":"    \u0027EC2SnapshotMapping\u0027: \u00271.0-47e7ddabe1af966dce0cfd0ed6cd7cd1\u0027,"},{"line_number":1180,"context_line":"    \u0027EC2VolumeMapping\u0027: \u00271.0-5b713751d6f97bad620f3378a521020d\u0027,"},{"line_number":1181,"context_line":"    \u0027EventType\u0027: \u00271.0-ae96297716868f2c140a2498b37c44d8\u0027,"},{"line_number":1182,"context_line":"    \u0027FixedIP\u0027: \u00271.14-53e1c10b539f1a82fe83b1af4720efae\u0027,"},{"line_number":1183,"context_line":"    \u0027FixedIPList\u0027: \u00271.14-87a39361c8f08f059004d6b15103cdfd\u0027,"},{"line_number":1184,"context_line":"    \u0027Flavor\u0027: \u00271.1-b6bb7a730a79d720344accefafacf7ee\u0027,"}],"source_content_type":"text/x-python","patch_set":3,"id":"ba8a016a_8e4eb06d","line":1181,"updated":"2015-11-17 22:13:28.000000000","message":"This will get moved up to the parent patch","commit_id":"25b774c7a60f0400cd69149e496c27bb11cad1b0"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"6a3b68fb410d8c71c29a4c660cf92b86298b6e91","unresolved":false,"context_lines":[{"line_number":1178,"context_line":"    \u0027EC2InstanceMapping\u0027: \u00271.0-a4556eb5c5e94c045fe84f49cf71644f\u0027,"},{"line_number":1179,"context_line":"    \u0027EC2SnapshotMapping\u0027: \u00271.0-47e7ddabe1af966dce0cfd0ed6cd7cd1\u0027,"},{"line_number":1180,"context_line":"    \u0027EC2VolumeMapping\u0027: \u00271.0-5b713751d6f97bad620f3378a521020d\u0027,"},{"line_number":1181,"context_line":"    \u0027EventType\u0027: \u00271.0-ae96297716868f2c140a2498b37c44d8\u0027,"},{"line_number":1182,"context_line":"    \u0027FixedIP\u0027: \u00271.14-53e1c10b539f1a82fe83b1af4720efae\u0027,"},{"line_number":1183,"context_line":"    \u0027FixedIPList\u0027: \u00271.14-87a39361c8f08f059004d6b15103cdfd\u0027,"},{"line_number":1184,"context_line":"    \u0027Flavor\u0027: \u00271.1-b6bb7a730a79d720344accefafacf7ee\u0027,"}],"source_content_type":"text/x-python","patch_set":3,"id":"ba8a016a_d97692a3","line":1181,"in_reply_to":"ba8a016a_8e4eb06d","updated":"2015-11-18 16:50:44.000000000","message":"Done","commit_id":"25b774c7a60f0400cd69149e496c27bb11cad1b0"},{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"b1fb552628691d68d297a08dcde442d5e1880ddc","unresolved":false,"context_lines":[{"line_number":1214,"context_line":"    \u0027MigrationList\u0027: \u00271.2-02c0ec0c50b75ca86a2a74c5e8c911cc\u0027,"},{"line_number":1215,"context_line":"    \u0027MonitorMetric\u0027: \u00271.1-53b1db7c4ae2c531db79761e7acc52ba\u0027,"},{"line_number":1216,"context_line":"    \u0027MonitorMetricList\u0027: \u00271.1-15ecf022a68ddbb8c2a6739cfc9f8f5e\u0027,"},{"line_number":1217,"context_line":"    \u0027NotificationBase\u0027: \u00271.0-db408b3f623d468d0cd4048300399fae\u0027,"},{"line_number":1218,"context_line":"    \u0027NotificationPayloadBase\u0027: \u00271.0-77509ea1ea0dd750d5864b9bd87d3f9d\u0027,"},{"line_number":1219,"context_line":"    \u0027NUMACell\u0027: \u00271.2-74fc993ac5c83005e76e34e8487f1c05\u0027,"},{"line_number":1220,"context_line":"    \u0027NUMAPagesTopology\u0027: \u00271.0-c71d86317283266dc8364c149155e48e\u0027,"}],"source_content_type":"text/x-python","patch_set":3,"id":"ba8a016a_ae513410","line":1217,"updated":"2015-11-17 22:13:28.000000000","message":"These 2 will also move up","commit_id":"25b774c7a60f0400cd69149e496c27bb11cad1b0"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"6a3b68fb410d8c71c29a4c660cf92b86298b6e91","unresolved":false,"context_lines":[{"line_number":1214,"context_line":"    \u0027MigrationList\u0027: \u00271.2-02c0ec0c50b75ca86a2a74c5e8c911cc\u0027,"},{"line_number":1215,"context_line":"    \u0027MonitorMetric\u0027: \u00271.1-53b1db7c4ae2c531db79761e7acc52ba\u0027,"},{"line_number":1216,"context_line":"    \u0027MonitorMetricList\u0027: \u00271.1-15ecf022a68ddbb8c2a6739cfc9f8f5e\u0027,"},{"line_number":1217,"context_line":"    \u0027NotificationBase\u0027: \u00271.0-db408b3f623d468d0cd4048300399fae\u0027,"},{"line_number":1218,"context_line":"    \u0027NotificationPayloadBase\u0027: \u00271.0-77509ea1ea0dd750d5864b9bd87d3f9d\u0027,"},{"line_number":1219,"context_line":"    \u0027NUMACell\u0027: \u00271.2-74fc993ac5c83005e76e34e8487f1c05\u0027,"},{"line_number":1220,"context_line":"    \u0027NUMAPagesTopology\u0027: \u00271.0-c71d86317283266dc8364c149155e48e\u0027,"}],"source_content_type":"text/x-python","patch_set":3,"id":"ba8a016a_f97b568a","line":1217,"in_reply_to":"ba8a016a_ae513410","updated":"2015-11-18 16:50:44.000000000","message":"Done","commit_id":"25b774c7a60f0400cd69149e496c27bb11cad1b0"}],"nova/tests/unit/objects/test_service.py":[{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"530c0349d3b2e589ae5a5892f7d3d08a6ca08b47","unresolved":false,"context_lines":[{"line_number":390,"context_line":""},{"line_number":391,"context_line":"class TestServiceStatusNotification(test.TestCase):"},{"line_number":392,"context_line":""},{"line_number":393,"context_line":"    @mock.patch(\u0027nova.objects.notification.NotificationBase.__init__\u0027)"},{"line_number":394,"context_line":"    @mock.patch(\u0027nova.objects.notification.NotificationBase.emit\u0027)"},{"line_number":395,"context_line":"    def _verify_notification(self, service_obj, mock_notification_emit,"},{"line_number":396,"context_line":"                             mock_notification_init):"}],"source_content_type":"text/x-python","patch_set":2,"id":"ba8a016a_e1ae7f97","line":393,"updated":"2015-11-17 16:55:11.000000000","message":"To me it just seems a little weird to be patching __init__... we may need to think about making a factory for creating notifications","commit_id":"a34f23cc87da5d702a34e0156c22970169e582d6"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"1c6fb3c3685e6c2bf22c9efddf844c9207854cae","unresolved":false,"context_lines":[{"line_number":390,"context_line":""},{"line_number":391,"context_line":"class TestServiceStatusNotification(test.TestCase):"},{"line_number":392,"context_line":""},{"line_number":393,"context_line":"    @mock.patch(\u0027nova.objects.notification.NotificationBase.__init__\u0027)"},{"line_number":394,"context_line":"    @mock.patch(\u0027nova.objects.notification.NotificationBase.emit\u0027)"},{"line_number":395,"context_line":"    def _verify_notification(self, service_obj, mock_notification_emit,"},{"line_number":396,"context_line":"                             mock_notification_init):"}],"source_content_type":"text/x-python","patch_set":2,"id":"ba8a016a_e41be619","line":393,"in_reply_to":"ba8a016a_e1ae7f97","updated":"2015-11-17 19:33:41.000000000","message":"Done","commit_id":"a34f23cc87da5d702a34e0156c22970169e582d6"},{"author":{"_account_id":1063,"name":"Ed Leafe","email":"ed@leafe.com","username":"ed-leafe"},"change_message_id":"2f340dcbe8513a6bccf749a0a085a3a4ec2a6dd2","unresolved":false,"context_lines":[{"line_number":27,"context_line":"from nova import test"},{"line_number":28,"context_line":"from nova.tests.unit.objects import test_compute_node"},{"line_number":29,"context_line":"from nova.tests.unit.objects import test_objects"},{"line_number":30,"context_line":""},{"line_number":31,"context_line":""},{"line_number":32,"context_line":"NOW \u003d timeutils.utcnow().replace(microsecond\u003d0)"},{"line_number":33,"context_line":"fake_service \u003d {"}],"source_content_type":"text/x-python","patch_set":7,"id":"ba8a016a_a0998621","line":30,"updated":"2015-11-20 22:56:45.000000000","message":"Nit: unrelated whitespace change","commit_id":"e4c8f3a24efc24faa4055129ac6d71a6cde2e8f4"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"6a292e9118cab97ad54af762fa65083f003803eb","unresolved":false,"context_lines":[{"line_number":27,"context_line":"from nova import test"},{"line_number":28,"context_line":"from nova.tests.unit.objects import test_compute_node"},{"line_number":29,"context_line":"from nova.tests.unit.objects import test_objects"},{"line_number":30,"context_line":""},{"line_number":31,"context_line":""},{"line_number":32,"context_line":"NOW \u003d timeutils.utcnow().replace(microsecond\u003d0)"},{"line_number":33,"context_line":"fake_service \u003d {"}],"source_content_type":"text/x-python","patch_set":7,"id":"ba8a016a_2417dcee","line":30,"in_reply_to":"ba8a016a_a0998621","updated":"2015-11-21 21:24:27.000000000","message":"Done","commit_id":"e4c8f3a24efc24faa4055129ac6d71a6cde2e8f4"},{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"14b2a3e07f1fd20bcdd9bd9fb38b37d5e42d3bf9","unresolved":false,"context_lines":[{"line_number":369,"context_line":"        self.assertEqual(fake_version, obj.version)"},{"line_number":370,"context_line":""},{"line_number":371,"context_line":"    @mock.patch(\u0027nova.objects.notification.NotificationBase.emit\u0027)"},{"line_number":372,"context_line":"    def test_save_noop_with_only_version(self, mock_notification):"},{"line_number":373,"context_line":"        o \u003d objects.Service(context\u003dmock.sentinel.context,"},{"line_number":374,"context_line":"                            id\u003dfake_service[\u0027id\u0027])"},{"line_number":375,"context_line":"        o.obj_reset_changes([\u0027id\u0027])"}],"source_content_type":"text/x-python","patch_set":17,"id":"7a740942_492fe93e","line":372,"updated":"2015-12-08 22:41:26.000000000","message":"You shouldn\u0027t need to mock this out, because emit shouldn\u0027t be called when only the version is changed right?","commit_id":"e82106f5f1f7317ff8490c2e557442dc4d4bd7da"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"c475d295f2a36453d9fe14f2a143fdc06d771817","unresolved":false,"context_lines":[{"line_number":369,"context_line":"        self.assertEqual(fake_version, obj.version)"},{"line_number":370,"context_line":""},{"line_number":371,"context_line":"    @mock.patch(\u0027nova.objects.notification.NotificationBase.emit\u0027)"},{"line_number":372,"context_line":"    def test_save_noop_with_only_version(self, mock_notification):"},{"line_number":373,"context_line":"        o \u003d objects.Service(context\u003dmock.sentinel.context,"},{"line_number":374,"context_line":"                            id\u003dfake_service[\u0027id\u0027])"},{"line_number":375,"context_line":"        o.obj_reset_changes([\u0027id\u0027])"}],"source_content_type":"text/x-python","patch_set":17,"id":"7a740942_fa84f90b","line":372,"in_reply_to":"7a740942_492fe93e","updated":"2015-12-10 13:42:04.000000000","message":"The name of the test is a bit misleading as from L381 it actually tests that save() is not a noop if something else than version is changed.\nI moved the mocking of emit to L381 to avoid even more confusion. :)","commit_id":"e82106f5f1f7317ff8490c2e557442dc4d4bd7da"},{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"14b2a3e07f1fd20bcdd9bd9fb38b37d5e42d3bf9","unresolved":false,"context_lines":[{"line_number":436,"context_line":"        service_obj \u003d objects.Service(context\u003dmock.sentinel.context,"},{"line_number":437,"context_line":"                                      id\u003dfake_service[\u0027id\u0027])"},{"line_number":438,"context_line":""},{"line_number":439,"context_line":"        service_obj.obj_reset_changes([\u0027version\u0027])"},{"line_number":440,"context_line":"        mock_db_service_update.return_value \u003d fake_service"},{"line_number":441,"context_line":""},{"line_number":442,"context_line":"        for key, value in {\u0027report_count\u0027: 13,"}],"source_content_type":"text/x-python","patch_set":17,"id":"7a740942_a9ebedda","line":439,"updated":"2015-12-08 22:41:26.000000000","message":"You shouldn\u0027t be manually resetting the changes to version in order to make sure it\u0027s updated without a notification. That means in the normal code path, it will be emitted when anything changes (unless we feel like manually resetting the changes on version).","commit_id":"e82106f5f1f7317ff8490c2e557442dc4d4bd7da"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"c475d295f2a36453d9fe14f2a143fdc06d771817","unresolved":false,"context_lines":[{"line_number":436,"context_line":"        service_obj \u003d objects.Service(context\u003dmock.sentinel.context,"},{"line_number":437,"context_line":"                                      id\u003dfake_service[\u0027id\u0027])"},{"line_number":438,"context_line":""},{"line_number":439,"context_line":"        service_obj.obj_reset_changes([\u0027version\u0027])"},{"line_number":440,"context_line":"        mock_db_service_update.return_value \u003d fake_service"},{"line_number":441,"context_line":""},{"line_number":442,"context_line":"        for key, value in {\u0027report_count\u0027: 13,"}],"source_content_type":"text/x-python","patch_set":17,"id":"7a740942_30c7fd13","line":439,"in_reply_to":"7a740942_a9ebedda","updated":"2015-12-10 13:42:04.000000000","message":"You are right.","commit_id":"e82106f5f1f7317ff8490c2e557442dc4d4bd7da"},{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"0970fc756a6f6dcd82fbef6cb22145fc9e04761c","unresolved":false,"context_lines":[{"line_number":380,"context_line":"        with ("},{"line_number":381,"context_line":"                mock.patch(\u0027nova.db.service_update\u0027)"},{"line_number":382,"context_line":"        ) as mock_update, ("},{"line_number":383,"context_line":"                mock.patch(\u0027nova.objects.notification.NotificationBase.emit\u0027)):"},{"line_number":384,"context_line":"            mock_update.return_value \u003d fake_service"},{"line_number":385,"context_line":"            o.save()"},{"line_number":386,"context_line":"            mock_update.assert_called_once_with("}],"source_content_type":"text/x-python","patch_set":18,"id":"7a740942_49e77712","line":383,"updated":"2015-12-10 17:03:19.000000000","message":"now that we don\u0027t fire a notification on only version changing, this shouldn\u0027t need to be mocked out anymore. Unless I\u0027m reading this wrong, because in this case, host is the changed value, which is something the service notification isn\u0027t used on.","commit_id":"b84f074bb9725eb5ed3c4c311ccef6f55abb0010"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"ccc7efd986c98d562d4f4339059d63d89de7c112","unresolved":false,"context_lines":[{"line_number":380,"context_line":"        with ("},{"line_number":381,"context_line":"                mock.patch(\u0027nova.db.service_update\u0027)"},{"line_number":382,"context_line":"        ) as mock_update, ("},{"line_number":383,"context_line":"                mock.patch(\u0027nova.objects.notification.NotificationBase.emit\u0027)):"},{"line_number":384,"context_line":"            mock_update.return_value \u003d fake_service"},{"line_number":385,"context_line":"            o.save()"},{"line_number":386,"context_line":"            mock_update.assert_called_once_with("}],"source_content_type":"text/x-python","patch_set":18,"id":"7a740942_eac6d998","line":383,"in_reply_to":"7a740942_49e77712","updated":"2015-12-14 10:36:50.000000000","message":"I think I need some vacation time, as I missed this again. :)\nAnyhow I simply removed the emit mock and it passes so you are totally right.","commit_id":"b84f074bb9725eb5ed3c4c311ccef6f55abb0010"},{"author":{"_account_id":11803,"name":"Ryan Rossiter","email":"rlrossit@us.ibm.com","username":"rlrossiter"},"change_message_id":"0970fc756a6f6dcd82fbef6cb22145fc9e04761c","unresolved":false,"context_lines":[{"line_number":415,"context_line":"            mock.sentinel.context)"},{"line_number":416,"context_line":""},{"line_number":417,"context_line":"    @mock.patch(\u0027nova.db.service_update\u0027)"},{"line_number":418,"context_line":"    def test_service_update_with_notification(self, mock_db_service_update):"},{"line_number":419,"context_line":"        service_obj \u003d objects.Service(context\u003dmock.sentinel.context,"},{"line_number":420,"context_line":"                                      id\u003dfake_service[\u0027id\u0027])"},{"line_number":421,"context_line":"        mock_db_service_update.return_value \u003d fake_service"}],"source_content_type":"text/x-python","patch_set":18,"id":"7a740942_29a54b46","line":418,"updated":"2015-12-10 17:03:19.000000000","message":"These 2 tests are compact and very good!","commit_id":"b84f074bb9725eb5ed3c4c311ccef6f55abb0010"}],"releasenotes/notes/service-status-notification-e137297f5d5aa45d.yaml":[{"author":{"_account_id":782,"name":"John Garbutt","email":"john@johngarbutt.com","username":"johngarbutt"},"change_message_id":"12fa670aebe89b6ee60d1922c1b7b91564087050","unresolved":false,"context_lines":[{"line_number":1,"context_line":"---"},{"line_number":2,"context_line":"features:"},{"line_number":3,"context_line":"  - A new service.status notification has been introduced. "},{"line_number":4,"context_line":"    When the status of the Service object is changed nova will "},{"line_number":5,"context_line":"    send a new service.update notification with versioned payload "},{"line_number":6,"context_line":"    according to bp versioned-notification-api."}],"source_content_type":"text/x-yaml","patch_set":30,"id":"da6ed579_8dc6c647","line":3,"updated":"2016-01-13 11:51:34.000000000","message":"Nit: whitespace could be removed here.\n\nNit: maybe s/notification has/versioned notification has/?","commit_id":"babfe5b11605c3807627d303b857dc6044ae8219"},{"author":{"_account_id":9708,"name":"Balazs Gibizer","display_name":"gibi","email":"gibizer@gmail.com","username":"gibi"},"change_message_id":"bfd969337b3794aff0045e5b4a8932849b1b7b9d","unresolved":false,"context_lines":[{"line_number":1,"context_line":"---"},{"line_number":2,"context_line":"features:"},{"line_number":3,"context_line":"  - A new service.status notification has been introduced. "},{"line_number":4,"context_line":"    When the status of the Service object is changed nova will "},{"line_number":5,"context_line":"    send a new service.update notification with versioned payload "},{"line_number":6,"context_line":"    according to bp versioned-notification-api."}],"source_content_type":"text/x-yaml","patch_set":30,"id":"da6ed579_4256545d","line":3,"in_reply_to":"da6ed579_8dc6c647","updated":"2016-01-13 15:06:04.000000000","message":"Done","commit_id":"babfe5b11605c3807627d303b857dc6044ae8219"}]}
