)]}'
{"/PATCHSET_LEVEL":[{"author":{"_account_id":4690,"name":"melanie witt","display_name":"melwitt","email":"melwittt@gmail.com","username":"melwitt"},"change_message_id":"cbfc029837fec00b4cd581fc65c3c6f6d35a6258","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":1,"id":"975cf56c_8a55f9f9","updated":"2026-02-12 00:00:17.000000000","message":"recheck ModuleNotFoundError: No module named \u0027pkg_resources\u0027","commit_id":"1419ee60398be73cd39cffc4a72e16a4eab124d8"},{"author":{"_account_id":7166,"name":"Sylvain Bauza","email":"sbauza@redhat.com","username":"sbauza"},"change_message_id":"7d11bf413a8ede4eb6de194685b6f77d2d8b5920","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":1,"id":"f0b1369e_db0f63c3","updated":"2026-02-16 16:06:00.000000000","message":"wfm, thanks for the follow-up","commit_id":"1419ee60398be73cd39cffc4a72e16a4eab124d8"},{"author":{"_account_id":7166,"name":"Sylvain Bauza","email":"sbauza@redhat.com","username":"sbauza"},"change_message_id":"20c1b44f8ac31ad9df6ec067febf66cad59757b1","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":2,"id":"8acdd159_f27de6e3","updated":"2026-02-19 16:06:06.000000000","message":"I\u0027m a bit lost with the field envelope format we have : if that\u0027s only nova which sets its value from Barbican encoded in bytes, let\u0027s pop it as bytes too so that can be idempotent.\nThat said, I understand that we need to decode the formatting before writing it into the libvirt API, right, so that has to be some helper if we want to","commit_id":"30ee238b7293ff3e16017823f530715b1b64f541"},{"author":{"_account_id":11604,"name":"sean mooney","email":"smooney@redhat.com","username":"sean-k-mooney"},"change_message_id":"fe2c4ea9d8d08d2a04f9931caba7ac2d8ea5401c","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":3,"id":"6cbfc6f0_b0814a49","updated":"2026-02-25 20:24:44.000000000","message":"+1 mainly because i have not been following this closely and i have not fully loaded context on  it","commit_id":"e5a3f73368795b3db3f26a3feb99b3a2bc8d3f91"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"c1dfa6b91929bea2b2579ba46eea1f64ed05f3bf","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":3,"id":"d4f2070d_3d62fe0d","updated":"2026-02-26 15:10:15.000000000","message":"If the consensus is that we need to add the typing to objects, then I\u0027ll +2 but I\u0027d really rather not.","commit_id":"e5a3f73368795b3db3f26a3feb99b3a2bc8d3f91"},{"author":{"_account_id":7166,"name":"Sylvain Bauza","email":"sbauza@redhat.com","username":"sbauza"},"change_message_id":"99a8658970b83a99da2878911af74a1181e318a3","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":3,"id":"3e916cfb_00d23271","updated":"2026-02-25 17:37:30.000000000","message":"OK, let\u0027s give it a spin.","commit_id":"e5a3f73368795b3db3f26a3feb99b3a2bc8d3f91"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"c778fd892b3237392c64049ca43ea19830ea1022","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":4,"id":"1061cc60_5873b4ea","updated":"2026-02-26 18:19:44.000000000","message":"Proxying bauzas\u0027 previous +2","commit_id":"afd8c5d7de1c05fa3609961600a4af1599fc6a3e"},{"author":{"_account_id":7166,"name":"Sylvain Bauza","email":"sbauza@redhat.com","username":"sbauza"},"change_message_id":"439e064e945dcdbb9b731c89b6085a91012d1149","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":5,"id":"1f4b8465_b73d7a4b","updated":"2026-02-27 09:45:21.000000000","message":"just a rebase","commit_id":"bfe5b7fd1425ce385a89c4afc0b51ffdb3b4484c"},{"author":{"_account_id":4690,"name":"melanie witt","display_name":"melwitt","email":"melwittt@gmail.com","username":"melwitt"},"change_message_id":"025126a97413682b6f0f34152dabe7115d41f581","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":5,"id":"b0f217d3_a15733e0","updated":"2026-02-27 00:48:02.000000000","message":"recheck /opt/stack/nova/roles/run-evacuate-hook/files/setup_evacuate_resources.sh: line 11: openstack: command not found","commit_id":"bfe5b7fd1425ce385a89c4afc0b51ffdb3b4484c"}],"nova/objects/migrate_data.py":[{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"ec6f67c103133cc7f8a80186eef0964756e05c58","unresolved":true,"context_lines":[{"line_number":409,"context_line":"        standard Base64 alphabet."},{"line_number":410,"context_line":"        \"\"\""},{"line_number":411,"context_line":"        if isinstance(value, bytes):"},{"line_number":412,"context_line":"            value \u003d value.decode(encoding\u003d\u0027ascii\u0027)"},{"line_number":413,"context_line":"        self.vtpm_secret_value \u003d value"},{"line_number":414,"context_line":""},{"line_number":415,"context_line":""}],"source_content_type":"text/x-python","patch_set":2,"id":"01e14775_3afa42ad","line":412,"updated":"2026-02-19 15:29:36.000000000","message":"Hmm, why this? Doing this makes it more ambiguous (IMHO) in that we should expect bytes in/out only, since we\u0027re using bytes everywhere _but_ the object, no? I assume you added this for a reason, but this would let me send a poop emoji (i.e. not ascii) if I pass a str here.","commit_id":"30ee238b7293ff3e16017823f530715b1b64f541"},{"author":{"_account_id":7166,"name":"Sylvain Bauza","email":"sbauza@redhat.com","username":"sbauza"},"change_message_id":"20c1b44f8ac31ad9df6ec067febf66cad59757b1","unresolved":true,"context_lines":[{"line_number":409,"context_line":"        standard Base64 alphabet."},{"line_number":410,"context_line":"        \"\"\""},{"line_number":411,"context_line":"        if isinstance(value, bytes):"},{"line_number":412,"context_line":"            value \u003d value.decode(encoding\u003d\u0027ascii\u0027)"},{"line_number":413,"context_line":"        self.vtpm_secret_value \u003d value"},{"line_number":414,"context_line":""},{"line_number":415,"context_line":""}],"source_content_type":"text/x-python","patch_set":2,"id":"87c097c9_50531856","line":412,"in_reply_to":"01e14775_3afa42ad","updated":"2026-02-19 16:06:06.000000000","message":"agreed with Dan here, we said it should only be bytes, nope ?","commit_id":"30ee238b7293ff3e16017823f530715b1b64f541"},{"author":{"_account_id":4690,"name":"melanie witt","display_name":"melwitt","email":"melwittt@gmail.com","username":"melwitt"},"change_message_id":"54ddbe70954acd03630019e9e297c5b8e0546b29","unresolved":true,"context_lines":[{"line_number":409,"context_line":"        standard Base64 alphabet."},{"line_number":410,"context_line":"        \"\"\""},{"line_number":411,"context_line":"        if isinstance(value, bytes):"},{"line_number":412,"context_line":"            value \u003d value.decode(encoding\u003d\u0027ascii\u0027)"},{"line_number":413,"context_line":"        self.vtpm_secret_value \u003d value"},{"line_number":414,"context_line":""},{"line_number":415,"context_line":""}],"source_content_type":"text/x-python","patch_set":2,"id":"daafa57d_40dcba00","line":412,"in_reply_to":"87c097c9_50531856","updated":"2026-02-19 17:37:08.000000000","message":"That\u0027s true -- no specific reason, I basically just thought, \"since I can check, maybe I should check\" but it\u0027s a good point that its presence makes it confusing. I\u0027ll remove the check.","commit_id":"30ee238b7293ff3e16017823f530715b1b64f541"},{"author":{"_account_id":4690,"name":"melanie witt","display_name":"melwitt","email":"melwittt@gmail.com","username":"melwitt"},"change_message_id":"e34cf3bbfb147abc577f57a4f98f7999517f4119","unresolved":false,"context_lines":[{"line_number":409,"context_line":"        standard Base64 alphabet."},{"line_number":410,"context_line":"        \"\"\""},{"line_number":411,"context_line":"        if isinstance(value, bytes):"},{"line_number":412,"context_line":"            value \u003d value.decode(encoding\u003d\u0027ascii\u0027)"},{"line_number":413,"context_line":"        self.vtpm_secret_value \u003d value"},{"line_number":414,"context_line":""},{"line_number":415,"context_line":""}],"source_content_type":"text/x-python","patch_set":2,"id":"bb695adc_25807846","line":412,"in_reply_to":"daafa57d_40dcba00","updated":"2026-02-26 18:16:07.000000000","message":"Done","commit_id":"30ee238b7293ff3e16017823f530715b1b64f541"},{"author":{"_account_id":7166,"name":"Sylvain Bauza","email":"sbauza@redhat.com","username":"sbauza"},"change_message_id":"99a8658970b83a99da2878911af74a1181e318a3","unresolved":true,"context_lines":[{"line_number":376,"context_line":"            self.has_vtpm and self.vtpm_secret_uuid and self.vtpm_secret_value)"},{"line_number":377,"context_line":""},{"line_number":378,"context_line":"    @property"},{"line_number":379,"context_line":"    def vtpm_secret_value_bytes(self) -\u003e bytes:"},{"line_number":380,"context_line":"        \"\"\"Get the vTPM secret value as bytes after transport over RPC."},{"line_number":381,"context_line":""},{"line_number":382,"context_line":"        A vTPM secret is a Barbican secret of type \"passphrase\", which are"}],"source_content_type":"text/x-python","patch_set":3,"id":"0961c644_104579db","line":379,"updated":"2026-02-25 17:37:30.000000000","message":"a long time before in a galaxy far far away, people were not annotating return values, they were just adding a :return: value in the docstring because we\u0027re humans that can read.\n\nBut meh, don\u0027t want to hold that patch before now everything has to be about typing.","commit_id":"e5a3f73368795b3db3f26a3feb99b3a2bc8d3f91"},{"author":{"_account_id":11604,"name":"sean mooney","email":"smooney@redhat.com","username":"sean-k-mooney"},"change_message_id":"fe2c4ea9d8d08d2a04f9931caba7ac2d8ea5401c","unresolved":true,"context_lines":[{"line_number":376,"context_line":"            self.has_vtpm and self.vtpm_secret_uuid and self.vtpm_secret_value)"},{"line_number":377,"context_line":""},{"line_number":378,"context_line":"    @property"},{"line_number":379,"context_line":"    def vtpm_secret_value_bytes(self) -\u003e bytes:"},{"line_number":380,"context_line":"        \"\"\"Get the vTPM secret value as bytes after transport over RPC."},{"line_number":381,"context_line":""},{"line_number":382,"context_line":"        A vTPM secret is a Barbican secret of type \"passphrase\", which are"}],"source_content_type":"text/x-python","patch_set":3,"id":"98c84eed_2152185f","line":379,"in_reply_to":"0961c644_104579db","updated":"2026-02-25 20:24:44.000000000","message":"type annotation can be checked by tools without using llms.","commit_id":"e5a3f73368795b3db3f26a3feb99b3a2bc8d3f91"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"c1dfa6b91929bea2b2579ba46eea1f64ed05f3bf","unresolved":true,"context_lines":[{"line_number":376,"context_line":"            self.has_vtpm and self.vtpm_secret_uuid and self.vtpm_secret_value)"},{"line_number":377,"context_line":""},{"line_number":378,"context_line":"    @property"},{"line_number":379,"context_line":"    def vtpm_secret_value_bytes(self) -\u003e bytes:"},{"line_number":380,"context_line":"        \"\"\"Get the vTPM secret value as bytes after transport over RPC."},{"line_number":381,"context_line":""},{"line_number":382,"context_line":"        A vTPM secret is a Barbican secret of type \"passphrase\", which are"}],"source_content_type":"text/x-python","patch_set":3,"id":"824932b5_8f49dca5","line":379,"in_reply_to":"476c4e76_bef717d2","updated":"2026-02-26 15:10:15.000000000","message":"Not at runtime, only static check time. It provides no actual safety, and I agree with bauzas, I *hate* the clutter this adds. The amount of time I spent yesterday trying to convince mypy in oslo.utils that the types _in mocked tests_ were fine was insanity. Claude told me to just disable the checks with a comment.","commit_id":"e5a3f73368795b3db3f26a3feb99b3a2bc8d3f91"},{"author":{"_account_id":4690,"name":"melanie witt","display_name":"melwitt","email":"melwittt@gmail.com","username":"melwitt"},"change_message_id":"e34cf3bbfb147abc577f57a4f98f7999517f4119","unresolved":true,"context_lines":[{"line_number":376,"context_line":"            self.has_vtpm and self.vtpm_secret_uuid and self.vtpm_secret_value)"},{"line_number":377,"context_line":""},{"line_number":378,"context_line":"    @property"},{"line_number":379,"context_line":"    def vtpm_secret_value_bytes(self) -\u003e bytes:"},{"line_number":380,"context_line":"        \"\"\"Get the vTPM secret value as bytes after transport over RPC."},{"line_number":381,"context_line":""},{"line_number":382,"context_line":"        A vTPM secret is a Barbican secret of type \"passphrase\", which are"}],"source_content_type":"text/x-python","patch_set":3,"id":"95def34c_d2d2cf7c","line":379,"in_reply_to":"824932b5_8f49dca5","updated":"2026-02-26 18:16:07.000000000","message":"OK, I added this bc it helped catch the typing issue in the unit test but I can remove the file from the mypy file list if objects/ files were intentionally not supposed to be included.","commit_id":"e5a3f73368795b3db3f26a3feb99b3a2bc8d3f91"},{"author":{"_account_id":4690,"name":"melanie witt","display_name":"melwitt","email":"melwittt@gmail.com","username":"melwitt"},"change_message_id":"b2f0f828e21485a18521a5ad32568b1ba99bf3df","unresolved":false,"context_lines":[{"line_number":376,"context_line":"            self.has_vtpm and self.vtpm_secret_uuid and self.vtpm_secret_value)"},{"line_number":377,"context_line":""},{"line_number":378,"context_line":"    @property"},{"line_number":379,"context_line":"    def vtpm_secret_value_bytes(self) -\u003e bytes:"},{"line_number":380,"context_line":"        \"\"\"Get the vTPM secret value as bytes after transport over RPC."},{"line_number":381,"context_line":""},{"line_number":382,"context_line":"        A vTPM secret is a Barbican secret of type \"passphrase\", which are"}],"source_content_type":"text/x-python","patch_set":3,"id":"07ea2528_9018c51f","line":379,"in_reply_to":"95def34c_d2d2cf7c","updated":"2026-02-26 18:40:34.000000000","message":"Done","commit_id":"e5a3f73368795b3db3f26a3feb99b3a2bc8d3f91"},{"author":{"_account_id":4690,"name":"melanie witt","display_name":"melwitt","email":"melwittt@gmail.com","username":"melwitt"},"change_message_id":"6eea3595ef05af53e953d192e21684050f071ec7","unresolved":true,"context_lines":[{"line_number":376,"context_line":"            self.has_vtpm and self.vtpm_secret_uuid and self.vtpm_secret_value)"},{"line_number":377,"context_line":""},{"line_number":378,"context_line":"    @property"},{"line_number":379,"context_line":"    def vtpm_secret_value_bytes(self) -\u003e bytes:"},{"line_number":380,"context_line":"        \"\"\"Get the vTPM secret value as bytes after transport over RPC."},{"line_number":381,"context_line":""},{"line_number":382,"context_line":"        A vTPM secret is a Barbican secret of type \"passphrase\", which are"}],"source_content_type":"text/x-python","patch_set":3,"id":"476c4e76_bef717d2","line":379,"in_reply_to":"98c84eed_2152185f","updated":"2026-02-25 22:45:36.000000000","message":"FWIW IIUC this will get checked by mypy at its call site so it does more than just for reading.","commit_id":"e5a3f73368795b3db3f26a3feb99b3a2bc8d3f91"}],"nova/tests/unit/virt/libvirt/test_driver.py":[{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"ec6f67c103133cc7f8a80186eef0964756e05c58","unresolved":true,"context_lines":[{"line_number":13302,"context_line":"        }"},{"line_number":13303,"context_line":"        dest_check_data \u003d objects.LibvirtLiveMigrateData(filename\u003d\u0027file\u0027)"},{"line_number":13304,"context_line":"        mock_find.return_value.UUIDString.return_value \u003d uuids.secret"},{"line_number":13305,"context_line":"        mock_find.return_value.value.return_value \u003d b\u0027foo\u0027"},{"line_number":13306,"context_line":""},{"line_number":13307,"context_line":"        drvr \u003d libvirt_driver.LibvirtDriver(fake.FakeVirtAPI(), False)"},{"line_number":13308,"context_line":"        drvr.check_can_live_migrate_source(self.context, instance,"}],"source_content_type":"text/x-python","patch_set":2,"id":"0fad6cd8_59ebe2c1","line":13305,"updated":"2026-02-19 15:29:36.000000000","message":"So your mock was incorrectly returning `str` before, instead of `bytes` like libvirt actually does?","commit_id":"30ee238b7293ff3e16017823f530715b1b64f541"},{"author":{"_account_id":4690,"name":"melanie witt","display_name":"melwitt","email":"melwittt@gmail.com","username":"melwitt"},"change_message_id":"54ddbe70954acd03630019e9e297c5b8e0546b29","unresolved":true,"context_lines":[{"line_number":13302,"context_line":"        }"},{"line_number":13303,"context_line":"        dest_check_data \u003d objects.LibvirtLiveMigrateData(filename\u003d\u0027file\u0027)"},{"line_number":13304,"context_line":"        mock_find.return_value.UUIDString.return_value \u003d uuids.secret"},{"line_number":13305,"context_line":"        mock_find.return_value.value.return_value \u003d b\u0027foo\u0027"},{"line_number":13306,"context_line":""},{"line_number":13307,"context_line":"        drvr \u003d libvirt_driver.LibvirtDriver(fake.FakeVirtAPI(), False)"},{"line_number":13308,"context_line":"        drvr.check_can_live_migrate_source(self.context, instance,"}],"source_content_type":"text/x-python","patch_set":2,"id":"af625f55_484928b4","line":13305,"in_reply_to":"0fad6cd8_59ebe2c1","updated":"2026-02-19 17:37:08.000000000","message":"This was mocking `decode()` before so it was correct for returning a `str` from `decode()`. I think it wasn\u0027t necessary to mock `decode()` though so if we don\u0027t mock `decode()`, this (i.e. `secret.value()`) should be `bytes`.","commit_id":"30ee238b7293ff3e16017823f530715b1b64f541"},{"author":{"_account_id":11604,"name":"sean mooney","email":"smooney@redhat.com","username":"sean-k-mooney"},"change_message_id":"fe2c4ea9d8d08d2a04f9931caba7ac2d8ea5401c","unresolved":true,"context_lines":[{"line_number":13302,"context_line":"        }"},{"line_number":13303,"context_line":"        dest_check_data \u003d objects.LibvirtLiveMigrateData(filename\u003d\u0027file\u0027)"},{"line_number":13304,"context_line":"        mock_find.return_value.UUIDString.return_value \u003d uuids.secret"},{"line_number":13305,"context_line":"        mock_find.return_value.value.return_value \u003d b\u0027foo\u0027"},{"line_number":13306,"context_line":""},{"line_number":13307,"context_line":"        drvr \u003d libvirt_driver.LibvirtDriver(fake.FakeVirtAPI(), False)"},{"line_number":13308,"context_line":"        drvr.check_can_live_migrate_source(self.context, instance,"}],"source_content_type":"text/x-python","patch_set":2,"id":"d30b7a42_e1debd11","line":13305,"in_reply_to":"af625f55_484928b4","updated":"2026-02-25 20:24:44.000000000","message":"decode is a pure fucntion of its input and relitivley cheap so not mocking it is ok\n\nwith that said if you do end up updating this again i feel like \ninstead of \n```\n mock_find.return_value.UUIDString.return_value \u003d uuids.secret\n mock_find.return_value.value.return_value \u003d b\u0027foo\u0027\n```\nwe proably shoudl be constucting a fake object and assing it ot \n\nmock_find.return_value\n\nthis i guess is pretended to be the libvirt secret datascuture but we proably have that or shoudl add that to the fake libvirt fixutre.\n\nthat could be done in a followup but it would make this code nice to read","commit_id":"30ee238b7293ff3e16017823f530715b1b64f541"},{"author":{"_account_id":4690,"name":"melanie witt","display_name":"melwitt","email":"melwittt@gmail.com","username":"melwitt"},"change_message_id":"6eea3595ef05af53e953d192e21684050f071ec7","unresolved":true,"context_lines":[{"line_number":13302,"context_line":"        }"},{"line_number":13303,"context_line":"        dest_check_data \u003d objects.LibvirtLiveMigrateData(filename\u003d\u0027file\u0027)"},{"line_number":13304,"context_line":"        mock_find.return_value.UUIDString.return_value \u003d uuids.secret"},{"line_number":13305,"context_line":"        mock_find.return_value.value.return_value \u003d b\u0027foo\u0027"},{"line_number":13306,"context_line":""},{"line_number":13307,"context_line":"        drvr \u003d libvirt_driver.LibvirtDriver(fake.FakeVirtAPI(), False)"},{"line_number":13308,"context_line":"        drvr.check_can_live_migrate_source(self.context, instance,"}],"source_content_type":"text/x-python","patch_set":2,"id":"0c461808_d9071605","line":13305,"in_reply_to":"d30b7a42_e1debd11","updated":"2026-02-25 22:45:36.000000000","message":"There is a fake Secret object here but it\u0027s kinda specialized around Connection and XML:\n\nhttps://github.com/openstack/nova/blob/afac8df46dcfc0a6b68bce1e9041fbf910bf0a89/nova/tests/fixtures/libvirt.py#L1956","commit_id":"30ee238b7293ff3e16017823f530715b1b64f541"}],"nova/virt/libvirt/driver.py":[{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"7abafa723e59bd34348b67cd234b2d720acfda8a","unresolved":true,"context_lines":[{"line_number":10892,"context_line":"            # the secret value as opaque bytes and does not decode or encode"},{"line_number":10893,"context_line":"            # anything. Here, we decode the opaque bytes retrieved from libvirt"},{"line_number":10894,"context_line":"            # to a utf-8 encoded string to set the SensitiveStringField in the"},{"line_number":10895,"context_line":"            # LibvirtLiveMigrateData object."},{"line_number":10896,"context_line":"            dest_check_data.vtpm_secret_value \u003d secret.value().decode()"},{"line_number":10897,"context_line":"        else:"},{"line_number":10898,"context_line":"            # If the instance has a vTPM, set the relevant fields to None in"}],"source_content_type":"text/x-python","patch_set":1,"id":"16a15c39_c3d7651d","line":10895,"updated":"2026-02-16 16:15:55.000000000","message":"\u003e Here, we decode the opaque bytes retrieved from libvirt to a utf-8 encoded string\n\nThis is not wrong, but I think the wording will be confusing later. The thing we want to clarify is that the bytes will be exactly the base64 string, and \"opaque bytes\" sounds (to me) like somewhere the base64 has been decoded. This is an annoyingly complicated thing to explain because everything is bytes, but python is \"encoding\" a `str` into `bytes` which can imply further changes, but in this case is not, and only because libvirt needs bytes (in the form of a python `bytes` and not because it wants UTF-8. I know this is a bit of pedantry, but since this has tripped us up several times I\u0027d like to preserve as much correctness for the record as possible. If I may suggest:","commit_id":"1419ee60398be73cd39cffc4a72e16a4eab124d8"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"7abafa723e59bd34348b67cd234b2d720acfda8a","unresolved":true,"context_lines":[{"line_number":10883,"context_line":"            dest_check_data.vtpm_secret_uuid \u003d secret.UUIDString()"},{"line_number":10884,"context_line":"            # NOTE(melwitt): The vTPM secret is a Barbican secret of type"},{"line_number":10885,"context_line":"            # \"passphrase\", which are used for storing plain text secrets."},{"line_number":10886,"context_line":"            # The value of the secret is generated in nova/crypto.py as a"},{"line_number":10887,"context_line":"            # random bytestring that is subsequently base64 encoded and"},{"line_number":10888,"context_line":"            # passed to Barbican in order to create a passphrase."},{"line_number":10889,"context_line":"            # The base64 encoded string is the passphrase itself and it is"},{"line_number":10890,"context_line":"            # passed to libvirt as-is when creating a libvirt secret with a"},{"line_number":10891,"context_line":"            # UUID that matches the secret UUID in Barbican. Libvirt treats"},{"line_number":10892,"context_line":"            # the secret value as opaque bytes and does not decode or encode"},{"line_number":10893,"context_line":"            # anything. Here, we decode the opaque bytes retrieved from libvirt"},{"line_number":10894,"context_line":"            # to a utf-8 encoded string to set the SensitiveStringField in the"},{"line_number":10895,"context_line":"            # LibvirtLiveMigrateData object."},{"line_number":10896,"context_line":"            dest_check_data.vtpm_secret_value \u003d secret.value().decode()"},{"line_number":10897,"context_line":"        else:"},{"line_number":10898,"context_line":"            # If the instance has a vTPM, set the relevant fields to None in"}],"source_content_type":"text/x-python","patch_set":1,"id":"0648f585_6fcc6262","line":10895,"range":{"start_line":10886,"start_character":0,"end_line":10895,"end_character":44},"updated":"2026-02-16 16:15:55.000000000","message":"```suggestion\n            # The value of the secret is generated in nova/crypto.py as a\n            # random bytestring that is subsequently base64 encoded and\n            # passed to Barbican in order to create a passphrase.\n            # The base64 encoded string is the passphrase itself and it is\n            # passed to libvirt (as a 1:1 conversion to bytes) when creating\n            # a libvirt secret with a UUID that matches the secret UUID in\n            # Barbican. Libvirt treats the secret value as opaque. Here, we\n            # decode the opaque bytes retrieved from libvirt back into the\n            # python string, to match the string passphrase we use everywhere\n            # else (including the SensitiveStringField in the\n            # LibvirtLiveMigrateData object). While the UTF-8 codec is\n            # technically used when encoding the passphrase string to bytes\n            # for libvirt, it\u0027s just base64 ASCII text, and thus decoding it\n            # here is simply the reverse operation, giving us the original\n            # value (base64 passphrase) back in the original data type (str).\n```","commit_id":"1419ee60398be73cd39cffc4a72e16a4eab124d8"},{"author":{"_account_id":4690,"name":"melanie witt","display_name":"melwitt","email":"melwittt@gmail.com","username":"melwitt"},"change_message_id":"1d4da83059076b2422b91a1c901e78041bb4a946","unresolved":true,"context_lines":[{"line_number":10883,"context_line":"            dest_check_data.vtpm_secret_uuid \u003d secret.UUIDString()"},{"line_number":10884,"context_line":"            # NOTE(melwitt): The vTPM secret is a Barbican secret of type"},{"line_number":10885,"context_line":"            # \"passphrase\", which are used for storing plain text secrets."},{"line_number":10886,"context_line":"            # The value of the secret is generated in nova/crypto.py as a"},{"line_number":10887,"context_line":"            # random bytestring that is subsequently base64 encoded and"},{"line_number":10888,"context_line":"            # passed to Barbican in order to create a passphrase."},{"line_number":10889,"context_line":"            # The base64 encoded string is the passphrase itself and it is"},{"line_number":10890,"context_line":"            # passed to libvirt as-is when creating a libvirt secret with a"},{"line_number":10891,"context_line":"            # UUID that matches the secret UUID in Barbican. Libvirt treats"},{"line_number":10892,"context_line":"            # the secret value as opaque bytes and does not decode or encode"},{"line_number":10893,"context_line":"            # anything. Here, we decode the opaque bytes retrieved from libvirt"},{"line_number":10894,"context_line":"            # to a utf-8 encoded string to set the SensitiveStringField in the"},{"line_number":10895,"context_line":"            # LibvirtLiveMigrateData object."},{"line_number":10896,"context_line":"            dest_check_data.vtpm_secret_value \u003d secret.value().decode()"},{"line_number":10897,"context_line":"        else:"},{"line_number":10898,"context_line":"            # If the instance has a vTPM, set the relevant fields to None in"}],"source_content_type":"text/x-python","patch_set":1,"id":"5e5ead68_24fdb3c2","line":10895,"range":{"start_line":10886,"start_character":0,"end_line":10895,"end_character":44},"in_reply_to":"0648f585_6fcc6262","updated":"2026-02-16 23:40:14.000000000","message":"Sorry ... I am still not understanding this unfortunately 🙁 To me the \"original data type\" is not (str), it is (bytes) i.e. `secret \u003d base64.b64encode(os.urandom(_VTPM_SECRET_BYTE_LENGTH))` in nova/crypto.py:\n\nhttps://github.com/openstack/nova/blob/f3d9188a937518e9dbfa434436ba336bc2107fc2/nova/crypto.py#L226-L231\n\nThat is what we pass to libvirt and to Barbican (Castellan) which also uses data type (bytes):\n\nhttps://github.com/openstack/castellan/blob/1b3e0a0c7149a1e3e5dd941368f43c462d810f7b/castellan/common/objects/passphrase.py#L32\n\nTo me it seems like the opposite. It\u0027s always data type bytes and we don\u0027t have to convert anything for libvirt. We have to convert to (str) for SensitiveStringField and then immediately convert back to (bytes) on the other side of the RPC.\n\nI also want to make sure this comment text is as pedantically accurate as possible for reading, but currently I am myself not understanding the suggested text 🙃","commit_id":"1419ee60398be73cd39cffc4a72e16a4eab124d8"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"1a60c5d57ba0e12f51377371f5cf63845eb168b5","unresolved":true,"context_lines":[{"line_number":10883,"context_line":"            dest_check_data.vtpm_secret_uuid \u003d secret.UUIDString()"},{"line_number":10884,"context_line":"            # NOTE(melwitt): The vTPM secret is a Barbican secret of type"},{"line_number":10885,"context_line":"            # \"passphrase\", which are used for storing plain text secrets."},{"line_number":10886,"context_line":"            # The value of the secret is generated in nova/crypto.py as a"},{"line_number":10887,"context_line":"            # random bytestring that is subsequently base64 encoded and"},{"line_number":10888,"context_line":"            # passed to Barbican in order to create a passphrase."},{"line_number":10889,"context_line":"            # The base64 encoded string is the passphrase itself and it is"},{"line_number":10890,"context_line":"            # passed to libvirt as-is when creating a libvirt secret with a"},{"line_number":10891,"context_line":"            # UUID that matches the secret UUID in Barbican. Libvirt treats"},{"line_number":10892,"context_line":"            # the secret value as opaque bytes and does not decode or encode"},{"line_number":10893,"context_line":"            # anything. Here, we decode the opaque bytes retrieved from libvirt"},{"line_number":10894,"context_line":"            # to a utf-8 encoded string to set the SensitiveStringField in the"},{"line_number":10895,"context_line":"            # LibvirtLiveMigrateData object."},{"line_number":10896,"context_line":"            dest_check_data.vtpm_secret_value \u003d secret.value().decode()"},{"line_number":10897,"context_line":"        else:"},{"line_number":10898,"context_line":"            # If the instance has a vTPM, set the relevant fields to None in"}],"source_content_type":"text/x-python","patch_set":1,"id":"d7c1c48c_6e0b1a8a","line":10895,"range":{"start_line":10886,"start_character":0,"end_line":10895,"end_character":44},"in_reply_to":"5e5ead68_24fdb3c2","updated":"2026-02-17 15:54:40.000000000","message":"UGH, okay this is again not what I had in my head after the last time we talked on gmeet about this.. I should have confirmed everything in the code, so that\u0027s my bad. This goes back to your assertion about \"we only store it as str for the object\" and I when I said \"that can\u0027t be true\" you said it was stored as text/passphrase for barbican as well:\n\nhttps://meetings.opendev.org/irclogs/%23openstack-nova/%23openstack-nova.2026-02-10.log.html#openstack-nova.2026-02-10.log.html#t2026-02-10T19:30:55\n\nSo this is working because b64encode() is generating a \"string\" that we can decode even though it packs it into `bytes`. It\u0027s decode-able only because the output namespace of base64 happens to be ASCII. This means we really _should_ be using some sort of bytes field, and if not, it would be best to encode and decode only and exactly at the point at which we set it on and get it from, the object.\n\nGiven we keep being confused about this, I think we probably need to do something tighter than we have today to avoid getting stuck on this in the future. Let me try to cook something up this afternoon to see if it makes me feel better about it.","commit_id":"1419ee60398be73cd39cffc4a72e16a4eab124d8"},{"author":{"_account_id":4690,"name":"melanie witt","display_name":"melwitt","email":"melwittt@gmail.com","username":"melwitt"},"change_message_id":"29b73f588b344ac57dd53aca6efc0dd2649fb7d9","unresolved":true,"context_lines":[{"line_number":10883,"context_line":"            dest_check_data.vtpm_secret_uuid \u003d secret.UUIDString()"},{"line_number":10884,"context_line":"            # NOTE(melwitt): The vTPM secret is a Barbican secret of type"},{"line_number":10885,"context_line":"            # \"passphrase\", which are used for storing plain text secrets."},{"line_number":10886,"context_line":"            # The value of the secret is generated in nova/crypto.py as a"},{"line_number":10887,"context_line":"            # random bytestring that is subsequently base64 encoded and"},{"line_number":10888,"context_line":"            # passed to Barbican in order to create a passphrase."},{"line_number":10889,"context_line":"            # The base64 encoded string is the passphrase itself and it is"},{"line_number":10890,"context_line":"            # passed to libvirt as-is when creating a libvirt secret with a"},{"line_number":10891,"context_line":"            # UUID that matches the secret UUID in Barbican. Libvirt treats"},{"line_number":10892,"context_line":"            # the secret value as opaque bytes and does not decode or encode"},{"line_number":10893,"context_line":"            # anything. Here, we decode the opaque bytes retrieved from libvirt"},{"line_number":10894,"context_line":"            # to a utf-8 encoded string to set the SensitiveStringField in the"},{"line_number":10895,"context_line":"            # LibvirtLiveMigrateData object."},{"line_number":10896,"context_line":"            dest_check_data.vtpm_secret_value \u003d secret.value().decode()"},{"line_number":10897,"context_line":"        else:"},{"line_number":10898,"context_line":"            # If the instance has a vTPM, set the relevant fields to None in"}],"source_content_type":"text/x-python","patch_set":1,"id":"12f48fcf_c4c44a19","line":10895,"range":{"start_line":10886,"start_character":0,"end_line":10895,"end_character":44},"in_reply_to":"8b197189_c481f243","updated":"2026-02-17 21:41:14.000000000","message":"To the rest of your reply, I agree I think it would a lot better to move the decode/encode into the object as its the only place where it\u0027s truly relevant. I don\u0027t mind making the change but appreciate your offer to do it.\n\nI have been nearly maximum confused by all of this so it\u0027s not only your complaint 😣","commit_id":"1419ee60398be73cd39cffc4a72e16a4eab124d8"},{"author":{"_account_id":4690,"name":"melanie witt","display_name":"melwitt","email":"melwittt@gmail.com","username":"melwitt"},"change_message_id":"d2284138dc79b17f1e470ca37c22cce4905297dc","unresolved":true,"context_lines":[{"line_number":10883,"context_line":"            dest_check_data.vtpm_secret_uuid \u003d secret.UUIDString()"},{"line_number":10884,"context_line":"            # NOTE(melwitt): The vTPM secret is a Barbican secret of type"},{"line_number":10885,"context_line":"            # \"passphrase\", which are used for storing plain text secrets."},{"line_number":10886,"context_line":"            # The value of the secret is generated in nova/crypto.py as a"},{"line_number":10887,"context_line":"            # random bytestring that is subsequently base64 encoded and"},{"line_number":10888,"context_line":"            # passed to Barbican in order to create a passphrase."},{"line_number":10889,"context_line":"            # The base64 encoded string is the passphrase itself and it is"},{"line_number":10890,"context_line":"            # passed to libvirt as-is when creating a libvirt secret with a"},{"line_number":10891,"context_line":"            # UUID that matches the secret UUID in Barbican. Libvirt treats"},{"line_number":10892,"context_line":"            # the secret value as opaque bytes and does not decode or encode"},{"line_number":10893,"context_line":"            # anything. Here, we decode the opaque bytes retrieved from libvirt"},{"line_number":10894,"context_line":"            # to a utf-8 encoded string to set the SensitiveStringField in the"},{"line_number":10895,"context_line":"            # LibvirtLiveMigrateData object."},{"line_number":10896,"context_line":"            dest_check_data.vtpm_secret_value \u003d secret.value().decode()"},{"line_number":10897,"context_line":"        else:"},{"line_number":10898,"context_line":"            # If the instance has a vTPM, set the relevant fields to None in"}],"source_content_type":"text/x-python","patch_set":1,"id":"8b197189_c481f243","line":10895,"range":{"start_line":10886,"start_character":0,"end_line":10895,"end_character":44},"in_reply_to":"a35ea30d_1b2c065e","updated":"2026-02-17 21:27:34.000000000","message":"\u003e This goes back to your assertion about \"we only store it as str for the object\" and I when I said \"that can\u0027t be true\" you said it was stored as text/passphrase for barbican as well:\n\u003e\n\u003e https://meetings.opendev.org/irclogs/%23openstack-nova/%23openstack-nova.2026-02-10.log.html#openstack-nova.2026-02-10.log.html#t2026-02-10T19:30:55\n\nI think I had said \"we only convert it to str for the object\" because that\u0027s what I see on the Nova side and you mentioned something about how Barbican stores it, so I checked the Barbican documentation:\n\nhttps://docs.openstack.org/barbican/latest/api/reference/secret_types.html\n\ndue to a combination of low knowledge + did not know where to look in the Barbican code yet. The doc made me think Barbican might be converting things of secret type \"passphrase\" to (str) before storing them on the Barbican side. Which maybe doesn\u0027t really matter but I wasn\u0027t sure.\n\nThe doc says `• passphrase - Used for storing plain text passphrases.` While trying to formulate a reply to your text suggestion, I dug in more into the Barbican and Castellan code because it all just did not make sense to me.\n\nOn the Nova side, we generate the `os.urandom` (bytes) and then `b64encode` it, still (bytes).\n\nWe pass that to Castellan as a `Passphrase` object which stores the \"payload\" as-is i.e. (bytes).\n\nThen Castellan calls Barbican to create the secret via python-barbicanclient, which decides what to do based on the payload data type [1]:\n\n```\n        elif type(self.payload) is bytes:\n            \u0027\u0027\u0027\n            bytes is stored as application/octet-stream\n            and it is base64 encoded for a one-step POST\n            \u0027\u0027\u0027\n            secret_dict[\u0027payload\u0027] \u003d (\n                base64.b64encode(self.payload)\n            ).decode(\u0027UTF-8\u0027)\n            secret_dict[\u0027payload_content_type\u0027] \u003d \u0027application/octet-stream\u0027\n            secret_dict[\u0027payload_content_encoding\u0027] \u003d \u0027base64\u0027\n```\n\nSo this `b64encode` a second time and then converts to UTF-8 (str) for the REST call, indicating application/octet-stream content type and base64 content encoding.\n\nOn the Barbican side, the Castellan plugin `b64decode` it and stores it [2] presumably as (bytes):\n\n```\n    def store_secret(self, secret_dto):\n        if not self.store_secret_supports(secret_dto.key_spec):\n            raise ss.SecretAlgorithmNotSupportedException(\n                secret_dto.key_spec.alg)\n        plaintext \u003d base64.b64decode(secret_dto.secret)\n        try:\n            secret_id \u003d self.key_manager.store(\n                self.context,\n                opaque_data.OpaqueData(plaintext)\n            )\n```\n\nSo secret type \"passphrase\" and \"plain text\" are (bytes) which I did not expect based on the word \"passphrase\". This was part of my confusion, sorry 🙁\n\nI will reply to your last comment separately to try to keep this semi organized.\n\n[1] https://github.com/openstack/python-barbicanclient/blob/9fa3a3689e22a5c1825e21bc0e1a446ea24193e5/barbicanclient/v1/secrets.py#L370C1-L379C63\n[2] https://github.com/openstack/barbican/blob/317e70e98c39c39ce44f22b303cd3aaa739abafd/barbican/plugin/castellan_secret_store.py#L131-L140","commit_id":"1419ee60398be73cd39cffc4a72e16a4eab124d8"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"0a146f26c0f0551517e43e143dc216d892db6253","unresolved":true,"context_lines":[{"line_number":10883,"context_line":"            dest_check_data.vtpm_secret_uuid \u003d secret.UUIDString()"},{"line_number":10884,"context_line":"            # NOTE(melwitt): The vTPM secret is a Barbican secret of type"},{"line_number":10885,"context_line":"            # \"passphrase\", which are used for storing plain text secrets."},{"line_number":10886,"context_line":"            # The value of the secret is generated in nova/crypto.py as a"},{"line_number":10887,"context_line":"            # random bytestring that is subsequently base64 encoded and"},{"line_number":10888,"context_line":"            # passed to Barbican in order to create a passphrase."},{"line_number":10889,"context_line":"            # The base64 encoded string is the passphrase itself and it is"},{"line_number":10890,"context_line":"            # passed to libvirt as-is when creating a libvirt secret with a"},{"line_number":10891,"context_line":"            # UUID that matches the secret UUID in Barbican. Libvirt treats"},{"line_number":10892,"context_line":"            # the secret value as opaque bytes and does not decode or encode"},{"line_number":10893,"context_line":"            # anything. Here, we decode the opaque bytes retrieved from libvirt"},{"line_number":10894,"context_line":"            # to a utf-8 encoded string to set the SensitiveStringField in the"},{"line_number":10895,"context_line":"            # LibvirtLiveMigrateData object."},{"line_number":10896,"context_line":"            dest_check_data.vtpm_secret_value \u003d secret.value().decode()"},{"line_number":10897,"context_line":"        else:"},{"line_number":10898,"context_line":"            # If the instance has a vTPM, set the relevant fields to None in"}],"source_content_type":"text/x-python","patch_set":1,"id":"a35ea30d_1b2c065e","line":10895,"range":{"start_line":10886,"start_character":0,"end_line":10895,"end_character":44},"in_reply_to":"b7cd703f_dbf2e8c6","updated":"2026-02-17 19:16:37.000000000","message":"So, can we change these naked (defaulting to UTF-8) encode/decodes to specify ASCII explicitly? That will help to further narrow and codify the values we expect to be in the field and it will provide further (IMHO) stability on what happens if we end up with something other than base64-encoded bits in here. We should leave the default error-if-decode-fails behavior for sure. We don\u0027t (also IMHO) need to bump the version or change anything about that stuff here because it\u0027s already ASCII everywhere, were just tightening the input and output. If somehow we got a passphrase with a poop emoji in it, we\u0027d currently allow that to pass, but it would fail early and on the sending side if we try to encode that to ascii.\n\nI also think we should move these get/set methods into the object, nearer the version history and other definitions instead of having the what-is-this-really be so far away in the libvirt driver. I know it\u0027s the libvirt live migrate data object, but...\n\nIf that sounds okay, I\u0027m happy to propose that into this patch to help improve my complaint-to-actual-work ratio.","commit_id":"1419ee60398be73cd39cffc4a72e16a4eab124d8"},{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"6517c4ed854fa06a781202c56b4e4c3baa297fee","unresolved":true,"context_lines":[{"line_number":10883,"context_line":"            dest_check_data.vtpm_secret_uuid \u003d secret.UUIDString()"},{"line_number":10884,"context_line":"            # NOTE(melwitt): The vTPM secret is a Barbican secret of type"},{"line_number":10885,"context_line":"            # \"passphrase\", which are used for storing plain text secrets."},{"line_number":10886,"context_line":"            # The value of the secret is generated in nova/crypto.py as a"},{"line_number":10887,"context_line":"            # random bytestring that is subsequently base64 encoded and"},{"line_number":10888,"context_line":"            # passed to Barbican in order to create a passphrase."},{"line_number":10889,"context_line":"            # The base64 encoded string is the passphrase itself and it is"},{"line_number":10890,"context_line":"            # passed to libvirt as-is when creating a libvirt secret with a"},{"line_number":10891,"context_line":"            # UUID that matches the secret UUID in Barbican. Libvirt treats"},{"line_number":10892,"context_line":"            # the secret value as opaque bytes and does not decode or encode"},{"line_number":10893,"context_line":"            # anything. Here, we decode the opaque bytes retrieved from libvirt"},{"line_number":10894,"context_line":"            # to a utf-8 encoded string to set the SensitiveStringField in the"},{"line_number":10895,"context_line":"            # LibvirtLiveMigrateData object."},{"line_number":10896,"context_line":"            dest_check_data.vtpm_secret_value \u003d secret.value().decode()"},{"line_number":10897,"context_line":"        else:"},{"line_number":10898,"context_line":"            # If the instance has a vTPM, set the relevant fields to None in"}],"source_content_type":"text/x-python","patch_set":1,"id":"b7cd703f_dbf2e8c6","line":10895,"range":{"start_line":10886,"start_character":0,"end_line":10895,"end_character":44},"in_reply_to":"d7c1c48c_6e0b1a8a","updated":"2026-02-17 16:03:15.000000000","message":"\u003e Given we keep being confused about this, I think we probably need to do something tighter than we have today to avoid getting stuck on this in the future. Let me try to cook something up this afternoon to see if it makes me feel better about it.\n\nOkay, sorry, I guess this is the sort of encapsulation of the entry to and exit from the object to reduce the blast radius, it just seems like it shouldn\u0027t be in the libvirt driver which is why I wasn\u0027t thinking this was all of it. Like, I was thinking it should be in the object itself to keep all the details of the encoding with the \"transport\".","commit_id":"1419ee60398be73cd39cffc4a72e16a4eab124d8"}],"pyproject.toml":[{"author":{"_account_id":4393,"name":"Dan Smith","email":"dms@danplanet.com","username":"danms"},"change_message_id":"c1dfa6b91929bea2b2579ba46eea1f64ed05f3bf","unresolved":true,"context_lines":[{"line_number":132,"context_line":"    \"nova/limit/local.py\","},{"line_number":133,"context_line":"    \"nova/limit/placement.py\","},{"line_number":134,"context_line":"    \"nova/network/neutron.py\","},{"line_number":135,"context_line":"    \"nova/objects/migrate_data.py\","},{"line_number":136,"context_line":"    \"nova/pci/*.py\","},{"line_number":137,"context_line":"    \"nova/privsep/path.py\","},{"line_number":138,"context_line":"    \"nova/scheduler/client/report.py\","}],"source_content_type":"text/x-toml","patch_set":3,"id":"bcba0613_1e9e3f92","line":135,"updated":"2026-02-26 15:10:15.000000000","message":"I thought that we intentionally didn\u0027t have object files in here because they\u0027re so dynamic and hard to get mypy to work. Obviously the one you added is straightforward, but if we\u0027ve voting, I\u0027d sure love to _not_ drag them in.","commit_id":"e5a3f73368795b3db3f26a3feb99b3a2bc8d3f91"},{"author":{"_account_id":4690,"name":"melanie witt","display_name":"melwitt","email":"melwittt@gmail.com","username":"melwitt"},"change_message_id":"b2f0f828e21485a18521a5ad32568b1ba99bf3df","unresolved":false,"context_lines":[{"line_number":132,"context_line":"    \"nova/limit/local.py\","},{"line_number":133,"context_line":"    \"nova/limit/placement.py\","},{"line_number":134,"context_line":"    \"nova/network/neutron.py\","},{"line_number":135,"context_line":"    \"nova/objects/migrate_data.py\","},{"line_number":136,"context_line":"    \"nova/pci/*.py\","},{"line_number":137,"context_line":"    \"nova/privsep/path.py\","},{"line_number":138,"context_line":"    \"nova/scheduler/client/report.py\","}],"source_content_type":"text/x-toml","patch_set":3,"id":"7bb25959_225e5d39","line":135,"in_reply_to":"62b62734_8ef954e1","updated":"2026-02-26 18:40:34.000000000","message":"Done","commit_id":"e5a3f73368795b3db3f26a3feb99b3a2bc8d3f91"},{"author":{"_account_id":4690,"name":"melanie witt","display_name":"melwitt","email":"melwittt@gmail.com","username":"melwitt"},"change_message_id":"e34cf3bbfb147abc577f57a4f98f7999517f4119","unresolved":true,"context_lines":[{"line_number":132,"context_line":"    \"nova/limit/local.py\","},{"line_number":133,"context_line":"    \"nova/limit/placement.py\","},{"line_number":134,"context_line":"    \"nova/network/neutron.py\","},{"line_number":135,"context_line":"    \"nova/objects/migrate_data.py\","},{"line_number":136,"context_line":"    \"nova/pci/*.py\","},{"line_number":137,"context_line":"    \"nova/privsep/path.py\","},{"line_number":138,"context_line":"    \"nova/scheduler/client/report.py\","}],"source_content_type":"text/x-toml","patch_set":3,"id":"62b62734_8ef954e1","line":135,"in_reply_to":"bcba0613_1e9e3f92","updated":"2026-02-26 18:16:07.000000000","message":"I\u0027ll remove this line, I didn\u0027t realize there was some problem with including it.","commit_id":"e5a3f73368795b3db3f26a3feb99b3a2bc8d3f91"}]}
