import unreal RECIPE_FOLDER = "/Game/Agrarian/DataAssets/Recipes" EXPECTED_RECIPES = { "DA_Recipe_Campfire": { "recipe_id": "campfire", "ingredients": {"wood": 5, "stone": 8, "fiber": 2}, "result": ("campfire", 1), }, "DA_Recipe_PrimitiveShelter": { "recipe_id": "primitive_shelter", "ingredients": { "primitive_frame": 2, "primitive_wall_panel": 4, "primitive_roof_panel": 2, "hide": 2, "fiber": 6, }, "result": ("primitive_shelter", 1), }, "DA_Recipe_PrimitiveFrame": { "recipe_id": "primitive_frame", "ingredients": {"wood": 4, "fiber": 2}, "result": ("primitive_frame", 1), }, "DA_Recipe_PrimitiveWallPanel": { "recipe_id": "primitive_wall_panel", "ingredients": {"wood": 3, "fiber": 2}, "result": ("primitive_wall_panel", 1), }, "DA_Recipe_PrimitiveRoofPanel": { "recipe_id": "primitive_roof_panel", "ingredients": {"wood": 3, "fiber": 3}, "result": ("primitive_roof_panel", 1), }, "DA_Recipe_BasicTool": { "recipe_id": "basic_tool", "ingredients": {"wood": 1, "stone": 2, "fiber": 1}, "result": ("basic_tool", 1), }, "DA_Recipe_SimpleContainer": { "recipe_id": "simple_container", "ingredients": {"wood": 3, "fiber": 6, "hide": 2}, "result": ("simple_container", 1), }, "DA_Recipe_Bandage": { "recipe_id": "bandage", "ingredients": {"fiber": 3, "hide": 1}, "result": ("bandage", 1), }, } def stack_item_id(stack): return str(stack.get_editor_property("item_id")) def main(): missing = [] for asset_name, expected in EXPECTED_RECIPES.items(): path = f"{RECIPE_FOLDER}/{asset_name}" asset = unreal.EditorAssetLibrary.load_asset(path) if not asset: missing.append(f"{path} missing") continue recipe = asset.get_editor_property("recipe") recipe_id = str(recipe.get_editor_property("recipe_id")) display_name = str(recipe.get_editor_property("display_name")) craft_seconds = recipe.get_editor_property("craft_seconds") result = recipe.get_editor_property("result") ingredients = list(recipe.get_editor_property("ingredients")) if recipe_id != expected["recipe_id"]: missing.append(f"{path} recipe_id expected {expected['recipe_id']}, got {recipe_id}") if not display_name: missing.append(f"{path} display_name empty") if craft_seconds <= 0.0: missing.append(f"{path} craft_seconds must be positive") expected_result_id, expected_result_quantity = expected["result"] if stack_item_id(result) != expected_result_id: missing.append(f"{path} result id expected {expected_result_id}, got {stack_item_id(result)}") if result.get_editor_property("quantity") != expected_result_quantity: missing.append(f"{path} result quantity expected {expected_result_quantity}") if result.get_editor_property("unit_weight") <= 0.0: missing.append(f"{path} result unit weight must be positive") actual_ingredients = {stack_item_id(stack): stack for stack in ingredients} for expected_item_id, expected_quantity in expected["ingredients"].items(): stack = actual_ingredients.get(expected_item_id) if not stack: missing.append(f"{path} missing ingredient {expected_item_id}") continue if stack.get_editor_property("quantity") != expected_quantity: missing.append(f"{path} ingredient {expected_item_id} expected quantity {expected_quantity}") if stack.get_editor_property("unit_weight") <= 0.0: missing.append(f"{path} ingredient {expected_item_id} unit weight must be positive") unexpected = set(actual_ingredients.keys()) - set(expected["ingredients"].keys()) if unexpected: missing.append(f"{path} has unexpected ingredients: {sorted(unexpected)}") if missing: raise RuntimeError("Recipe definition verification failed: " + "; ".join(missing)) unreal.log("Agrarian recipe definition verification complete.") main()