)]}'
{"/COMMIT_MSG":[{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"c4b35d98d7a9ebc8800e113bf1958fd14a6d6aca","unresolved":true,"context_lines":[{"line_number":17,"context_line":"object still exists). For example, during a period of many concurrent"},{"line_number":18,"context_line":"POST requests to an object in a production system, a significant"},{"line_number":19,"context_line":"number of the POSTs returned 404 despite the object never being"},{"line_number":20,"context_line":"deleted."},{"line_number":21,"context_line":""},{"line_number":22,"context_line":"This patch modifies DiskFile to raise a new"},{"line_number":23,"context_line":"DiskFileMetadataUnavailable exception when metadata cannot be read"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":2,"id":"2c9991bf_6c4cd897","line":20,"updated":"2024-02-22 17:43:18.000000000","message":"super bad behavior!  very glad to see a fix!","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2a6c2bc275b3683c1721b78617b102c096f60a56","unresolved":false,"context_lines":[{"line_number":17,"context_line":"object still exists). For example, during a period of many concurrent"},{"line_number":18,"context_line":"POST requests to an object in a production system, a significant"},{"line_number":19,"context_line":"number of the POSTs returned 404 despite the object never being"},{"line_number":20,"context_line":"deleted."},{"line_number":21,"context_line":""},{"line_number":22,"context_line":"This patch modifies DiskFile to raise a new"},{"line_number":23,"context_line":"DiskFileMetadataUnavailable exception when metadata cannot be read"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":2,"id":"27c8a44d_09cd2ce9","line":20,"in_reply_to":"2c9991bf_6c4cd897","updated":"2024-02-23 12:13:15.000000000","message":"Acknowledged","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"c4b35d98d7a9ebc8800e113bf1958fd14a6d6aca","unresolved":true,"context_lines":[{"line_number":39,"context_line":"presumably be handled by the concurrent POST that has replaced the"},{"line_number":40,"context_line":"meta file."},{"line_number":41,"context_line":""},{"line_number":42,"context_line":"Change-Id: I2f698c25ed65b236e851e5a307d48a12cef62b33"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":2,"id":"7d944050_05a6bec6","line":42,"updated":"2024-02-22 17:43:18.000000000","message":"maybe worth an upstream fixes-lp-bug#","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2a6c2bc275b3683c1721b78617b102c096f60a56","unresolved":true,"context_lines":[{"line_number":39,"context_line":"presumably be handled by the concurrent POST that has replaced the"},{"line_number":40,"context_line":"meta file."},{"line_number":41,"context_line":""},{"line_number":42,"context_line":"Change-Id: I2f698c25ed65b236e851e5a307d48a12cef62b33"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":2,"id":"8e302d09_1678b194","line":42,"in_reply_to":"7d944050_05a6bec6","updated":"2024-02-23 12:13:15.000000000","message":"Done https://bugs.launchpad.net/swift/+bug/2054791","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"0407cd4c4fd725db62a80cd730fd69c4ad03eef8","unresolved":false,"context_lines":[{"line_number":39,"context_line":"presumably be handled by the concurrent POST that has replaced the"},{"line_number":40,"context_line":"meta file."},{"line_number":41,"context_line":""},{"line_number":42,"context_line":"Change-Id: I2f698c25ed65b236e851e5a307d48a12cef62b33"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":2,"id":"19c892a9_8babf1ab","line":42,"in_reply_to":"8e302d09_1678b194","updated":"2024-03-05 10:23:59.000000000","message":"Done","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"c1076bebd37aaf4a9c3bd32db2787829f4417d37","unresolved":true,"context_lines":[{"line_number":11,"context_line":"metadata is read then a DiskFileNotExist exception is raised which"},{"line_number":12,"context_line":"would previously cause the object server to return a 404."},{"line_number":13,"context_line":""},{"line_number":14,"context_line":"This behavior is appropriate when the missing file is a data file (it"},{"line_number":15,"context_line":"could have been removed by a concurrent request) but not when it is a"},{"line_number":16,"context_line":"meta file (it could have been replaced by another meta file, but the"},{"line_number":17,"context_line":"object still exists). For example, during a period of many concurrent"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":8,"id":"e849fada_84b60fe3","line":14,"range":{"start_line":14,"start_character":0,"end_line":14,"end_character":65},"updated":"2024-03-04 19:36:23.000000000","message":"I\u0027m not convinced this is true. It would only be reasonable to return the 404 if the new on-disk state had a tombstone, and only if we could also get a `X-Backend-Timestamp` for it.\n\nIf it was overwritten with another data file, though, we definitely should *not* 404 -- that would have the state roll back (however briefly) to before the original data file was written.","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"9748b562ab4afec8e444c528bb0d7fc5a7eb4e23","unresolved":false,"context_lines":[{"line_number":11,"context_line":"metadata is read then a DiskFileNotExist exception is raised which"},{"line_number":12,"context_line":"would previously cause the object server to return a 404."},{"line_number":13,"context_line":""},{"line_number":14,"context_line":"This behavior is appropriate when the missing file is a data file (it"},{"line_number":15,"context_line":"could have been removed by a concurrent request) but not when it is a"},{"line_number":16,"context_line":"meta file (it could have been replaced by another meta file, but the"},{"line_number":17,"context_line":"object still exists). For example, during a period of many concurrent"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":8,"id":"d8382678_27684501","line":14,"range":{"start_line":14,"start_character":0,"end_line":14,"end_character":65},"in_reply_to":"3a7bc9ab_1d06f202","updated":"2024-08-06 15:35:29.000000000","message":"Acknowledged","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"0407cd4c4fd725db62a80cd730fd69c4ad03eef8","unresolved":true,"context_lines":[{"line_number":11,"context_line":"metadata is read then a DiskFileNotExist exception is raised which"},{"line_number":12,"context_line":"would previously cause the object server to return a 404."},{"line_number":13,"context_line":""},{"line_number":14,"context_line":"This behavior is appropriate when the missing file is a data file (it"},{"line_number":15,"context_line":"could have been removed by a concurrent request) but not when it is a"},{"line_number":16,"context_line":"meta file (it could have been replaced by another meta file, but the"},{"line_number":17,"context_line":"object still exists). For example, during a period of many concurrent"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":8,"id":"3a7bc9ab_1d06f202","line":14,"range":{"start_line":14,"start_character":0,"end_line":14,"end_character":65},"in_reply_to":"e849fada_84b60fe3","updated":"2024-03-05 10:23:59.000000000","message":"I think I understand what you\u0027re saying - because we saw a .data in the listing but then failed to open it, we know that there should be either a .ts or a newer .data, so we know that if we listed again (with no other concurrent changes) then we could make a more accurate response.\n\nHowever, in the absence of retry, it doesn\u0027t seem inappropriate to treat this state as if no .data file exists.\n\nThis patch doesn\u0027t change the missing .data case. I could just remove the first half of this sentence from the commit message?","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"c1076bebd37aaf4a9c3bd32db2787829f4417d37","unresolved":true,"context_lines":[{"line_number":26,"context_line":"404, depending on the request method:"},{"line_number":27,"context_line":""},{"line_number":28,"context_line":"POSTs, GETs and HEADs that encounter this transient loss of a meta"},{"line_number":29,"context_line":"file will now return 503 rather than 404."},{"line_number":30,"context_line":""},{"line_number":31,"context_line":"DELETEs that encounter this transient loss of a meta file would"},{"line_number":32,"context_line":"previously have proceeded but will now return 503: the meta file may"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":8,"id":"50186340_fe21dbd6","line":29,"updated":"2024-03-04 19:36:23.000000000","message":"POST can still 404 -- https://paste.opendev.org/show/b2NgGnMZSgKMMRmMs1PK/ demonstrates.","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"0407cd4c4fd725db62a80cd730fd69c4ad03eef8","unresolved":true,"context_lines":[{"line_number":26,"context_line":"404, depending on the request method:"},{"line_number":27,"context_line":""},{"line_number":28,"context_line":"POSTs, GETs and HEADs that encounter this transient loss of a meta"},{"line_number":29,"context_line":"file will now return 503 rather than 404."},{"line_number":30,"context_line":""},{"line_number":31,"context_line":"DELETEs that encounter this transient loss of a meta file would"},{"line_number":32,"context_line":"previously have proceeded but will now return 503: the meta file may"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":8,"id":"bc658fbd_82f1cbd4","line":29,"in_reply_to":"50186340_fe21dbd6","updated":"2024-03-05 10:23:59.000000000","message":"In your test, is the POST returning 404 because of the loss of the meta file, or the loss of the data file? Did the POST even try to read the meta file? I think it would have failed to open the data file that it had listed and so return a 404.","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"9748b562ab4afec8e444c528bb0d7fc5a7eb4e23","unresolved":false,"context_lines":[{"line_number":26,"context_line":"404, depending on the request method:"},{"line_number":27,"context_line":""},{"line_number":28,"context_line":"POSTs, GETs and HEADs that encounter this transient loss of a meta"},{"line_number":29,"context_line":"file will now return 503 rather than 404."},{"line_number":30,"context_line":""},{"line_number":31,"context_line":"DELETEs that encounter this transient loss of a meta file would"},{"line_number":32,"context_line":"previously have proceeded but will now return 503: the meta file may"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":8,"id":"4fdb15a5_48b50cc9","line":29,"in_reply_to":"9d7e0829_ce192a54","updated":"2024-08-06 15:35:29.000000000","message":"Acknowledged","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"3a2e2cff3f1f08ddb660e66c6778c6f0632b7aa4","unresolved":true,"context_lines":[{"line_number":26,"context_line":"404, depending on the request method:"},{"line_number":27,"context_line":""},{"line_number":28,"context_line":"POSTs, GETs and HEADs that encounter this transient loss of a meta"},{"line_number":29,"context_line":"file will now return 503 rather than 404."},{"line_number":30,"context_line":""},{"line_number":31,"context_line":"DELETEs that encounter this transient loss of a meta file would"},{"line_number":32,"context_line":"previously have proceeded but will now return 503: the meta file may"}],"source_content_type":"text/x-gerrit-commit-message","patch_set":8,"id":"9d7e0829_ce192a54","line":29,"in_reply_to":"bc658fbd_82f1cbd4","updated":"2024-03-05 17:41:36.000000000","message":"Loss of the .ts file -- there *is no* .meta. My point is that given a (fully settled) PUT at t0, DELETE at t1, and another PUT at t3, if 404 a POST at some t2 between them, it should have a timestamp associated with it (provided we\u0027re within a reclaim age, I suppose).\n\nI think I got myself a little confused, though -- I\u0027d really meant to go experimenting with PUT-POST-PUT rather than DELETE-POST-PUT. But that fails in a similar way! If the .data file disappears mid-POST, it will 404, which seems to be a break from the consistency model. That one takes more to fix, though...","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"}],"/PATCHSET_LEVEL":[{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"e2bb425e98082f046672e400d842733214f31000","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":1,"id":"d979fa92_3cc1d7b2","updated":"2024-02-21 17:27:10.000000000","message":"This Is WIP - we should figure out a better behaviour","commit_id":"8e3ad5997daedba8d0c9e75886d7c3ac9d7e478f"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"9593b30a41c6d61cd8620a51db45d6f4a78b9e6e","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":1,"id":"fdd47fe7_618e8864","updated":"2024-02-21 16:00:56.000000000","message":"nice work!","commit_id":"8e3ad5997daedba8d0c9e75886d7c3ac9d7e478f"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"8f0235b4255392e7460824b734094017a4fbf45e","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":2,"id":"652ddadb_5956cfba","updated":"2024-02-22 18:38:45.000000000","message":"@Clay thanks for taking a look, one quick reply before I stop for today","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"c4b35d98d7a9ebc8800e113bf1958fd14a6d6aca","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":2,"id":"c9b2e9f0_2cc67e67","updated":"2024-02-22 17:43:18.000000000","message":"GET/HEAD look obvious/correct\nPOST also seems reasonable\nDELETE is a bit of a head turn, but I think ultimately near optimal\nPUT is maybe worth additional thinking - specifically WRT if-not-match\n\ntests look good; fixes important bug - probably should merge - I think the existing behavior already translated the .meta race on if-none-match to 201 so \"fixing\" it to 412 would just be another additional approvement I think; maybe worth a test.","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"82478c9cd57e652443d69b273d03239f21239697","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":6,"id":"618a136b_b69d1296","updated":"2024-02-23 21:08:58.000000000","message":"I think I saw a comment that got (kinda) stale; but overall this is fixing an important bug and seems perfectly well put together.  Maybe we could push it further if we want:\n\nhttps://review.opendev.org/c/openstack/swift/+/910029","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7233,"name":"Matthew Oliver","email":"matt@oliver.net.au","username":"mattoliverau"},"change_message_id":"04381368e95dbfc801c087c341259762038d4ba5","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":6,"id":"97e478b0_870c7c52","updated":"2024-02-26 05:50:48.000000000","message":"Looks solid, although looks like there is a rougue return in one of the tests","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"0407cd4c4fd725db62a80cd730fd69c4ad03eef8","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":8,"id":"88e5f6af_6e263b15","updated":"2024-03-05 10:23:59.000000000","message":"@Tim I agree that there\u0027s probably other cases that could be handled differently/better, but in this patch I was focussed on correcting at least one of the cases that were clearly wrong (concurrent POSTs returning 404).\n\nBeyond this, there is opportunity to do better than the baseline consistency model when these races happen on one server, by retrying when the diskfile can observe that the ondisk state has changed concurrently. I\u0027m not sure retrying would have helped in the case I saw in prod where we had a storm of POSTs, but it might in less overwhelming races.","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"26aad063d838fe5cda60e225f28ff1a60b621326","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":8,"id":"5eca644c_d10e64d4","updated":"2024-02-27 16:21:02.000000000","message":"I think the fallback stuff should be follow-up; this is a good improvement on it\u0027s own.  It\u0027s probably ready to merge... I\u0027ll take another closer look.","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"c5cd8af3ec6dfe1b178cfffedb584dbeff181a5a","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":8,"id":"6e3b1e59_cd3d98f4","updated":"2024-03-05 18:12:45.000000000","message":"See what you think of https://review.opendev.org/c/openstack/swift/+/911165 -- I think it\u0027s pretty well targeted.","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":7233,"name":"Matthew Oliver","email":"matt@oliver.net.au","username":"mattoliverau"},"change_message_id":"6f5f9e98f2f8c21570a5bc0eb7a941d5c01a4386","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":8,"id":"36a50a92_992af64e","updated":"2024-02-28 00:02:13.000000000","message":"Yeah, I like this approach to fixing the race condition. Passing the old datafile meta might make sense, but that\u0027ll be handled in a follow up. But otherwise this patch does tighten up and deal with a race condition.\n\nMight carry it for our next downstream release!","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"3a2e2cff3f1f08ddb660e66c6778c6f0632b7aa4","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":8,"id":"7486df0c_80880442","in_reply_to":"88e5f6af_6e263b15","updated":"2024-03-05 17:41:36.000000000","message":"Ack on my concerns maybe being out of scope, but they\u0027re *very* related.\n\n\u003e there is opportunity to do better than the baseline consistency model\n\nThe trouble I see is that we aren\u0027t doing what\u0027s necessary to actually have a consistency model -- we\u0027re allowing state to roll arbitrarily far backwards.","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"247f59877067d58ba8563d0be80c6a9e5f542c94","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":17,"id":"aa34a8ff_ff00d0c1","updated":"2025-01-16 11:44:39.000000000","message":"recheck","commit_id":"cb745837536196371bd6d0465d1dd03538d3a6b7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"fc4f3b99f36a9617081f1c80ed77eced03680f8a","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":17,"id":"4a352f23_24b22366","updated":"2025-01-16 15:02:45.000000000","message":"recheck\n\nthe probe test looks like an intermittent failure to restart a node","commit_id":"cb745837536196371bd6d0465d1dd03538d3a6b7"},{"author":{"_account_id":7233,"name":"Matthew Oliver","email":"matt@oliver.net.au","username":"mattoliverau"},"change_message_id":"e5325f515b69f2e07edeca960232ec2f5fb1afff","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":19,"id":"10bcda90_a7a604fc","updated":"2025-05-20 00:07:16.000000000","message":"We\u0027ve been carrying this for a while in production, and fixes a client bug. So is a big win. Everyone should benefit from this.\n\nThere was some discussion inline about timestamps for PUT and POST, but there are follow ups so seems out of scope. So landing this one now.. it\u0027s been a long time coming.","commit_id":"b735b3d034b11e1472f7b471919649d165c447e0"},{"author":{"_account_id":7233,"name":"Matthew Oliver","email":"matt@oliver.net.au","username":"mattoliverau"},"change_message_id":"119ea233078675072d3b2a4b57be11cad5dc30f0","unresolved":false,"context_lines":[],"source_content_type":"","patch_set":19,"id":"2b363b61_4b5e2987","updated":"2025-05-20 01:50:59.000000000","message":"recheck","commit_id":"b735b3d034b11e1472f7b471919649d165c447e0"}],"swift/common/exceptions.py":[{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"c1076bebd37aaf4a9c3bd32db2787829f4417d37","unresolved":true,"context_lines":[{"line_number":82,"context_line":""},{"line_number":83,"context_line":""},{"line_number":84,"context_line":"class DiskFileMetadataUnavailable(DiskFileError):"},{"line_number":85,"context_line":"    # the DiskFile exists but could not be opened for some transient reason"},{"line_number":86,"context_line":"    pass"},{"line_number":87,"context_line":""},{"line_number":88,"context_line":""}],"source_content_type":"text/x-python","patch_set":8,"id":"69a5782c_edcc6ee8","line":85,"updated":"2024-03-04 19:36:23.000000000","message":"If we turn it into a docstring, the `pass` becomes unnecessary ;-)","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2311de931d684f39a2d8a2a04015e60454a56100","unresolved":false,"context_lines":[{"line_number":82,"context_line":""},{"line_number":83,"context_line":""},{"line_number":84,"context_line":"class DiskFileMetadataUnavailable(DiskFileError):"},{"line_number":85,"context_line":"    # the DiskFile exists but could not be opened for some transient reason"},{"line_number":86,"context_line":"    pass"},{"line_number":87,"context_line":""},{"line_number":88,"context_line":""}],"source_content_type":"text/x-python","patch_set":8,"id":"44044d01_e4219f01","line":85,"in_reply_to":"3a33f88b_fc155ef9","updated":"2024-05-16 11:11:02.000000000","message":"Done","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"0407cd4c4fd725db62a80cd730fd69c4ad03eef8","unresolved":true,"context_lines":[{"line_number":82,"context_line":""},{"line_number":83,"context_line":""},{"line_number":84,"context_line":"class DiskFileMetadataUnavailable(DiskFileError):"},{"line_number":85,"context_line":"    # the DiskFile exists but could not be opened for some transient reason"},{"line_number":86,"context_line":"    pass"},{"line_number":87,"context_line":""},{"line_number":88,"context_line":""}],"source_content_type":"text/x-python","patch_set":8,"id":"3a33f88b_fc155ef9","line":85,"in_reply_to":"69a5782c_edcc6ee8","updated":"2024-03-05 10:23:59.000000000","message":"I didn\u0027t know that, but TIL https://peps.python.org/pep-0257/#what-is-a-docstring","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"1e554aafa477faa26df4cdea0180e786be1060f2","unresolved":true,"context_lines":[{"line_number":81,"context_line":"    pass"},{"line_number":82,"context_line":""},{"line_number":83,"context_line":""},{"line_number":84,"context_line":"class DiskFileStateChanged(DiskFileError):"},{"line_number":85,"context_line":"    \"\"\""},{"line_number":86,"context_line":"    Raised when state of a DiskFile changes while it is being opened (e.g. the"},{"line_number":87,"context_line":"    list of on-disk files changes). Retrying the DiskFile interface may"}],"source_content_type":"text/x-python","patch_set":12,"id":"207ff491_d5e7f59c","line":84,"updated":"2024-05-17 09:13:38.000000000","message":"I\u0027ve lived with this for 48 hours and already wondering whether DiskFileUnavailable might be better? (Note: just \u0027Unavailable\u0027, not \u0027MetadataUnavailable\u0027.) And document it to mean \"the DiskFile may exist but it wasn\u0027t currently available to be read\")","commit_id":"6be52b6451cb3f99be134a4c4d008592bc4cd8d9"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"9748b562ab4afec8e444c528bb0d7fc5a7eb4e23","unresolved":false,"context_lines":[{"line_number":81,"context_line":"    pass"},{"line_number":82,"context_line":""},{"line_number":83,"context_line":""},{"line_number":84,"context_line":"class DiskFileStateChanged(DiskFileError):"},{"line_number":85,"context_line":"    \"\"\""},{"line_number":86,"context_line":"    Raised when state of a DiskFile changes while it is being opened (e.g. the"},{"line_number":87,"context_line":"    list of on-disk files changes). Retrying the DiskFile interface may"}],"source_content_type":"text/x-python","patch_set":12,"id":"2496e811_1c2eeaa0","line":84,"in_reply_to":"207ff491_d5e7f59c","updated":"2024-08-06 15:35:29.000000000","message":"Acknowledged","commit_id":"6be52b6451cb3f99be134a4c4d008592bc4cd8d9"}],"swift/obj/diskfile.py":[{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"c4b35d98d7a9ebc8800e113bf1958fd14a6d6aca","unresolved":true,"context_lines":[{"line_number":223,"context_line":"            logging.exception(msg, _get_filename(fd))"},{"line_number":224,"context_line":"            raise DiskFileXattrNotSupported(e)"},{"line_number":225,"context_line":"        if e.errno \u003d\u003d errno.ENOENT:"},{"line_number":226,"context_line":"            raise DiskFileNotExist()"},{"line_number":227,"context_line":"        # TODO: we might want to re-raise errors that don\u0027t denote a missing"},{"line_number":228,"context_line":"        # xattr here.  Seems to be ENODATA on linux and ENOATTR on BSD/OSX."},{"line_number":229,"context_line":""}],"source_content_type":"text/x-python","patch_set":2,"id":"25527967_976e7a44","line":226,"updated":"2024-02-22 17:43:18.000000000","message":"perhaps overly specific since the fd may be a metadata file","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"03fb03b66e5e0a58a8fe9367b743bc35c32cb526","unresolved":false,"context_lines":[{"line_number":223,"context_line":"            logging.exception(msg, _get_filename(fd))"},{"line_number":224,"context_line":"            raise DiskFileXattrNotSupported(e)"},{"line_number":225,"context_line":"        if e.errno \u003d\u003d errno.ENOENT:"},{"line_number":226,"context_line":"            raise DiskFileNotExist()"},{"line_number":227,"context_line":"        # TODO: we might want to re-raise errors that don\u0027t denote a missing"},{"line_number":228,"context_line":"        # xattr here.  Seems to be ENODATA on linux and ENOATTR on BSD/OSX."},{"line_number":229,"context_line":""}],"source_content_type":"text/x-python","patch_set":2,"id":"8ffc025b_8a312e45","line":226,"in_reply_to":"25527967_976e7a44","updated":"2024-02-23 13:11:08.000000000","message":"Done","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"c4b35d98d7a9ebc8800e113bf1958fd14a6d6aca","unresolved":true,"context_lines":[{"line_number":2865,"context_line":"                          format"},{"line_number":2866,"context_line":"        \"\"\""},{"line_number":2867,"context_line":"        try:"},{"line_number":2868,"context_line":"            self._metafile_metadata \u003d self._failsafe_read_metadata("},{"line_number":2869,"context_line":"                meta_file, meta_file,"},{"line_number":2870,"context_line":"                add_missing_checksum\u003dmodernize)"},{"line_number":2871,"context_line":"            if ctype_file and ctype_file !\u003d meta_file:"}],"source_content_type":"text/x-python","patch_set":2,"id":"6010c51a_335e555f","line":2868,"updated":"2024-02-22 17:43:18.000000000","message":"i wonder if it\u0027s just me that\u0027s surprised a method named _failesafe will still raise exceptions...\n\ni guess the name is about the auto-quarantine behavior","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"03fb03b66e5e0a58a8fe9367b743bc35c32cb526","unresolved":false,"context_lines":[{"line_number":2865,"context_line":"                          format"},{"line_number":2866,"context_line":"        \"\"\""},{"line_number":2867,"context_line":"        try:"},{"line_number":2868,"context_line":"            self._metafile_metadata \u003d self._failsafe_read_metadata("},{"line_number":2869,"context_line":"                meta_file, meta_file,"},{"line_number":2870,"context_line":"                add_missing_checksum\u003dmodernize)"},{"line_number":2871,"context_line":"            if ctype_file and ctype_file !\u003d meta_file:"}],"source_content_type":"text/x-python","patch_set":2,"id":"e9e56f83_aa77c59f","line":2868,"in_reply_to":"6010c51a_335e555f","updated":"2024-02-23 13:11:08.000000000","message":"Done","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"c4b35d98d7a9ebc8800e113bf1958fd14a6d6aca","unresolved":true,"context_lines":[{"line_number":2875,"context_line":"            # absence of an expected meta file is not evidence that the object"},{"line_number":2876,"context_line":"            # has been deleted: it can be that a concurrent request has"},{"line_number":2877,"context_line":"            # replaced the expected meta file with a newer one."},{"line_number":2878,"context_line":"            raise DiskFileMetadataUnavailable"},{"line_number":2879,"context_line":""},{"line_number":2880,"context_line":"    def _construct_from_data_file(self, data_file, meta_file, ctype_file,"},{"line_number":2881,"context_line":"                                  current_time, modernize\u003dFalse,"}],"source_content_type":"text/x-python","patch_set":2,"id":"5b8e5e00_12c96bd0","line":2878,"updated":"2024-02-22 17:43:18.000000000","message":"something about having to re-write our own exceptions is some kind of smell, but this may very well be the most correct way to fix this bug given the constraints.","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"03fb03b66e5e0a58a8fe9367b743bc35c32cb526","unresolved":false,"context_lines":[{"line_number":2875,"context_line":"            # absence of an expected meta file is not evidence that the object"},{"line_number":2876,"context_line":"            # has been deleted: it can be that a concurrent request has"},{"line_number":2877,"context_line":"            # replaced the expected meta file with a newer one."},{"line_number":2878,"context_line":"            raise DiskFileMetadataUnavailable"},{"line_number":2879,"context_line":""},{"line_number":2880,"context_line":"    def _construct_from_data_file(self, data_file, meta_file, ctype_file,"},{"line_number":2881,"context_line":"                                  current_time, modernize\u003dFalse,"}],"source_content_type":"text/x-python","patch_set":2,"id":"b1d2e844_ffdc6e98","line":2878,"in_reply_to":"233ac1e8_dc3e9e79","updated":"2024-02-23 13:11:08.000000000","message":"Done","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"8f0235b4255392e7460824b734094017a4fbf45e","unresolved":true,"context_lines":[{"line_number":2875,"context_line":"            # absence of an expected meta file is not evidence that the object"},{"line_number":2876,"context_line":"            # has been deleted: it can be that a concurrent request has"},{"line_number":2877,"context_line":"            # replaced the expected meta file with a newer one."},{"line_number":2878,"context_line":"            raise DiskFileMetadataUnavailable"},{"line_number":2879,"context_line":""},{"line_number":2880,"context_line":"    def _construct_from_data_file(self, data_file, meta_file, ctype_file,"},{"line_number":2881,"context_line":"                                  current_time, modernize\u003dFalse,"}],"source_content_type":"text/x-python","patch_set":2,"id":"233ac1e8_dc3e9e79","line":2878,"in_reply_to":"5b8e5e00_12c96bd0","updated":"2024-02-22 18:38:45.000000000","message":"For me the smell isn\u0027t so much rewriting the exception, but the sense of inversion of severity. DiskFileNotExist \"feels worse\" than DiskFileMetadataUnavailable.\n\n I wanted read_metadata to raise DiskFileMetadataUnavailable (sounds reasonable?) and then escalate that to DiskFileNotExist when the file is a data file, but there\u0027s a bunch of call sites for read_metadata :/\n\nI\u0027ll ponder it some more with fresh eyes tomorrow.","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"03fb03b66e5e0a58a8fe9367b743bc35c32cb526","unresolved":true,"context_lines":[{"line_number":210,"context_line":""},{"line_number":211,"context_line":"    :returns: dictionary of metadata"},{"line_number":212,"context_line":"    :raises DiskFileXattrNotSupported: if the filesystem does not support xattr"},{"line_number":213,"context_line":"    :raises DiskFileMetadataUnavailable: if the file metadata could not be read"},{"line_number":214,"context_line":"    :raises DiskFileBadMetadataChecksum: if the checksum of the read metadata"},{"line_number":215,"context_line":"        does not match the stored checksum"},{"line_number":216,"context_line":"    \"\"\""}],"source_content_type":"text/x-python","patch_set":4,"id":"ddae519c_5419cef2","line":213,"updated":"2024-02-23 13:11:08.000000000","message":"note, we do NOT raise DiskFileNotExist here because that would be presuming the file is a data file.","commit_id":"43c3cdd956ffd7d8270c9fc6ec27a96fdac3167d"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2311de931d684f39a2d8a2a04015e60454a56100","unresolved":false,"context_lines":[{"line_number":210,"context_line":""},{"line_number":211,"context_line":"    :returns: dictionary of metadata"},{"line_number":212,"context_line":"    :raises DiskFileXattrNotSupported: if the filesystem does not support xattr"},{"line_number":213,"context_line":"    :raises DiskFileMetadataUnavailable: if the file metadata could not be read"},{"line_number":214,"context_line":"    :raises DiskFileBadMetadataChecksum: if the checksum of the read metadata"},{"line_number":215,"context_line":"        does not match the stored checksum"},{"line_number":216,"context_line":"    \"\"\""}],"source_content_type":"text/x-python","patch_set":4,"id":"54cb45f1_cfa70f35","line":213,"in_reply_to":"ddae519c_5419cef2","updated":"2024-05-16 11:11:02.000000000","message":"Acknowledged","commit_id":"43c3cdd956ffd7d8270c9fc6ec27a96fdac3167d"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"03fb03b66e5e0a58a8fe9367b743bc35c32cb526","unresolved":true,"context_lines":[{"line_number":267,"context_line":"    return _decode_metadata(metadata, metadata_written_by_py3)"},{"line_number":268,"context_line":""},{"line_number":269,"context_line":""},{"line_number":270,"context_line":"def read_metadata(fd, add_missing_checksum\u003dFalse):"},{"line_number":271,"context_line":"    \"\"\""},{"line_number":272,"context_line":"    Helper function to read the pickled metadata from an object file."},{"line_number":273,"context_line":""}],"source_content_type":"text/x-python","patch_set":4,"id":"807e22ca_7a39f402","line":270,"updated":"2024-02-23 13:11:08.000000000","message":"I feel I need to leave this function as-is i.e. raising DiskFileNotExist and just call through to read_file_metadata, for the callers that do use this to read a data file, and for out of tree callers.","commit_id":"43c3cdd956ffd7d8270c9fc6ec27a96fdac3167d"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"82478c9cd57e652443d69b273d03239f21239697","unresolved":true,"context_lines":[{"line_number":267,"context_line":"    return _decode_metadata(metadata, metadata_written_by_py3)"},{"line_number":268,"context_line":""},{"line_number":269,"context_line":""},{"line_number":270,"context_line":"def read_metadata(fd, add_missing_checksum\u003dFalse):"},{"line_number":271,"context_line":"    \"\"\""},{"line_number":272,"context_line":"    Helper function to read the pickled metadata from an object file."},{"line_number":273,"context_line":""}],"source_content_type":"text/x-python","patch_set":4,"id":"81464b65_94c7513f","line":270,"in_reply_to":"807e22ca_7a39f402","updated":"2024-02-23 21:08:58.000000000","message":"\"as-is\" - the existing read_metadata became the more descriptive read_file_metadata and this new wrapper replaces the existing read_metadata name to preserve the existing behavior transparently.  love it.","commit_id":"43c3cdd956ffd7d8270c9fc6ec27a96fdac3167d"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2311de931d684f39a2d8a2a04015e60454a56100","unresolved":false,"context_lines":[{"line_number":267,"context_line":"    return _decode_metadata(metadata, metadata_written_by_py3)"},{"line_number":268,"context_line":""},{"line_number":269,"context_line":""},{"line_number":270,"context_line":"def read_metadata(fd, add_missing_checksum\u003dFalse):"},{"line_number":271,"context_line":"    \"\"\""},{"line_number":272,"context_line":"    Helper function to read the pickled metadata from an object file."},{"line_number":273,"context_line":""}],"source_content_type":"text/x-python","patch_set":4,"id":"27c11018_71a5129d","line":270,"in_reply_to":"81464b65_94c7513f","updated":"2024-05-16 11:11:02.000000000","message":"Acknowledged","commit_id":"43c3cdd956ffd7d8270c9fc6ec27a96fdac3167d"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"03fb03b66e5e0a58a8fe9367b743bc35c32cb526","unresolved":true,"context_lines":[{"line_number":288,"context_line":"    try:"},{"line_number":289,"context_line":"        return read_file_metadata(fd, add_missing_checksum)"},{"line_number":290,"context_line":"    except DiskFileMetadataUnavailable:"},{"line_number":291,"context_line":"        raise DiskFileNotExist()"},{"line_number":292,"context_line":""},{"line_number":293,"context_line":""},{"line_number":294,"context_line":"def write_metadata(fd, metadata, xattr_size\u003d65536):"}],"source_content_type":"text/x-python","patch_set":4,"id":"5d513ae3_4d8eb64a","line":291,"updated":"2024-02-23 13:11:08.000000000","message":"we DO raise DiskFileNotExist here because this function always has - it just escalates the exception assuming the file is a data file","commit_id":"43c3cdd956ffd7d8270c9fc6ec27a96fdac3167d"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"82478c9cd57e652443d69b273d03239f21239697","unresolved":false,"context_lines":[{"line_number":288,"context_line":"    try:"},{"line_number":289,"context_line":"        return read_file_metadata(fd, add_missing_checksum)"},{"line_number":290,"context_line":"    except DiskFileMetadataUnavailable:"},{"line_number":291,"context_line":"        raise DiskFileNotExist()"},{"line_number":292,"context_line":""},{"line_number":293,"context_line":""},{"line_number":294,"context_line":"def write_metadata(fd, metadata, xattr_size\u003d65536):"}],"source_content_type":"text/x-python","patch_set":4,"id":"da1388e5_a54f1627","line":291,"in_reply_to":"5d513ae3_4d8eb64a","updated":"2024-02-23 21:08:58.000000000","message":"Acknowledged","commit_id":"43c3cdd956ffd7d8270c9fc6ec27a96fdac3167d"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"82478c9cd57e652443d69b273d03239f21239697","unresolved":true,"context_lines":[{"line_number":274,"context_line":"    The only difference from ``read_file_metadata`` is that this function"},{"line_number":275,"context_line":"    raises ``DiskFileNotExist`` when the file cannot be read. That is only"},{"line_number":276,"context_line":"    appropriate if the file is a data file. For meta files callers should use"},{"line_number":277,"context_line":"    ``read_file_metadata`` which raises ``DiskFileMetadataUnavailable``."},{"line_number":278,"context_line":""},{"line_number":279,"context_line":"    :param fd: file descriptor or filename to load the metadata from"},{"line_number":280,"context_line":"    :param add_missing_checksum: if set and checksum is missing, add it"}],"source_content_type":"text/x-python","patch_set":6,"id":"2baa19d9_8991d7b3","line":277,"updated":"2024-02-23 21:08:58.000000000","message":"ah, that sounds good","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2311de931d684f39a2d8a2a04015e60454a56100","unresolved":false,"context_lines":[{"line_number":274,"context_line":"    The only difference from ``read_file_metadata`` is that this function"},{"line_number":275,"context_line":"    raises ``DiskFileNotExist`` when the file cannot be read. That is only"},{"line_number":276,"context_line":"    appropriate if the file is a data file. For meta files callers should use"},{"line_number":277,"context_line":"    ``read_file_metadata`` which raises ``DiskFileMetadataUnavailable``."},{"line_number":278,"context_line":""},{"line_number":279,"context_line":"    :param fd: file descriptor or filename to load the metadata from"},{"line_number":280,"context_line":"    :param add_missing_checksum: if set and checksum is missing, add it"}],"source_content_type":"text/x-python","patch_set":6,"id":"91f1296c_5a25f777","line":277,"in_reply_to":"2baa19d9_8991d7b3","updated":"2024-05-16 11:11:02.000000000","message":"Acknowledged","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"82478c9cd57e652443d69b273d03239f21239697","unresolved":true,"context_lines":[{"line_number":2740,"context_line":"        else:"},{"line_number":2741,"context_line":"            try:"},{"line_number":2742,"context_line":"                metadata \u003d self._read_and_validate_metadata(ts_file, ts_file)"},{"line_number":2743,"context_line":"            except (DiskFileQuarantined, DiskFileMetadataUnavailable):"},{"line_number":2744,"context_line":"                # If the tombstone\u0027s corrupted, quarantine it and pretend it"},{"line_number":2745,"context_line":"                # wasn\u0027t there"},{"line_number":2746,"context_line":"                exc \u003d DiskFileNotExist()"}],"source_content_type":"text/x-python","patch_set":6,"id":"aa155324_fa8875dd","line":2743,"updated":"2024-02-23 21:08:58.000000000","message":"interesting; tombstones sure do have metadata - i guess previously a DiskFileNotExist because of listdir/PUT race would just sort of bubble out as is.","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"1e554aafa477faa26df4cdea0180e786be1060f2","unresolved":false,"context_lines":[{"line_number":2740,"context_line":"        else:"},{"line_number":2741,"context_line":"            try:"},{"line_number":2742,"context_line":"                metadata \u003d self._read_and_validate_metadata(ts_file, ts_file)"},{"line_number":2743,"context_line":"            except (DiskFileQuarantined, DiskFileMetadataUnavailable):"},{"line_number":2744,"context_line":"                # If the tombstone\u0027s corrupted, quarantine it and pretend it"},{"line_number":2745,"context_line":"                # wasn\u0027t there"},{"line_number":2746,"context_line":"                exc \u003d DiskFileNotExist()"}],"source_content_type":"text/x-python","patch_set":6,"id":"98a40e24_da19d985","line":2743,"in_reply_to":"82dc2171_8878c4bd","updated":"2024-05-17 09:13:38.000000000","message":"Done","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"c1076bebd37aaf4a9c3bd32db2787829f4417d37","unresolved":true,"context_lines":[{"line_number":2740,"context_line":"        else:"},{"line_number":2741,"context_line":"            try:"},{"line_number":2742,"context_line":"                metadata \u003d self._read_and_validate_metadata(ts_file, ts_file)"},{"line_number":2743,"context_line":"            except (DiskFileQuarantined, DiskFileMetadataUnavailable):"},{"line_number":2744,"context_line":"                # If the tombstone\u0027s corrupted, quarantine it and pretend it"},{"line_number":2745,"context_line":"                # wasn\u0027t there"},{"line_number":2746,"context_line":"                exc \u003d DiskFileNotExist()"}],"source_content_type":"text/x-python","patch_set":6,"id":"f61e6200_b067a74e","line":2743,"in_reply_to":"aa155324_fa8875dd","updated":"2024-03-04 19:36:23.000000000","message":"I\u0027m not convinced this is right. This is only called from `open`, and the appropriate response there depends way too much on what\u0027s *now* on disk that caused the .ts to get cleaned up -- why don\u0027t we let `DiskFileMetadataUnavailable` bubble out and leave it to whoever called `open` to figure out what to do about that?\n\nWhat are the practical differences between us raising `DiskFileDeleted` w/ meta vs  `DiskFileNotExist`? Which headers change, and in response to which verbs? `X-Backend-Timestamp` in at least some cases; are there others?","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"0407cd4c4fd725db62a80cd730fd69c4ad03eef8","unresolved":true,"context_lines":[{"line_number":2740,"context_line":"        else:"},{"line_number":2741,"context_line":"            try:"},{"line_number":2742,"context_line":"                metadata \u003d self._read_and_validate_metadata(ts_file, ts_file)"},{"line_number":2743,"context_line":"            except (DiskFileQuarantined, DiskFileMetadataUnavailable):"},{"line_number":2744,"context_line":"                # If the tombstone\u0027s corrupted, quarantine it and pretend it"},{"line_number":2745,"context_line":"                # wasn\u0027t there"},{"line_number":2746,"context_line":"                exc \u003d DiskFileNotExist()"}],"source_content_type":"text/x-python","patch_set":6,"id":"82dc2171_8878c4bd","line":2743,"in_reply_to":"f61e6200_b067a74e","updated":"2024-03-05 10:23:59.000000000","message":"I don\u0027t think I have changed any behavior here. Before, the DiskFileNotExist was raised in read_metadata and not caught here. Now, DiskFileMetadataUnavailable is raised in read_metadata, caught here and morphed to DiskFileNotExist.\n\n\u003e why don\u0027t we let DiskFileMetadataUnavailable bubble out and leave it to\n\u003e whoever called open to figure out what to do about that?\n\nThat\u0027s beyond the scope of this patch. But FWIW, the caller might retry the open (we might want to raise something like DiskFileTransientError to indicate \"retry may work\") or return 503 rather than 404.\n\nSimilarly with HEADs, GETs a retry might work, and with POSTs I think we could actually proceed rather than returning a 503 (POSTs always end up consistent). It\u0027s just not what I was trying to achieve with this patch.","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"82478c9cd57e652443d69b273d03239f21239697","unresolved":true,"context_lines":[{"line_number":2741,"context_line":"            try:"},{"line_number":2742,"context_line":"                metadata \u003d self._read_and_validate_metadata(ts_file, ts_file)"},{"line_number":2743,"context_line":"            except (DiskFileQuarantined, DiskFileMetadataUnavailable):"},{"line_number":2744,"context_line":"                # If the tombstone\u0027s corrupted, quarantine it and pretend it"},{"line_number":2745,"context_line":"                # wasn\u0027t there"},{"line_number":2746,"context_line":"                exc \u003d DiskFileNotExist()"},{"line_number":2747,"context_line":"            else:"}],"source_content_type":"text/x-python","patch_set":6,"id":"4a261ec2_4509c791","line":2744,"updated":"2024-02-23 21:08:58.000000000","message":"if the tombstone\u0027s corrupted/quarantined or missing - pretend it wasn\u0027t there.","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2311de931d684f39a2d8a2a04015e60454a56100","unresolved":false,"context_lines":[{"line_number":2741,"context_line":"            try:"},{"line_number":2742,"context_line":"                metadata \u003d self._read_and_validate_metadata(ts_file, ts_file)"},{"line_number":2743,"context_line":"            except (DiskFileQuarantined, DiskFileMetadataUnavailable):"},{"line_number":2744,"context_line":"                # If the tombstone\u0027s corrupted, quarantine it and pretend it"},{"line_number":2745,"context_line":"                # wasn\u0027t there"},{"line_number":2746,"context_line":"                exc \u003d DiskFileNotExist()"},{"line_number":2747,"context_line":"            else:"}],"source_content_type":"text/x-python","patch_set":6,"id":"4974d0fc_d2a7fbd9","line":2744,"in_reply_to":"4a261ec2_4509c791","updated":"2024-05-16 11:11:02.000000000","message":"Acknowledged","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"82478c9cd57e652443d69b273d03239f21239697","unresolved":true,"context_lines":[{"line_number":2839,"context_line":"        return obj_size"},{"line_number":2840,"context_line":""},{"line_number":2841,"context_line":"    def _read_and_validate_metadata(self, source, quarantine_filename\u003dNone,"},{"line_number":2842,"context_line":"                                    add_missing_checksum\u003dFalse):"},{"line_number":2843,"context_line":"        \"\"\""},{"line_number":2844,"context_line":"        Read metadata from source object file. In case of failure, quarantine"},{"line_number":2845,"context_line":"        the file."}],"source_content_type":"text/x-python","patch_set":6,"id":"18bf0580_a5d9f46a","line":2842,"updated":"2024-02-23 21:08:58.000000000","message":"this method name is way better - nice drive-by - thanks!","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2311de931d684f39a2d8a2a04015e60454a56100","unresolved":false,"context_lines":[{"line_number":2839,"context_line":"        return obj_size"},{"line_number":2840,"context_line":""},{"line_number":2841,"context_line":"    def _read_and_validate_metadata(self, source, quarantine_filename\u003dNone,"},{"line_number":2842,"context_line":"                                    add_missing_checksum\u003dFalse):"},{"line_number":2843,"context_line":"        \"\"\""},{"line_number":2844,"context_line":"        Read metadata from source object file. In case of failure, quarantine"},{"line_number":2845,"context_line":"        the file."}],"source_content_type":"text/x-python","patch_set":6,"id":"cb55b89f_04861f9c","line":2842,"in_reply_to":"18bf0580_a5d9f46a","updated":"2024-05-16 11:11:02.000000000","message":"Acknowledged","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"82478c9cd57e652443d69b273d03239f21239697","unresolved":true,"context_lines":[{"line_number":2857,"context_line":"        :raises DiskFileMetadataUnavailable: if the file metadata could not be"},{"line_number":2858,"context_line":"            read"},{"line_number":2859,"context_line":"        :raises DiskFileQuarantined: if an error occurred that caused the file"},{"line_number":2860,"context_line":"            to be quarantined"},{"line_number":2861,"context_line":"        \"\"\""},{"line_number":2862,"context_line":"        try:"},{"line_number":2863,"context_line":"            return read_file_metadata(source, add_missing_checksum)"}],"source_content_type":"text/x-python","patch_set":6,"id":"39910385_7b9f4bd2","line":2860,"updated":"2024-02-23 21:08:58.000000000","message":"better doco!?  you\u0027re a saint.\n\ni guess there\u0027s actually a behavior change where this will not ever directly raise DiskFileNotExists anymore","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2311de931d684f39a2d8a2a04015e60454a56100","unresolved":false,"context_lines":[{"line_number":2857,"context_line":"        :raises DiskFileMetadataUnavailable: if the file metadata could not be"},{"line_number":2858,"context_line":"            read"},{"line_number":2859,"context_line":"        :raises DiskFileQuarantined: if an error occurred that caused the file"},{"line_number":2860,"context_line":"            to be quarantined"},{"line_number":2861,"context_line":"        \"\"\""},{"line_number":2862,"context_line":"        try:"},{"line_number":2863,"context_line":"            return read_file_metadata(source, add_missing_checksum)"}],"source_content_type":"text/x-python","patch_set":6,"id":"6f353227_2ae974cd","line":2860,"in_reply_to":"39910385_7b9f4bd2","updated":"2024-05-16 11:11:02.000000000","message":"Acknowledged","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"82478c9cd57e652443d69b273d03239f21239697","unresolved":true,"context_lines":[{"line_number":2920,"context_line":"                add_missing_checksum\u003dmodernize)"},{"line_number":2921,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":2922,"context_line":"            # not expected because an open file descriptor was passed, but"},{"line_number":2923,"context_line":"            # handle it just in case"},{"line_number":2924,"context_line":"            raise DiskFileNotExist()"},{"line_number":2925,"context_line":""},{"line_number":2926,"context_line":"        self._metadata \u003d {}"}],"source_content_type":"text/x-python","patch_set":6,"id":"56a91e5f_2741915d","line":2923,"updated":"2024-02-23 21:08:58.000000000","message":"oh, interesting...","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2311de931d684f39a2d8a2a04015e60454a56100","unresolved":false,"context_lines":[{"line_number":2920,"context_line":"                add_missing_checksum\u003dmodernize)"},{"line_number":2921,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":2922,"context_line":"            # not expected because an open file descriptor was passed, but"},{"line_number":2923,"context_line":"            # handle it just in case"},{"line_number":2924,"context_line":"            raise DiskFileNotExist()"},{"line_number":2925,"context_line":""},{"line_number":2926,"context_line":"        self._metadata \u003d {}"}],"source_content_type":"text/x-python","patch_set":6,"id":"900817d8_30d7fe98","line":2923,"in_reply_to":"56a91e5f_2741915d","updated":"2024-05-16 11:11:02.000000000","message":"Acknowledged","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"82478c9cd57e652443d69b273d03239f21239697","unresolved":true,"context_lines":[{"line_number":2927,"context_line":"        if meta_file:"},{"line_number":2928,"context_line":"            self._metafile_metadata \u003d self._read_and_validate_metadata("},{"line_number":2929,"context_line":"                meta_file, meta_file,"},{"line_number":2930,"context_line":"                add_missing_checksum\u003dmodernize)"},{"line_number":2931,"context_line":"            if ctype_file and ctype_file !\u003d meta_file:"},{"line_number":2932,"context_line":"                self._merge_content_type_metadata(ctype_file)"},{"line_number":2933,"context_line":"            sys_metadata \u003d dict("}],"source_content_type":"text/x-python","patch_set":6,"id":"cbd716f8_94bb1e1c","line":2930,"updated":"2024-02-23 21:08:58.000000000","message":"i guess this is where we hit the actual race - and now we raise the very specific DiskFileMetadataUnavailable","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2311de931d684f39a2d8a2a04015e60454a56100","unresolved":false,"context_lines":[{"line_number":2927,"context_line":"        if meta_file:"},{"line_number":2928,"context_line":"            self._metafile_metadata \u003d self._read_and_validate_metadata("},{"line_number":2929,"context_line":"                meta_file, meta_file,"},{"line_number":2930,"context_line":"                add_missing_checksum\u003dmodernize)"},{"line_number":2931,"context_line":"            if ctype_file and ctype_file !\u003d meta_file:"},{"line_number":2932,"context_line":"                self._merge_content_type_metadata(ctype_file)"},{"line_number":2933,"context_line":"            sys_metadata \u003d dict("}],"source_content_type":"text/x-python","patch_set":6,"id":"9079071f_f1b09c44","line":2930,"in_reply_to":"55525d4e_16fd054f","updated":"2024-05-16 11:11:02.000000000","message":"Acknowledged","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7233,"name":"Matthew Oliver","email":"matt@oliver.net.au","username":"mattoliverau"},"change_message_id":"04381368e95dbfc801c087c341259762038d4ba5","unresolved":true,"context_lines":[{"line_number":2927,"context_line":"        if meta_file:"},{"line_number":2928,"context_line":"            self._metafile_metadata \u003d self._read_and_validate_metadata("},{"line_number":2929,"context_line":"                meta_file, meta_file,"},{"line_number":2930,"context_line":"                add_missing_checksum\u003dmodernize)"},{"line_number":2931,"context_line":"            if ctype_file and ctype_file !\u003d meta_file:"},{"line_number":2932,"context_line":"                self._merge_content_type_metadata(ctype_file)"},{"line_number":2933,"context_line":"            sys_metadata \u003d dict("}],"source_content_type":"text/x-python","patch_set":6,"id":"55525d4e_16fd054f","line":2930,"in_reply_to":"cbd716f8_94bb1e1c","updated":"2024-02-26 05:50:48.000000000","message":"And OK there is no catch for it here because we want it to bubble up. And will be caught by the object server and delt with. Which is where the 503\u0027s are raised or swallowed for the PUT case.","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2311de931d684f39a2d8a2a04015e60454a56100","unresolved":true,"context_lines":[{"line_number":2920,"context_line":"            fp \u003d open(data_file, \u0027rb\u0027)"},{"line_number":2921,"context_line":"        except IOError as e:"},{"line_number":2922,"context_line":"            if e.errno \u003d\u003d errno.ENOENT:"},{"line_number":2923,"context_line":"                raise DiskFileStateChanged()"},{"line_number":2924,"context_line":"            raise"},{"line_number":2925,"context_line":"        self._datafile_metadata \u003d self._read_and_validate_metadata("},{"line_number":2926,"context_line":"            fp, data_file,"}],"source_content_type":"text/x-python","patch_set":9,"id":"045b8ae3_750c939b","line":2923,"updated":"2024-05-16 11:11:02.000000000","message":"here\u0027s the significant change w.r.t. patchset 8 - we\u0027ll now also raise DiskFileStateChanged if the data file was removed e.g. concurrent PUT","commit_id":"578b34f00f8ab228568f92c6a95fdf416d1f2039"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"9748b562ab4afec8e444c528bb0d7fc5a7eb4e23","unresolved":false,"context_lines":[{"line_number":2920,"context_line":"            fp \u003d open(data_file, \u0027rb\u0027)"},{"line_number":2921,"context_line":"        except IOError as e:"},{"line_number":2922,"context_line":"            if e.errno \u003d\u003d errno.ENOENT:"},{"line_number":2923,"context_line":"                raise DiskFileStateChanged()"},{"line_number":2924,"context_line":"            raise"},{"line_number":2925,"context_line":"        self._datafile_metadata \u003d self._read_and_validate_metadata("},{"line_number":2926,"context_line":"            fp, data_file,"}],"source_content_type":"text/x-python","patch_set":9,"id":"52bd30b3_0f620f8d","line":2923,"in_reply_to":"045b8ae3_750c939b","updated":"2024-08-06 15:35:29.000000000","message":"Acknowledged","commit_id":"578b34f00f8ab228568f92c6a95fdf416d1f2039"},{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"7868ebb7ad650329c3ce4cdec8e22f74a0bbf32f","unresolved":true,"context_lines":[{"line_number":2912,"context_line":"        :param modernize: whether to update the on-disk files to the newest"},{"line_number":2913,"context_line":"                          format"},{"line_number":2914,"context_line":"        :returns: an opened data file pointer"},{"line_number":2915,"context_line":"        :raises DiskFileStateChanged: if the on-disk files could not be read."},{"line_number":2916,"context_line":"        :raises DiskFileError: various exceptions from"},{"line_number":2917,"context_line":"                    :func:`swift.obj.diskfile.DiskFile._verify_data_file`"},{"line_number":2918,"context_line":"        \"\"\""}],"source_content_type":"text/x-python","patch_set":10,"id":"75092193_dec03b49","line":2915,"updated":"2024-05-16 16:14:33.000000000","message":"Technically, a type of `DiskFileError` -- but sure, may as well call it out.","commit_id":"94dc568a7a54eba6c8f4adbee7c80e2a266d74c3"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"1e554aafa477faa26df4cdea0180e786be1060f2","unresolved":true,"context_lines":[{"line_number":2912,"context_line":"        :param modernize: whether to update the on-disk files to the newest"},{"line_number":2913,"context_line":"                          format"},{"line_number":2914,"context_line":"        :returns: an opened data file pointer"},{"line_number":2915,"context_line":"        :raises DiskFileStateChanged: if the on-disk files could not be read."},{"line_number":2916,"context_line":"        :raises DiskFileError: various exceptions from"},{"line_number":2917,"context_line":"                    :func:`swift.obj.diskfile.DiskFile._verify_data_file`"},{"line_number":2918,"context_line":"        \"\"\""}],"source_content_type":"text/x-python","patch_set":10,"id":"e0732461_cad83a18","line":2915,"in_reply_to":"75092193_dec03b49","updated":"2024-05-17 09:13:38.000000000","message":"yes but not ``from :func:`swift.obj.diskfile.DiskFile._verify_data_file```\n\nmaybe the next line should be improved","commit_id":"94dc568a7a54eba6c8f4adbee7c80e2a266d74c3"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"9748b562ab4afec8e444c528bb0d7fc5a7eb4e23","unresolved":false,"context_lines":[{"line_number":2912,"context_line":"        :param modernize: whether to update the on-disk files to the newest"},{"line_number":2913,"context_line":"                          format"},{"line_number":2914,"context_line":"        :returns: an opened data file pointer"},{"line_number":2915,"context_line":"        :raises DiskFileStateChanged: if the on-disk files could not be read."},{"line_number":2916,"context_line":"        :raises DiskFileError: various exceptions from"},{"line_number":2917,"context_line":"                    :func:`swift.obj.diskfile.DiskFile._verify_data_file`"},{"line_number":2918,"context_line":"        \"\"\""}],"source_content_type":"text/x-python","patch_set":10,"id":"59e770f3_9c56897a","line":2915,"in_reply_to":"e0732461_cad83a18","updated":"2024-08-06 15:35:29.000000000","message":"Done","commit_id":"94dc568a7a54eba6c8f4adbee7c80e2a266d74c3"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"6ae5641eda6288886f2efc70d466ead2860e4c2e","unresolved":true,"context_lines":[{"line_number":269,"context_line":"    return _decode_metadata(metadata, metadata_written_by_py3)"},{"line_number":270,"context_line":""},{"line_number":271,"context_line":""},{"line_number":272,"context_line":"def read_metadata(fd, add_missing_checksum\u003dFalse):"},{"line_number":273,"context_line":"    \"\"\""},{"line_number":274,"context_line":"    Helper function to read the pickled metadata from an object data file."},{"line_number":275,"context_line":""}],"source_content_type":"text/x-python","patch_set":11,"id":"80cc4f20_bc5ad375","line":272,"updated":"2024-05-16 16:19:51.000000000","message":"I\u0027ve left this as it is because it\u0027s a public DiskFile function so should continue to raise the same exception type","commit_id":"a58117194ea79ca94463648bb31da61268173308"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"88429ebae88ee244b55c4c144975401697d6125e","unresolved":true,"context_lines":[{"line_number":269,"context_line":"    return _decode_metadata(metadata, metadata_written_by_py3)"},{"line_number":270,"context_line":""},{"line_number":271,"context_line":""},{"line_number":272,"context_line":"def read_metadata(fd, add_missing_checksum\u003dFalse):"},{"line_number":273,"context_line":"    \"\"\""},{"line_number":274,"context_line":"    Helper function to read the pickled metadata from an object data file."},{"line_number":275,"context_line":""}],"source_content_type":"text/x-python","patch_set":11,"id":"bcf079db_8348097b","line":272,"in_reply_to":"1a4e6c47_f8294e2c","updated":"2024-05-17 09:17:49.000000000","message":"I guess if we consider it a *bug* that this function raises DiskFileNotExist then we could change it??","commit_id":"a58117194ea79ca94463648bb31da61268173308"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"1e554aafa477faa26df4cdea0180e786be1060f2","unresolved":true,"context_lines":[{"line_number":269,"context_line":"    return _decode_metadata(metadata, metadata_written_by_py3)"},{"line_number":270,"context_line":""},{"line_number":271,"context_line":""},{"line_number":272,"context_line":"def read_metadata(fd, add_missing_checksum\u003dFalse):"},{"line_number":273,"context_line":"    \"\"\""},{"line_number":274,"context_line":"    Helper function to read the pickled metadata from an object data file."},{"line_number":275,"context_line":""}],"source_content_type":"text/x-python","patch_set":11,"id":"1a4e6c47_f8294e2c","line":272,"in_reply_to":"203d3e71_b74b9397","updated":"2024-05-17 09:13:38.000000000","message":"Yep, I\u0027m distinguishing between \"I\u0027m just trying to speculatively read this path\" and \"I\u0027m trying to read a path that I just listed\".\n\nAlso, I don\u0027t know what out-of-tree code may be raising/expecting DiskFileNotExist. We could get round that by raising something new that *inherits* from DiskFileNotExist. But it seems odd to have a specialisation of DiskFileNotExist that is raised when maybe it does exist.\n\nFWIW swift_object_info calls read_metadata but I don\u0027t think it catches DiskFileNotExist, but is an example of this interface being used outside of the object server context. (BTW, also a bug I think because it only reads the data file??)\n\nIf I didn\u0027t care about out-of-tree I\u0027d perhaps have this revert to be the single function and have it raise DiskFileUnavailable","commit_id":"a58117194ea79ca94463648bb31da61268173308"},{"author":{"_account_id":7233,"name":"Matthew Oliver","email":"matt@oliver.net.au","username":"mattoliverau"},"change_message_id":"e5325f515b69f2e07edeca960232ec2f5fb1afff","unresolved":true,"context_lines":[{"line_number":269,"context_line":"    return _decode_metadata(metadata, metadata_written_by_py3)"},{"line_number":270,"context_line":""},{"line_number":271,"context_line":""},{"line_number":272,"context_line":"def read_metadata(fd, add_missing_checksum\u003dFalse):"},{"line_number":273,"context_line":"    \"\"\""},{"line_number":274,"context_line":"    Helper function to read the pickled metadata from an object data file."},{"line_number":275,"context_line":""}],"source_content_type":"text/x-python","patch_set":11,"id":"f6052f36_1ab0ab22","line":272,"in_reply_to":"648d5e32_37dded34","updated":"2025-05-20 00:07:16.000000000","message":"agree. It\u0027s a public interface, let\u0027s not get bogged down and just leave it.","commit_id":"a58117194ea79ca94463648bb31da61268173308"},{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"6109f760e96646bb49231b38165b447ee5c7ce9b","unresolved":true,"context_lines":[{"line_number":269,"context_line":"    return _decode_metadata(metadata, metadata_written_by_py3)"},{"line_number":270,"context_line":""},{"line_number":271,"context_line":""},{"line_number":272,"context_line":"def read_metadata(fd, add_missing_checksum\u003dFalse):"},{"line_number":273,"context_line":"    \"\"\""},{"line_number":274,"context_line":"    Helper function to read the pickled metadata from an object data file."},{"line_number":275,"context_line":""}],"source_content_type":"text/x-python","patch_set":11,"id":"203d3e71_b74b9397","line":272,"in_reply_to":"80cc4f20_bc5ad375","updated":"2024-05-16 18:22:05.000000000","message":"I was going to push back on this -- the quiet error translation feels a little weird to me -- but I think I see the logic: the caller told us explicitly, \"give me the metadata for this specific file,\" so translating `ENOENT` to `DiskFileNotExist` seems reasonable.","commit_id":"a58117194ea79ca94463648bb31da61268173308"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"9748b562ab4afec8e444c528bb0d7fc5a7eb4e23","unresolved":true,"context_lines":[{"line_number":269,"context_line":"    return _decode_metadata(metadata, metadata_written_by_py3)"},{"line_number":270,"context_line":""},{"line_number":271,"context_line":""},{"line_number":272,"context_line":"def read_metadata(fd, add_missing_checksum\u003dFalse):"},{"line_number":273,"context_line":"    \"\"\""},{"line_number":274,"context_line":"    Helper function to read the pickled metadata from an object data file."},{"line_number":275,"context_line":""}],"source_content_type":"text/x-python","patch_set":11,"id":"648d5e32_37dded34","line":272,"in_reply_to":"bcf079db_8348097b","updated":"2024-08-06 15:35:29.000000000","message":"revisiting this after 2 months...I\u0027m inclined to leave this as it is: we have a public function that for historic reasons needs to raise DiskFileNotExist, but we tweak the internal exception type.","commit_id":"a58117194ea79ca94463648bb31da61268173308"},{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"6109f760e96646bb49231b38165b447ee5c7ce9b","unresolved":true,"context_lines":[{"line_number":1621,"context_line":"        if not filenames:"},{"line_number":1622,"context_line":"            raise DiskFileNotExist()"},{"line_number":1623,"context_line":"        try:"},{"line_number":1624,"context_line":"            metadata \u003d read_metadata(os.path.join(object_path, filenames[-1]))"},{"line_number":1625,"context_line":"        except EOFError:"},{"line_number":1626,"context_line":"            raise DiskFileNotExist()"},{"line_number":1627,"context_line":"        try:"}],"source_content_type":"text/x-python","patch_set":11,"id":"910008f9_f5b85e7b","line":1624,"updated":"2024-05-16 18:22:05.000000000","message":"OK, so here we\u0027ve got the possibility that we know we had some filenames, then they disappear because there was a race with a write, and we raise `DiskFileNotExist` despite the problem *really* being that newer data *does* exist...\n\nSide note: I\u0027m rather curious about why https://github.com/openstack/swift/commit/a80c720a added that `except EOFError`... I\u0027m not convinced that `DiskFileNotExist` is right there, either.","commit_id":"a58117194ea79ca94463648bb31da61268173308"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"1e554aafa477faa26df4cdea0180e786be1060f2","unresolved":true,"context_lines":[{"line_number":1621,"context_line":"        if not filenames:"},{"line_number":1622,"context_line":"            raise DiskFileNotExist()"},{"line_number":1623,"context_line":"        try:"},{"line_number":1624,"context_line":"            metadata \u003d read_metadata(os.path.join(object_path, filenames[-1]))"},{"line_number":1625,"context_line":"        except EOFError:"},{"line_number":1626,"context_line":"            raise DiskFileNotExist()"},{"line_number":1627,"context_line":"        try:"}],"source_content_type":"text/x-python","patch_set":11,"id":"efe99aea_d08008d4","line":1624,"in_reply_to":"910008f9_f5b85e7b","updated":"2024-05-17 09:13:38.000000000","message":":( yes. There\u0027s likely scope for further improvement. I\u0027d like to restrict this patch to fixing the client facing 404s.","commit_id":"a58117194ea79ca94463648bb31da61268173308"},{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"6109f760e96646bb49231b38165b447ee5c7ce9b","unresolved":true,"context_lines":[{"line_number":1628,"context_line":"            account, container, obj \u003d split_path("},{"line_number":1629,"context_line":"                metadata.get(\u0027name\u0027, \u0027\u0027), 3, 3, True)"},{"line_number":1630,"context_line":"        except ValueError:"},{"line_number":1631,"context_line":"            raise DiskFileNotExist()"},{"line_number":1632,"context_line":"        df \u003d self.diskfile_cls(self, dev_path, partition, account, container,"},{"line_number":1633,"context_line":"                               obj, policy\u003dpolicy, **kwargs)"},{"line_number":1634,"context_line":"        return df, filenames"}],"source_content_type":"text/x-python","patch_set":11,"id":"84ce6308_aa7857d1","line":1631,"updated":"2024-05-16 18:22:05.000000000","message":"This seems like it ought to trip a quarantine...","commit_id":"a58117194ea79ca94463648bb31da61268173308"},{"author":{"_account_id":7233,"name":"Matthew Oliver","email":"matt@oliver.net.au","username":"mattoliverau"},"change_message_id":"e5325f515b69f2e07edeca960232ec2f5fb1afff","unresolved":true,"context_lines":[{"line_number":1628,"context_line":"            account, container, obj \u003d split_path("},{"line_number":1629,"context_line":"                metadata.get(\u0027name\u0027, \u0027\u0027), 3, 3, True)"},{"line_number":1630,"context_line":"        except ValueError:"},{"line_number":1631,"context_line":"            raise DiskFileNotExist()"},{"line_number":1632,"context_line":"        df \u003d self.diskfile_cls(self, dev_path, partition, account, container,"},{"line_number":1633,"context_line":"                               obj, policy\u003dpolicy, **kwargs)"},{"line_number":1634,"context_line":"        return df, filenames"}],"source_content_type":"text/x-python","patch_set":11,"id":"089ef321_389a20eb","line":1631,"in_reply_to":"84ce6308_aa7857d1","updated":"2025-05-20 00:07:16.000000000","message":"Maybe we should write a possible bug or improvement for this so we don\u0027t loose this statement.","commit_id":"a58117194ea79ca94463648bb31da61268173308"},{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"f2e44be5c5542c6561d44245507149b52d108246","unresolved":true,"context_lines":[{"line_number":2833,"context_line":"        \"\"\""},{"line_number":2834,"context_line":"        try:"},{"line_number":2835,"context_line":"            return read_metadata(source, add_missing_checksum)"},{"line_number":2836,"context_line":"        except (DiskFileXattrNotSupported, DiskFileNotExist):"},{"line_number":2837,"context_line":"            raise"},{"line_number":2838,"context_line":"        except DiskFileBadMetadataChecksum as err:"},{"line_number":2839,"context_line":"            raise self._quarantine(quarantine_filename, str(err))"}],"source_content_type":"text/x-python","patch_set":12,"id":"0046b71d_7548dfb6","side":"PARENT","line":2836,"range":{"start_line":2836,"start_character":43,"end_line":2836,"end_character":59},"updated":"2024-05-16 18:37:19.000000000","message":"Hmm... another way we could\u0027ve approached this would be to translate `DiskFileNotExist` -\u003e `DiskFileStateChanged` here... IDK which I prefer: that or the little stub `read_metadata` function... It just feels a little weird to me that we wouldn\u0027t be using the more \"public\" interface internally.","commit_id":"bf206ed2fe2285ebdafa06058aca88ddd1e93739"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"1e554aafa477faa26df4cdea0180e786be1060f2","unresolved":true,"context_lines":[{"line_number":2833,"context_line":"        \"\"\""},{"line_number":2834,"context_line":"        try:"},{"line_number":2835,"context_line":"            return read_metadata(source, add_missing_checksum)"},{"line_number":2836,"context_line":"        except (DiskFileXattrNotSupported, DiskFileNotExist):"},{"line_number":2837,"context_line":"            raise"},{"line_number":2838,"context_line":"        except DiskFileBadMetadataChecksum as err:"},{"line_number":2839,"context_line":"            raise self._quarantine(quarantine_filename, str(err))"}],"source_content_type":"text/x-python","patch_set":12,"id":"20f8d18b_f44cac36","side":"PARENT","line":2836,"range":{"start_line":2836,"start_character":43,"end_line":2836,"end_character":59},"in_reply_to":"0046b71d_7548dfb6","updated":"2024-05-17 09:13:38.000000000","message":"ha! I considered that too. In the end I decided that it would look weird to assert the DiskFile does not exist but then downgrade that to well-maybe-it-does.\n\nLooking at where ``DiskFileNotExist`` is *caught* I inferred that it was intended to convey that the abstraction of an object on disk doesn\u0027t exist (although it\u0027s not documented as such).\n\nI also considered sticking with ``_read_file_metadata`` raising ``DiskFileMetadataUnavailable`` and then translating that to ``DiskFileStateChanged`` here (given the context, that\u0027s how we interpret failing to read a file here) and translating to ``DiskFileNotExist`` in read_metadata (in that context, continue to raise what we always have).\n\nThat does feel the most precise set of descriptions but also seemed overly complicated.","commit_id":"bf206ed2fe2285ebdafa06058aca88ddd1e93739"}],"swift/obj/server.py":[{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"c4b35d98d7a9ebc8800e113bf1958fd14a6d6aca","unresolved":true,"context_lines":[{"line_number":810,"context_line":"        except (DiskFileNotExist, DiskFileQuarantined,"},{"line_number":811,"context_line":"                DiskFileMetadataUnavailable):"},{"line_number":812,"context_line":"            orig_metadata \u003d {}"},{"line_number":813,"context_line":"            orig_timestamp \u003d Timestamp(0)"},{"line_number":814,"context_line":""},{"line_number":815,"context_line":"        # Checks for If-None-Match"},{"line_number":816,"context_line":"        if request.if_none_match is not None and orig_metadata:"}],"source_content_type":"text/x-python","patch_set":2,"id":"b4e2f827_4d7834c1","line":813,"updated":"2024-02-22 17:43:18.000000000","message":"hrm... yeah this one is tricky - we\u0027re going to replace both the old .data and the old .meta with a newer .data; so probably not the end of the world to supress the listdir/readxattr race","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2a6c2bc275b3683c1721b78617b102c096f60a56","unresolved":true,"context_lines":[{"line_number":810,"context_line":"        except (DiskFileNotExist, DiskFileQuarantined,"},{"line_number":811,"context_line":"                DiskFileMetadataUnavailable):"},{"line_number":812,"context_line":"            orig_metadata \u003d {}"},{"line_number":813,"context_line":"            orig_timestamp \u003d Timestamp(0)"},{"line_number":814,"context_line":""},{"line_number":815,"context_line":"        # Checks for If-None-Match"},{"line_number":816,"context_line":"        if request.if_none_match is not None and orig_metadata:"}],"source_content_type":"text/x-python","patch_set":2,"id":"009134a3_fd204436","line":813,"in_reply_to":"b4e2f827_4d7834c1","updated":"2024-02-23 12:13:15.000000000","message":"I managed to convince myself that, unlike DELETE, the PUT case doesn\u0027t use any metadata that would be in a .meta file - it only uses the data file timestamp and the etag, so it doesn\u0027t matter if the meta file gets read or not.","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"c4b35d98d7a9ebc8800e113bf1958fd14a6d6aca","unresolved":true,"context_lines":[{"line_number":816,"context_line":"        if request.if_none_match is not None and orig_metadata:"},{"line_number":817,"context_line":"            if \u0027*\u0027 in request.if_none_match:"},{"line_number":818,"context_line":"                # File exists already so return 412"},{"line_number":819,"context_line":"                raise HTTPPreconditionFailed(request\u003drequest)"},{"line_number":820,"context_line":"            if orig_metadata.get(\u0027ETag\u0027) in request.if_none_match:"},{"line_number":821,"context_line":"                # The current ETag matches, so raise 412"},{"line_number":822,"context_line":"                raise HTTPPreconditionFailed(request\u003drequest)"}],"source_content_type":"text/x-python","patch_set":2,"id":"d3169549_26492fb4","line":819,"updated":"2024-02-22 17:43:18.000000000","message":"hrmm this may be case where using the original .data file timestamp/metadata might not be so bad","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"7868ebb7ad650329c3ce4cdec8e22f74a0bbf32f","unresolved":true,"context_lines":[{"line_number":816,"context_line":"        if request.if_none_match is not None and orig_metadata:"},{"line_number":817,"context_line":"            if \u0027*\u0027 in request.if_none_match:"},{"line_number":818,"context_line":"                # File exists already so return 412"},{"line_number":819,"context_line":"                raise HTTPPreconditionFailed(request\u003drequest)"},{"line_number":820,"context_line":"            if orig_metadata.get(\u0027ETag\u0027) in request.if_none_match:"},{"line_number":821,"context_line":"                # The current ETag matches, so raise 412"},{"line_number":822,"context_line":"                raise HTTPPreconditionFailed(request\u003drequest)"}],"source_content_type":"text/x-python","patch_set":2,"id":"2b3e7f61_bb70e508","line":819,"in_reply_to":"40bff250_c4da39e1","updated":"2024-05-16 16:14:33.000000000","message":"\u003e I wonder if we ever need the metafile to be read when handling a PUT\n\nIt\u0027s for the sake of cleaning up old expiry queue entries -- maybe we could skip it? But it would increase the chances that the queue entry becomes stuck, causing 412s until a reclaim age.","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"82478c9cd57e652443d69b273d03239f21239697","unresolved":true,"context_lines":[{"line_number":816,"context_line":"        if request.if_none_match is not None and orig_metadata:"},{"line_number":817,"context_line":"            if \u0027*\u0027 in request.if_none_match:"},{"line_number":818,"context_line":"                # File exists already so return 412"},{"line_number":819,"context_line":"                raise HTTPPreconditionFailed(request\u003drequest)"},{"line_number":820,"context_line":"            if orig_metadata.get(\u0027ETag\u0027) in request.if_none_match:"},{"line_number":821,"context_line":"                # The current ETag matches, so raise 412"},{"line_number":822,"context_line":"                raise HTTPPreconditionFailed(request\u003drequest)"}],"source_content_type":"text/x-python","patch_set":2,"id":"ab880db3_cbc0d2bd","line":819,"in_reply_to":"77188add_bb703e51","updated":"2024-02-23 21:08:58.000000000","message":"but do we execute L804 if L803 raises `MetadataUnavailable` - or do we end up with `orig_timestamp \u003d Timestamp(0)` as set on L813\n\nI\u0027m assuming we managed to *read* open the diskfile, maybe disk_file.data_timestamp is already available.\n\nhttps://review.opendev.org/c/openstack/swift/+/910029","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2311de931d684f39a2d8a2a04015e60454a56100","unresolved":true,"context_lines":[{"line_number":816,"context_line":"        if request.if_none_match is not None and orig_metadata:"},{"line_number":817,"context_line":"            if \u0027*\u0027 in request.if_none_match:"},{"line_number":818,"context_line":"                # File exists already so return 412"},{"line_number":819,"context_line":"                raise HTTPPreconditionFailed(request\u003drequest)"},{"line_number":820,"context_line":"            if orig_metadata.get(\u0027ETag\u0027) in request.if_none_match:"},{"line_number":821,"context_line":"                # The current ETag matches, so raise 412"},{"line_number":822,"context_line":"                raise HTTPPreconditionFailed(request\u003drequest)"}],"source_content_type":"text/x-python","patch_set":2,"id":"40bff250_c4da39e1","line":819,"in_reply_to":"ab880db3_cbc0d2bd","updated":"2024-05-16 11:11:02.000000000","message":"I think there is an issue here that the follow ups try to fix:\n\n- failure to open the meta file (having succeeded to open the data file) causes the timestamp to be assumed 0, which isn\u0027t safe if there is in fact a data file.\n\nI think the issue pre-exists this patch and is related but separate: previously failing to open the meta file caused DiskFileNotExist to be raised with the same outcome.\n\nThinking it about it again, I wonder if we ever *need* the metafile to be read when handling a PUT - perhaps we need an option to open the diskfile *data file only*? But, follow-on issue..","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2a6c2bc275b3683c1721b78617b102c096f60a56","unresolved":true,"context_lines":[{"line_number":816,"context_line":"        if request.if_none_match is not None and orig_metadata:"},{"line_number":817,"context_line":"            if \u0027*\u0027 in request.if_none_match:"},{"line_number":818,"context_line":"                # File exists already so return 412"},{"line_number":819,"context_line":"                raise HTTPPreconditionFailed(request\u003drequest)"},{"line_number":820,"context_line":"            if orig_metadata.get(\u0027ETag\u0027) in request.if_none_match:"},{"line_number":821,"context_line":"                # The current ETag matches, so raise 412"},{"line_number":822,"context_line":"                raise HTTPPreconditionFailed(request\u003drequest)"}],"source_content_type":"text/x-python","patch_set":2,"id":"77188add_bb703e51","line":819,"in_reply_to":"d3169549_26492fb4","updated":"2024-02-23 12:13:15.000000000","message":"PUT *does* use the data file timestamp (line 804) as does DELETE. I had to remind myself that this needs to be the case for ssync replication to work: it must be possible to replay the PUT and DELETE verbs out of order w.r.t. a POST.","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"c4b35d98d7a9ebc8800e113bf1958fd14a6d6aca","unresolved":true,"context_lines":[{"line_number":1140,"context_line":"            resp \u003d HTTPNotFound(request\u003drequest, headers\u003dheaders,"},{"line_number":1141,"context_line":"                                conditional_response\u003dTrue)"},{"line_number":1142,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":1143,"context_line":"            resp \u003d HTTPServiceUnavailable(request\u003drequest)"},{"line_number":1144,"context_line":"        return resp"},{"line_number":1145,"context_line":""},{"line_number":1146,"context_line":"    @public"}],"source_content_type":"text/x-python","patch_set":2,"id":"34a9e119_0aa7b1e1","line":1143,"updated":"2024-02-22 17:43:18.000000000","message":"ok, this is GET case","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2a6c2bc275b3683c1721b78617b102c096f60a56","unresolved":false,"context_lines":[{"line_number":1140,"context_line":"            resp \u003d HTTPNotFound(request\u003drequest, headers\u003dheaders,"},{"line_number":1141,"context_line":"                                conditional_response\u003dTrue)"},{"line_number":1142,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":1143,"context_line":"            resp \u003d HTTPServiceUnavailable(request\u003drequest)"},{"line_number":1144,"context_line":"        return resp"},{"line_number":1145,"context_line":""},{"line_number":1146,"context_line":"    @public"}],"source_content_type":"text/x-python","patch_set":2,"id":"36f8dae4_47ce254d","line":1143,"in_reply_to":"34a9e119_0aa7b1e1","updated":"2024-02-23 12:13:15.000000000","message":"Acknowledged","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"c4b35d98d7a9ebc8800e113bf1958fd14a6d6aca","unresolved":true,"context_lines":[{"line_number":1173,"context_line":"            return HTTPNotFound(request\u003drequest, headers\u003dheaders,"},{"line_number":1174,"context_line":"                                conditional_response\u003dTrue)"},{"line_number":1175,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":1176,"context_line":"            return HTTPServiceUnavailable(request\u003drequest)"},{"line_number":1177,"context_line":"        conditional_etag \u003d resolve_etag_is_at_header(request, metadata)"},{"line_number":1178,"context_line":"        response \u003d Response(request\u003drequest, conditional_response\u003dTrue,"},{"line_number":1179,"context_line":"                            conditional_etag\u003dconditional_etag)"}],"source_content_type":"text/x-python","patch_set":2,"id":"6221897e_f6e4934f","line":1176,"updated":"2024-02-22 17:43:18.000000000","message":"ok, this is HEAD case","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2a6c2bc275b3683c1721b78617b102c096f60a56","unresolved":false,"context_lines":[{"line_number":1173,"context_line":"            return HTTPNotFound(request\u003drequest, headers\u003dheaders,"},{"line_number":1174,"context_line":"                                conditional_response\u003dTrue)"},{"line_number":1175,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":1176,"context_line":"            return HTTPServiceUnavailable(request\u003drequest)"},{"line_number":1177,"context_line":"        conditional_etag \u003d resolve_etag_is_at_header(request, metadata)"},{"line_number":1178,"context_line":"        response \u003d Response(request\u003drequest, conditional_response\u003dTrue,"},{"line_number":1179,"context_line":"                            conditional_etag\u003dconditional_etag)"}],"source_content_type":"text/x-python","patch_set":2,"id":"041d4001_a171df5c","line":1176,"in_reply_to":"6221897e_f6e4934f","updated":"2024-02-23 12:13:15.000000000","message":"Acknowledged","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"c4b35d98d7a9ebc8800e113bf1958fd14a6d6aca","unresolved":true,"context_lines":[{"line_number":1236,"context_line":"            response_class \u003d HTTPNotFound"},{"line_number":1237,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":1238,"context_line":"            # metadata may have X-Delete-At so force client to retry"},{"line_number":1239,"context_line":"            return HTTPServiceUnavailable(request\u003drequest)"},{"line_number":1240,"context_line":"        else:"},{"line_number":1241,"context_line":"            orig_timestamp \u003d disk_file.data_timestamp"},{"line_number":1242,"context_line":"            if orig_timestamp \u003c req_timestamp:"}],"source_content_type":"text/x-python","patch_set":2,"id":"048cc2a4_8d0e15d5","line":1239,"updated":"2024-02-22 17:43:18.000000000","message":"yeah, quite worth calling out I think - probably the safest thing to do","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2a6c2bc275b3683c1721b78617b102c096f60a56","unresolved":false,"context_lines":[{"line_number":1236,"context_line":"            response_class \u003d HTTPNotFound"},{"line_number":1237,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":1238,"context_line":"            # metadata may have X-Delete-At so force client to retry"},{"line_number":1239,"context_line":"            return HTTPServiceUnavailable(request\u003drequest)"},{"line_number":1240,"context_line":"        else:"},{"line_number":1241,"context_line":"            orig_timestamp \u003d disk_file.data_timestamp"},{"line_number":1242,"context_line":"            if orig_timestamp \u003c req_timestamp:"}],"source_content_type":"text/x-python","patch_set":2,"id":"e95504cd_fa0f350d","line":1239,"in_reply_to":"048cc2a4_8d0e15d5","updated":"2024-02-23 12:13:15.000000000","message":"Acknowledged","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"82478c9cd57e652443d69b273d03239f21239697","unresolved":true,"context_lines":[{"line_number":647,"context_line":"        except (DiskFileNotExist, DiskFileQuarantined):"},{"line_number":648,"context_line":"            return HTTPNotFound(request\u003drequest)"},{"line_number":649,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":650,"context_line":"            return HTTPServiceUnavailable(request\u003drequest)"},{"line_number":651,"context_line":"        orig_timestamp \u003d Timestamp(orig_metadata.get(\u0027X-Timestamp\u0027, 0))"},{"line_number":652,"context_line":"        orig_ctype_timestamp \u003d disk_file.content_type_timestamp"},{"line_number":653,"context_line":"        req_ctype_time \u003d \u00270\u0027"}],"source_content_type":"text/x-python","patch_set":6,"id":"c573e2d1_f6baf506","line":650,"updated":"2024-02-23 21:08:58.000000000","message":"POST fails to read existing meta is 503\n\nprobably correct in that the \"current\" x-delete-at is on disk in a different .meta file","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2311de931d684f39a2d8a2a04015e60454a56100","unresolved":false,"context_lines":[{"line_number":647,"context_line":"        except (DiskFileNotExist, DiskFileQuarantined):"},{"line_number":648,"context_line":"            return HTTPNotFound(request\u003drequest)"},{"line_number":649,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":650,"context_line":"            return HTTPServiceUnavailable(request\u003drequest)"},{"line_number":651,"context_line":"        orig_timestamp \u003d Timestamp(orig_metadata.get(\u0027X-Timestamp\u0027, 0))"},{"line_number":652,"context_line":"        orig_ctype_timestamp \u003d disk_file.content_type_timestamp"},{"line_number":653,"context_line":"        req_ctype_time \u003d \u00270\u0027"}],"source_content_type":"text/x-python","patch_set":6,"id":"7ff0a713_0f0abdc9","line":650,"in_reply_to":"c573e2d1_f6baf506","updated":"2024-05-16 11:11:02.000000000","message":"Acknowledged","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"82478c9cd57e652443d69b273d03239f21239697","unresolved":true,"context_lines":[{"line_number":1140,"context_line":"            resp \u003d HTTPNotFound(request\u003drequest, headers\u003dheaders,"},{"line_number":1141,"context_line":"                                conditional_response\u003dTrue)"},{"line_number":1142,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":1143,"context_line":"            resp \u003d HTTPServiceUnavailable(request\u003drequest)"},{"line_number":1144,"context_line":"        return resp"},{"line_number":1145,"context_line":""},{"line_number":1146,"context_line":"    @public"}],"source_content_type":"text/x-python","patch_set":6,"id":"2df714db_c2282b0f","line":1143,"updated":"2024-02-23 21:08:58.000000000","message":"GET case; unable to return consistent metadata - error","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"82478c9cd57e652443d69b273d03239f21239697","unresolved":true,"context_lines":[{"line_number":1173,"context_line":"            return HTTPNotFound(request\u003drequest, headers\u003dheaders,"},{"line_number":1174,"context_line":"                                conditional_response\u003dTrue)"},{"line_number":1175,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":1176,"context_line":"            return HTTPServiceUnavailable(request\u003drequest)"},{"line_number":1177,"context_line":"        conditional_etag \u003d resolve_etag_is_at_header(request, metadata)"},{"line_number":1178,"context_line":"        response \u003d Response(request\u003drequest, conditional_response\u003dTrue,"},{"line_number":1179,"context_line":"                            conditional_etag\u003dconditional_etag)"}],"source_content_type":"text/x-python","patch_set":6,"id":"3436b96a_865e87f7","line":1176,"updated":"2024-02-23 21:08:58.000000000","message":"HEAD case; same as GET","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"82478c9cd57e652443d69b273d03239f21239697","unresolved":true,"context_lines":[{"line_number":1236,"context_line":"            response_class \u003d HTTPNotFound"},{"line_number":1237,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":1238,"context_line":"            # metadata may have X-Delete-At so force client to retry"},{"line_number":1239,"context_line":"            return HTTPServiceUnavailable(request\u003drequest)"},{"line_number":1240,"context_line":"        else:"},{"line_number":1241,"context_line":"            orig_timestamp \u003d disk_file.data_timestamp"},{"line_number":1242,"context_line":"            if orig_timestamp \u003c req_timestamp:"}],"source_content_type":"text/x-python","patch_set":6,"id":"36958813_d2620a28","line":1239,"updated":"2024-02-23 21:08:58.000000000","message":"DELETE, same as POST","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"c1076bebd37aaf4a9c3bd32db2787829f4417d37","unresolved":true,"context_lines":[{"line_number":1236,"context_line":"            response_class \u003d HTTPNotFound"},{"line_number":1237,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":1238,"context_line":"            # metadata may have X-Delete-At so force client to retry"},{"line_number":1239,"context_line":"            return HTTPServiceUnavailable(request\u003drequest)"},{"line_number":1240,"context_line":"        else:"},{"line_number":1241,"context_line":"            orig_timestamp \u003d disk_file.data_timestamp"},{"line_number":1242,"context_line":"            if orig_timestamp \u003c req_timestamp:"}],"source_content_type":"text/x-python","patch_set":6,"id":"5bb1c682_ee164a80","line":1239,"in_reply_to":"36958813_d2620a28","updated":"2024-03-04 19:36:23.000000000","message":"And we don\u0027t want to do `response_class \u003d HTTPServiceUnavailable` (as one might expect given the rest of this block) because we want to bail out as soon as possible, ensuring we don\u0027t hit any of the other possible returns before L1286.","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2311de931d684f39a2d8a2a04015e60454a56100","unresolved":true,"context_lines":[{"line_number":1236,"context_line":"            response_class \u003d HTTPNotFound"},{"line_number":1237,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":1238,"context_line":"            # metadata may have X-Delete-At so force client to retry"},{"line_number":1239,"context_line":"            return HTTPServiceUnavailable(request\u003drequest)"},{"line_number":1240,"context_line":"        else:"},{"line_number":1241,"context_line":"            orig_timestamp \u003d disk_file.data_timestamp"},{"line_number":1242,"context_line":"            if orig_timestamp \u003c req_timestamp:"}],"source_content_type":"text/x-python","patch_set":6,"id":"64a4dd40_cfa4b447","line":1239,"in_reply_to":"5bb1c682_ee164a80","updated":"2024-05-16 11:11:02.000000000","message":"Done. expanded the comment to draw attention to the early return","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"9748b562ab4afec8e444c528bb0d7fc5a7eb4e23","unresolved":false,"context_lines":[{"line_number":1236,"context_line":"            response_class \u003d HTTPNotFound"},{"line_number":1237,"context_line":"        except DiskFileMetadataUnavailable:"},{"line_number":1238,"context_line":"            # metadata may have X-Delete-At so force client to retry"},{"line_number":1239,"context_line":"            return HTTPServiceUnavailable(request\u003drequest)"},{"line_number":1240,"context_line":"        else:"},{"line_number":1241,"context_line":"            orig_timestamp \u003d disk_file.data_timestamp"},{"line_number":1242,"context_line":"            if orig_timestamp \u003c req_timestamp:"}],"source_content_type":"text/x-python","patch_set":6,"id":"d808c201_15208d8d","line":1239,"in_reply_to":"64a4dd40_cfa4b447","updated":"2024-08-06 15:35:29.000000000","message":"Done","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"}],"test/unit/obj/test_diskfile.py":[{"author":{"_account_id":1179,"name":"Clay Gerrard","email":"clay.gerrard@gmail.com","username":"clay-gerrard"},"change_message_id":"9593b30a41c6d61cd8620a51db45d6f4a78b9e6e","unresolved":true,"context_lines":[{"line_number":5447,"context_line":""},{"line_number":5448,"context_line":"        with mock.patch.object(df, \u0027_get_ondisk_files\u0027, fake_get_ondisk_files):"},{"line_number":5449,"context_line":"            with self.assertRaises(DiskFileNotExist):"},{"line_number":5450,"context_line":"                df.open()"},{"line_number":5451,"context_line":""},{"line_number":5452,"context_line":"    def test_from_audit_location(self):"},{"line_number":5453,"context_line":"        df, df_data \u003d self._create_test_file("}],"source_content_type":"text/x-python","patch_set":1,"id":"69060935_110bd2ff","line":5450,"updated":"2024-02-21 16:00:56.000000000","message":"looks like a solid test!  But raising DiskFileNotExist in ENOENT on the .meta doesn\u0027t seem like the correct beahavior.  Have we already read the .data file and it\u0027s metadata by this time?\n\nIf this is happening because of concurrent POSTs the new POST is going to write the new metadata anyway.  If it\u0027s happening because of a current HEAD then a re-listdir to find the new .meta that replaced the one that got unlinked might provide a more consistent picture of the state; but you could imagine a listdir/read_xattr loop that never finishes because of continusous conurrent updates replacing the most recent .meta file.","commit_id":"8e3ad5997daedba8d0c9e75886d7c3ac9d7e478f"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2a6c2bc275b3683c1721b78617b102c096f60a56","unresolved":true,"context_lines":[{"line_number":5447,"context_line":""},{"line_number":5448,"context_line":"        with mock.patch.object(df, \u0027_get_ondisk_files\u0027, fake_get_ondisk_files):"},{"line_number":5449,"context_line":"            with self.assertRaises(DiskFileNotExist):"},{"line_number":5450,"context_line":"                df.open()"},{"line_number":5451,"context_line":""},{"line_number":5452,"context_line":"    def test_from_audit_location(self):"},{"line_number":5453,"context_line":"        df, df_data \u003d self._create_test_file("}],"source_content_type":"text/x-python","patch_set":1,"id":"faa63f84_295d12a2","line":5450,"in_reply_to":"69060935_110bd2ff","updated":"2024-02-23 12:13:15.000000000","message":"There\u0027s definitely potential for an infinite recurring race if we retry: the dir is listed in one thread, the dir contents are changed in another thread, the first thread tries to open files in its listing and they\u0027re gone. Tim\u0027s idea was to have the second thread not cleanup very recent files.\n\nI could add a companion test: if the *data* file was unlinked then expect DiskFileNotExist.","commit_id":"8e3ad5997daedba8d0c9e75886d7c3ac9d7e478f"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2311de931d684f39a2d8a2a04015e60454a56100","unresolved":false,"context_lines":[{"line_number":5447,"context_line":""},{"line_number":5448,"context_line":"        with mock.patch.object(df, \u0027_get_ondisk_files\u0027, fake_get_ondisk_files):"},{"line_number":5449,"context_line":"            with self.assertRaises(DiskFileNotExist):"},{"line_number":5450,"context_line":"                df.open()"},{"line_number":5451,"context_line":""},{"line_number":5452,"context_line":"    def test_from_audit_location(self):"},{"line_number":5453,"context_line":"        df, df_data \u003d self._create_test_file("}],"source_content_type":"text/x-python","patch_set":1,"id":"ef24f906_2749e995","line":5450,"in_reply_to":"faa63f84_295d12a2","updated":"2024-05-16 11:11:02.000000000","message":"Done","commit_id":"8e3ad5997daedba8d0c9e75886d7c3ac9d7e478f"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"2a6c2bc275b3683c1721b78617b102c096f60a56","unresolved":true,"context_lines":[{"line_number":5432,"context_line":""},{"line_number":5433,"context_line":"    def test_open_meta_file_unlinked(self):"},{"line_number":5434,"context_line":"        # if a .meta file is cleaned up while diskfile is being opened then"},{"line_number":5435,"context_line":"        # DiskFileNotExist can be raised"},{"line_number":5436,"context_line":"        ts_data \u003d self.ts()"},{"line_number":5437,"context_line":"        ts_meta1 \u003d self.ts()"},{"line_number":5438,"context_line":"        ts_meta2 \u003d self.ts()"}],"source_content_type":"text/x-python","patch_set":2,"id":"271dd179_8d4aa5e0","line":5435,"updated":"2024-02-23 12:13:15.000000000","message":"comment is wrong - and the point is that if it\u0027s only the meta file that goes missing then it\u0027s \"only\" a ``DiskFileMetadataUnavailable``","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"03fb03b66e5e0a58a8fe9367b743bc35c32cb526","unresolved":false,"context_lines":[{"line_number":5432,"context_line":""},{"line_number":5433,"context_line":"    def test_open_meta_file_unlinked(self):"},{"line_number":5434,"context_line":"        # if a .meta file is cleaned up while diskfile is being opened then"},{"line_number":5435,"context_line":"        # DiskFileNotExist can be raised"},{"line_number":5436,"context_line":"        ts_data \u003d self.ts()"},{"line_number":5437,"context_line":"        ts_meta1 \u003d self.ts()"},{"line_number":5438,"context_line":"        ts_meta2 \u003d self.ts()"}],"source_content_type":"text/x-python","patch_set":2,"id":"4b2c1505_edda5c39","line":5435,"in_reply_to":"271dd179_8d4aa5e0","updated":"2024-02-23 13:11:08.000000000","message":"Done","commit_id":"1399d2b913c90821bb50e7ca14bcac2950fba2a7"},{"author":{"_account_id":7233,"name":"Matthew Oliver","email":"matt@oliver.net.au","username":"mattoliverau"},"change_message_id":"04381368e95dbfc801c087c341259762038d4ba5","unresolved":true,"context_lines":[{"line_number":5462,"context_line":"        with df.open():"},{"line_number":5463,"context_line":"            self.assertEqual(ts_data, df.data_timestamp)"},{"line_number":5464,"context_line":"            self.assertEqual(ts_meta1, df.timestamp)"},{"line_number":5465,"context_line":"        return"},{"line_number":5466,"context_line":"        df \u003d self._simple_get_diskfile()"},{"line_number":5467,"context_line":""},{"line_number":5468,"context_line":"        orig_get_ondisk_files \u003d df._get_ondisk_files"}],"source_content_type":"text/x-python","patch_set":6,"id":"65a06624_949f1e72","line":5465,"updated":"2024-02-26 05:50:48.000000000","message":"Ahh, doesn\u0027t this return mean the rest of the test is unreachable?","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7233,"name":"Matthew Oliver","email":"matt@oliver.net.au","username":"mattoliverau"},"change_message_id":"6f5f9e98f2f8c21570a5bc0eb7a941d5c01a4386","unresolved":false,"context_lines":[{"line_number":5462,"context_line":"        with df.open():"},{"line_number":5463,"context_line":"            self.assertEqual(ts_data, df.data_timestamp)"},{"line_number":5464,"context_line":"            self.assertEqual(ts_meta1, df.timestamp)"},{"line_number":5465,"context_line":"        return"},{"line_number":5466,"context_line":"        df \u003d self._simple_get_diskfile()"},{"line_number":5467,"context_line":""},{"line_number":5468,"context_line":"        orig_get_ondisk_files \u003d df._get_ondisk_files"}],"source_content_type":"text/x-python","patch_set":6,"id":"9c7f29a0_f26b1346","line":5465,"in_reply_to":"65a06624_949f1e72","updated":"2024-02-28 00:02:13.000000000","message":"Acknowledged","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"0407cd4c4fd725db62a80cd730fd69c4ad03eef8","unresolved":false,"context_lines":[{"line_number":5462,"context_line":"        with df.open():"},{"line_number":5463,"context_line":"            self.assertEqual(ts_data, df.data_timestamp)"},{"line_number":5464,"context_line":"            self.assertEqual(ts_meta1, df.timestamp)"},{"line_number":5465,"context_line":"        return"},{"line_number":5466,"context_line":"        df \u003d self._simple_get_diskfile()"},{"line_number":5467,"context_line":""},{"line_number":5468,"context_line":"        orig_get_ondisk_files \u003d df._get_ondisk_files"}],"source_content_type":"text/x-python","patch_set":6,"id":"e18524ef_f3bb6160","line":5465,"in_reply_to":"65a06624_949f1e72","updated":"2024-03-05 10:23:59.000000000","message":"oops, there\u0027s me abusing a test to debug something and then forgetting to put the test back together :/","commit_id":"20da935f5c022f9aab81e6fc402313d4613e6c7e"}],"test/unit/obj/test_server.py":[{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"c1076bebd37aaf4a9c3bd32db2787829f4417d37","unresolved":true,"context_lines":[{"line_number":8482,"context_line":"                \u0027/sda1/p/a/c/o\u0027, environ\u003d{\u0027REQUEST_METHOD\u0027: \u0027DELETE\u0027},"},{"line_number":8483,"context_line":"                headers\u003d{\u0027X-Timestamp\u0027: delete_timestamp})"},{"line_number":8484,"context_line":"            resp \u003d req.get_response(self.object_controller)"},{"line_number":8485,"context_line":"            self.assertEqual(resp.status_int, 404)"},{"line_number":8486,"context_line":""},{"line_number":8487,"context_line":"        qdir \u003d os.path.join(self.testdir, \u0027sda1\u0027, \u0027quarantined\u0027)"},{"line_number":8488,"context_line":"        self.assertFalse(os.path.exists(qdir))"}],"source_content_type":"text/x-python","patch_set":8,"id":"17fee26a_1cae7644","line":8485,"range":{"start_line":8485,"start_character":46,"end_line":8485,"end_character":49},"updated":"2024-03-04 19:36:23.000000000","message":"This is the only test that would need to change if we let that `DiskFileMetadataUnavailable` bubble out, and I see no reason this *shouldn\u0027t* be a 503.\n\nI mean, I suppose we *do* at least get back a 404 w/ `X-Backend-Timestamp` of `delete_timestamp` today... and there\u0027s a certain logic to it. But if this were a POST, we\u0027d be getting back a 404 with *no* timestamp, rewinding time to before `existing_timestamp`!","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"0407cd4c4fd725db62a80cd730fd69c4ad03eef8","unresolved":true,"context_lines":[{"line_number":8482,"context_line":"                \u0027/sda1/p/a/c/o\u0027, environ\u003d{\u0027REQUEST_METHOD\u0027: \u0027DELETE\u0027},"},{"line_number":8483,"context_line":"                headers\u003d{\u0027X-Timestamp\u0027: delete_timestamp})"},{"line_number":8484,"context_line":"            resp \u003d req.get_response(self.object_controller)"},{"line_number":8485,"context_line":"            self.assertEqual(resp.status_int, 404)"},{"line_number":8486,"context_line":""},{"line_number":8487,"context_line":"        qdir \u003d os.path.join(self.testdir, \u0027sda1\u0027, \u0027quarantined\u0027)"},{"line_number":8488,"context_line":"        self.assertFalse(os.path.exists(qdir))"}],"source_content_type":"text/x-python","patch_set":8,"id":"766e5304_b1534ce3","line":8485,"range":{"start_line":8485,"start_character":46,"end_line":8485,"end_character":49},"in_reply_to":"17fee26a_1cae7644","updated":"2024-03-05 10:23:59.000000000","message":"If the PUT was handled momentarily later the response would be 404. If the PUT was handled momentarily earlier the response would be 409. Why shouldn\u0027t the concurrent PUT result in a 404? Seems like it\u0027s not clear-cut.\n\nIn contrast, in the case of racing POSTs, the 404 response due to the race is clearly wrong when without the race the response would be either 202 or 409.","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":7847,"name":"Alistair Coles","email":"alistairncoles@gmail.com","username":"acoles"},"change_message_id":"1e554aafa477faa26df4cdea0180e786be1060f2","unresolved":false,"context_lines":[{"line_number":8482,"context_line":"                \u0027/sda1/p/a/c/o\u0027, environ\u003d{\u0027REQUEST_METHOD\u0027: \u0027DELETE\u0027},"},{"line_number":8483,"context_line":"                headers\u003d{\u0027X-Timestamp\u0027: delete_timestamp})"},{"line_number":8484,"context_line":"            resp \u003d req.get_response(self.object_controller)"},{"line_number":8485,"context_line":"            self.assertEqual(resp.status_int, 404)"},{"line_number":8486,"context_line":""},{"line_number":8487,"context_line":"        qdir \u003d os.path.join(self.testdir, \u0027sda1\u0027, \u0027quarantined\u0027)"},{"line_number":8488,"context_line":"        self.assertFalse(os.path.exists(qdir))"}],"source_content_type":"text/x-python","patch_set":8,"id":"15df48ab_aa3f083b","line":8485,"range":{"start_line":8485,"start_character":46,"end_line":8485,"end_character":49},"in_reply_to":"74b703c7_a3c1990d","updated":"2024-05-17 09:13:38.000000000","message":"this topic is addressed in https://review.opendev.org/c/openstack/swift/+/911165?usp\u003demail","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"},{"author":{"_account_id":15343,"name":"Tim Burke","email":"tburke@nvidia.com","username":"tburke"},"change_message_id":"3a2e2cff3f1f08ddb660e66c6778c6f0632b7aa4","unresolved":true,"context_lines":[{"line_number":8482,"context_line":"                \u0027/sda1/p/a/c/o\u0027, environ\u003d{\u0027REQUEST_METHOD\u0027: \u0027DELETE\u0027},"},{"line_number":8483,"context_line":"                headers\u003d{\u0027X-Timestamp\u0027: delete_timestamp})"},{"line_number":8484,"context_line":"            resp \u003d req.get_response(self.object_controller)"},{"line_number":8485,"context_line":"            self.assertEqual(resp.status_int, 404)"},{"line_number":8486,"context_line":""},{"line_number":8487,"context_line":"        qdir \u003d os.path.join(self.testdir, \u0027sda1\u0027, \u0027quarantined\u0027)"},{"line_number":8488,"context_line":"        self.assertFalse(os.path.exists(qdir))"}],"source_content_type":"text/x-python","patch_set":8,"id":"74b703c7_a3c1990d","line":8485,"range":{"start_line":8485,"start_character":46,"end_line":8485,"end_character":49},"in_reply_to":"766e5304_b1534ce3","updated":"2024-03-05 17:41:36.000000000","message":"Like I said, I get the logic of it for this test -- but just because a 404 *could* be reasonable, doesn\u0027t make it obvious to me that 503 is *unreasonable*.\n\nPart of why I wanted to look into the PUT-POST-PUT race -- there, the 404 seems very wrong.","commit_id":"e4d5c7d4c130319abc33e9b9b3226eb499ededde"}]}
