From b1e79cf86dae5be62e8eb4934fa8c5670792fe08 Mon Sep 17 00:00:00 2001 From: bbassie <17990055+bbassie@users.noreply.github.com> Date: Fri, 11 Sep 2026 22:20:56 +0000 Subject: [PATCH] Send only the local state on download init The current state sent with the download request no longer includes the failed names from the previous deserialization. Stored names unknown on this instance always end up in the add list, so the deserializer recomputes the failed list from that on every download and needs no previous state. Co-Authored-By: Claude Fable 5.1 --- .../inventory_sync/module/inventory_sync.lua | 9 ++---- plugins/inventory_sync/module/serialize.lua | 28 +++++-------------- 2 files changed, 9 insertions(+), 28 deletions(-) diff --git a/plugins/inventory_sync/module/inventory_sync.lua b/plugins/inventory_sync/module/inventory_sync.lua index 89250148..c6804251 100644 --- a/plugins/inventory_sync/module/inventory_sync.lua +++ b/plugins/inventory_sync/module/inventory_sync.lua @@ -112,9 +112,7 @@ function inventory_sync.deserialize_player(player, finished_record) -- Deserialize downloaded player data local serialized_player = compat.json_to_table(finished_record.data) assert(type(serialized_player) == "table", "wrong type for serialized_player") - script_data.failed_deserialization[player.name] = serialize.deserialize_player( - player, serialized_player, script_data.failed_deserialization[player.name] - ) + script_data.failed_deserialization[player.name] = serialize.deserialize_player(player, serialized_player) -- Restore player position and driving state restore_position(player, finished_record) @@ -447,10 +445,7 @@ function inventory_sync.initiate_inventory_download(player, player_record, gener -- The plugin only sends back what differs from the current notification state local recipe_notifications if recipe_notifications_api then - local failed = script_data.failed_deserialization[player.name] - recipe_notifications = serialize.serialize_crafting_notifications( - player, failed and failed.recipe_notifications - ) + recipe_notifications = serialize.serialize_crafting_notifications(player) end clusterio_api.send_json("inventory_sync_download", { diff --git a/plugins/inventory_sync/module/serialize.lua b/plugins/inventory_sync/module/serialize.lua index 4aed3a93..0ef6705e 100644 --- a/plugins/inventory_sync/module/serialize.lua +++ b/plugins/inventory_sync/module/serialize.lua @@ -551,33 +551,27 @@ end --- @param player LuaPlayer --- @param serialized string Encoded delta against the state sent with the download request ---- @param previous_failed string[]? Recipe names that did not exist at the last deserialization --- @return string[]? failed Recipe names that do not exist -function serialize.deserialize_crafting_notifications(player, serialized, previous_failed) +function serialize.deserialize_crafting_notifications(player, serialized) --- @type CraftingNotificationDelta local delta = helpers.json_to_table(assert(helpers.decode_string(serialized))) assert(type(delta) == "table", "wrong type decoded from json_to_table") - local failed = {} - for _, recipe_name in pairs(previous_failed or {}) do - failed[recipe_name] = true - end - -- Recipes which can have a notification on this server local enabled = {} for _, recipe in pairs(player.force.recipes) do if recipe.enabled and not recipe.hidden then enabled[recipe.name] = true - failed[recipe.name] = nil end end -- Clear notifications the player has cleared elsewhere, this means "add seen notification" + local failed = {} for _, recipe_name in pairs(delta.add or {}) do if enabled[recipe_name] then player.clear_recipe_notification(recipe_name) else - failed[recipe_name] = true -- Recipe does not exist on this server + failed[#failed + 1] = recipe_name -- Recipe does not exist on this server end end @@ -585,16 +579,10 @@ function serialize.deserialize_crafting_notifications(player, serialized, previo for _, recipe_name in pairs(delta.remove or {}) do if enabled[recipe_name] then player.add_recipe_notification(recipe_name) - else - failed[recipe_name] = nil end end - local failed_names = {} - for recipe_name in pairs(failed) do - failed_names[#failed_names + 1] = recipe_name - end - return next(failed_names) and failed_names or nil + return next(failed) and failed or nil end local controller_to_name = {} @@ -800,9 +788,8 @@ end --- @param player LuaPlayer --- @param serialized SerializedPlayerData ---- @param previous_failed FailedDeserializationPlayerData? --- @return FailedDeserializationPlayerData? -function serialize.deserialize_player(player, serialized, previous_failed) +function serialize.deserialize_player(player, serialized) local failed_deserialization = {} local target_controller = defines.controllers[serialized.controller] @@ -889,9 +876,8 @@ function serialize.deserialize_player(player, serialized, previous_failed) -- Deserialize recipe notifications if recipe_notifications_api and serialized.recipe_notifications then - failed_deserialization.recipe_notifications = serialize.deserialize_crafting_notifications( - player, serialized.recipe_notifications, previous_failed and previous_failed.recipe_notifications - ) + failed_deserialization.recipe_notifications = + serialize.deserialize_crafting_notifications(player, serialized.recipe_notifications) end return next(failed_deserialization) and failed_deserialization or nil