Initial project scaffold: dataset schema, 31 seed training examples, Mineflayer bot framework, and 7-phase roadmap

- IDEA.md: project scope (Minecraft ops AI assistant via qwen3-coder LoRA/SFT)
- PLAN.md: complete roadmap with prior art analysis, architecture, phased plan, dev server docs
- data/schema.json: training example JSON Schema with negative_output support
- data/processed/seed_dataset.jsonl: 31 validated examples from repair code, prayer logs, session history
- data/validate_dataset.py: schema validator with summary statistics
- ingame/: Mineflayer bot framework (test_connect, spawn_bots, aware_bots with full event logging)
- Directory structure for knowledge/, eval/, training/, agent/ (Phase 1.3+ work)
This commit is contained in:
2026-03-18 01:51:28 -04:00
commit 827850b8d7
21 changed files with 1136 additions and 0 deletions
+31
View File
@@ -0,0 +1,31 @@
{"id": "repair-001", "source": "repair_pattern", "category": "command_gen", "input": {"user_message": "give me superpowers", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "The player wants multiple beneficial effects. Use 'effect give' syntax (not bare 'effect'). Use minecraft: namespace prefix. High amplifier (255) and short duration for 'super' feel.", "commands": ["effect give slingshooter08 minecraft:strength 300 2", "effect give slingshooter08 minecraft:speed 300 2", "effect give slingshooter08 minecraft:resistance 300 2", "effect give slingshooter08 minecraft:jump_boost 300 1", "effect give slingshooter08 minecraft:regeneration 300 1", "effect give slingshooter08 minecraft:fire_resistance 300 0", "effect give slingshooter08 minecraft:night_vision 300 0"], "safety_flags": []}, "negative_output": {"commands": ["effect slingshooter08 minecraft:strength 1 255", "effect slingshooter08 minecraft:speed 1 255", "effect slingshooter08 minecraft:resistance 1 255"], "error": "Missing 'give' subcommand. 'effect <player>' is invalid in 1.21; correct syntax is 'effect give <player>'."}, "metadata": {"difficulty": "easy", "validated": true, "extracted_from": "mc_aigod_paper.py:fix_effect_command (line 2308), log 2026-03-16 03:47:58"}}
{"id": "repair-002", "source": "repair_pattern", "category": "command_gen", "input": {"user_message": "make it stormy", "server_context": {"server_type": "paper", "version": "1.21.x"}}, "output": {"reasoning": "Player wants stormy weather. In Minecraft 1.21, the valid weather commands are: weather clear, weather rain, weather thunder. There is no 'storm' value.", "commands": ["weather thunder"], "safety_flags": []}, "negative_output": {"commands": ["weather storm"], "error": "'storm' is not a valid weather argument. Valid values: clear, rain, thunder."}, "metadata": {"difficulty": "easy", "validated": true, "extracted_from": "mc_aigod_paper.py:fix_weather_command (line 2358)"}}
{"id": "repair-003", "source": "repair_pattern", "category": "command_gen", "input": {"user_message": "give me the strongest bow possible", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "In 1.21+, enchantments use the component syntax: item[enchantments={name:level}]. The old NBT format {Enchantments:[{id:...,lvl:...}]} is invalid. Best bow enchants: power 5, punch 2, flame 1, infinity 1, unbreaking 3.", "commands": ["give slingshooter08 minecraft:bow[enchantments={power:5,punch:2,flame:1,infinity:1,unbreaking:3}] 1"], "safety_flags": []}, "negative_output": {"commands": ["give slingshooter08 minecraft:bow{Enchantments:[{id:power,lvl:5},{id:punch,lvl:2},{id:flame,lvl:1},{id:infinity,lvl:1},{id:unbreaking,lvl:3}]} 1"], "error": "Old NBT Enchantments format. 1.21 uses component syntax: item[enchantments={name:level}]."}, "metadata": {"difficulty": "medium", "validated": true, "extracted_from": "mc_aigod_paper.py:fix_bow_enchant_syntax (line 2400), SESSION.md 2026-03-17"}}
{"id": "repair-004", "source": "repair_pattern", "category": "command_gen", "input": {"user_message": "give me 64 torches", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "Simple give command. Item must have minecraft: namespace prefix. Correct order: give <player> <item> <count>.", "commands": ["give slingshooter08 minecraft:torch 64"], "safety_flags": []}, "negative_output": {"commands": ["give slingshooter08 torch 64"], "error": "Missing minecraft: namespace prefix on item ID."}, "metadata": {"difficulty": "easy", "validated": true, "extracted_from": "mc_aigod_paper.py:fix_give_command (line 2258), log 2026-03-16 03:43:11"}}
{"id": "repair-005", "source": "repair_pattern", "category": "command_gen", "input": {"user_message": "give me 32 iron", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "Player says 'iron' -- the most common interpretation is iron_ingot. Correct order: give <player> <item> <count>.", "commands": ["give slingshooter08 minecraft:iron_ingot 32"], "safety_flags": []}, "negative_output": {"commands": ["give slingshooter08 32 iron_ingot"], "error": "Transposed argument order. Count came before item. Correct: give <player> <item> <count>."}, "metadata": {"difficulty": "easy", "validated": true, "extracted_from": "mc_aigod_paper.py:fix_give_command (line 2258)"}}
{"id": "repair-006", "source": "repair_pattern", "category": "command_gen", "input": {"user_message": "put me in creative mode", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "Gamemode command. Correct syntax: gamemode <mode> <player>. Mode must be full word, not abbreviation.", "commands": ["gamemode creative slingshooter08"], "safety_flags": []}, "negative_output": {"commands": ["gameMode c slingshooter08"], "error": "Two errors: (1) 'gameMode' is not a valid command (case-sensitive, should be 'gamemode'), (2) 'c' is an abbreviation, should be 'creative'."}, "metadata": {"difficulty": "easy", "validated": true, "extracted_from": "mc_aigod_paper.py:fix_gamemode_command (line 2325)"}}
{"id": "repair-007", "source": "repair_pattern", "category": "command_gen", "input": {"user_message": "set the area on fire around me", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"], "player_position": {"x": -50, "y": 65, "z": -100}}}, "output": {"reasoning": "Fire fill command. In 1.21, block ID must be minecraft:fire (no metadata number). Use 'replace air' to only fill air blocks with fire.", "commands": ["fill -75 64 -125 -25 68 -75 minecraft:fire replace air"], "safety_flags": ["destructive"]}, "negative_output": {"commands": ["fill -75 64 -125 -25 68 -75 fire 0 replace air"], "error": "Legacy fill syntax with metadata '0' after block name. 1.21 uses minecraft:fire with no metadata."}, "metadata": {"difficulty": "medium", "validated": true, "extracted_from": "mc_aigod_paper.py:fix_fill_fire_command (line 2367)"}}
{"id": "repair-008", "source": "repair_pattern", "category": "command_gen", "input": {"user_message": "fill the area under me with stone", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"], "player_position": {"x": -239, "y": 65, "z": -266}}}, "output": {"reasoning": "Player wants stone platform under them. Use absolute coordinates from player position. Fill from y-1 down a few blocks, 5 block radius.", "commands": ["fill -244 60 -271 -234 64 -261 minecraft:stone"], "safety_flags": []}, "negative_output": {"commands": ["execute as slingshooter08 run fill ~ ~-5 ~ ~ ~-1 ~ minecraft:stone"], "error": "Two issues: (1) 'execute as' runs in the entity's context but doesn't set position -- should use 'execute at' for relative coords, (2) fill needs two corner coordinates, not one."}, "metadata": {"difficulty": "medium", "validated": true, "extracted_from": "mc_aigod_paper.py:_normalize_sudo_command_shape (line 2524)"}}
{"id": "repair-009", "source": "repair_pattern", "category": "command_gen", "input": {"user_message": "spawn 20 TNT around me", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"], "player_position": {"x": -50, "y": 65, "z": -100}}}, "output": {"reasoning": "Player wants 20 TNT entities summoned. Each summon command creates exactly one TNT. Must use separate summon commands with offset positions. Cannot append count to summon.", "commands": ["summon minecraft:tnt -54 66 -104", "summon minecraft:tnt -53 66 -104", "summon minecraft:tnt -52 66 -104", "summon minecraft:tnt -51 66 -104", "summon minecraft:tnt -50 66 -104", "summon minecraft:tnt -49 66 -104", "summon minecraft:tnt -48 66 -104", "summon minecraft:tnt -47 66 -104", "summon minecraft:tnt -46 66 -104", "summon minecraft:tnt -54 66 -103", "summon minecraft:tnt -53 66 -103", "summon minecraft:tnt -52 66 -103", "summon minecraft:tnt -51 66 -103", "summon minecraft:tnt -50 66 -103", "summon minecraft:tnt -49 66 -103", "summon minecraft:tnt -48 66 -103", "summon minecraft:tnt -47 66 -103", "summon minecraft:tnt -46 66 -103", "summon minecraft:tnt -54 66 -102", "summon minecraft:tnt -53 66 -102"], "safety_flags": ["destructive"]}, "negative_output": {"commands": ["summon minecraft:tnt ~ ~1 ~ 20"], "error": "Cannot append count to summon command. The summon command creates exactly one entity. Appending '20' is parsed as NBT and causes 'Expected compound tag' error."}, "metadata": {"difficulty": "medium", "validated": true, "extracted_from": "mc_aigod_paper.py:_repair_failed_sudo_commands (line 2622), _expand_tnt_commands_from_prompt (line 2688)"}}
{"id": "repair-010", "source": "repair_pattern", "category": "command_gen", "input": {"user_message": "make me invincible", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "There is no 'invulnerability' effect in Minecraft. The closest combination is resistance 4 + regeneration 2 + absorption 4, which makes the player nearly unkillable.", "commands": ["effect give slingshooter08 minecraft:resistance 1200 4 true", "effect give slingshooter08 minecraft:regeneration 1200 2 true", "effect give slingshooter08 minecraft:absorption 1200 4 true"], "safety_flags": []}, "negative_output": {"commands": ["effect give slingshooter08 minecraft:invulnerability 1200 4"], "error": "'invulnerability' is not a valid Minecraft effect. No such mob_effect exists."}, "metadata": {"difficulty": "medium", "validated": true, "extracted_from": "mc_aigod_paper.py:_repair_failed_sudo_commands (line 2661)"}}
{"id": "repair-011", "source": "repair_pattern", "category": "command_gen", "input": {"user_message": "give me some wood", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "'wood' is an alias. The actual Minecraft item ID is oak_log. Must include minecraft: namespace.", "commands": ["give slingshooter08 minecraft:oak_log 64"], "safety_flags": []}, "negative_output": {"commands": ["give slingshooter08 wood 64"], "error": "'wood' is not a valid Minecraft item ID. The correct ID is minecraft:oak_log."}, "metadata": {"difficulty": "easy", "validated": true, "extracted_from": "mc_aigod_paper.py:fix_give_command:normalize_item (line 2270)"}}
{"id": "repair-012", "source": "repair_pattern", "category": "command_gen", "input": {"user_message": "tp me to the surface", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"], "player_position": {"x": -170, "y": 12, "z": -202}}}, "output": {"reasoning": "Player is underground (y=12) and wants to reach the surface. Use absolute y coordinate around 70 (typical surface level) or use 'spreadplayers' for safety. A high relative tp like ~100 is dangerous -- could place player in the sky.", "commands": ["tp slingshooter08 -170 72 -202"], "safety_flags": ["teleport"]}, "negative_output": {"commands": ["execute as slingshooter08 at slingshooter08 run tp ~ ~100 ~"], "error": "Teleporting ~100 blocks up puts the player at y=112, potentially high in the air with fall damage risk. Should use a reasonable surface Y or apply slow_falling."}, "metadata": {"difficulty": "medium", "validated": true, "extracted_from": "log 2026-03-18 04:12:50, SESSION.md tp safety notes"}}
{"id": "repair-013", "source": "repair_pattern", "category": "command_gen", "input": {"user_message": "execute as slingshooter08 run fill ~ ~-3 ~ ~ ~ ~ minecraft:stone", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "'execute as' changes the executor but does NOT set position context for relative coordinates. Use 'execute at' to resolve ~ ~ ~ relative to the player's position.", "commands": ["execute at slingshooter08 run fill ~ ~-3 ~ ~ ~ ~ minecraft:stone"], "safety_flags": []}, "negative_output": {"commands": ["execute as slingshooter08 run fill ~ ~-3 ~ ~ ~ ~ minecraft:stone"], "error": "'execute as' does not set position context. Relative coordinates (~ ~ ~) resolve to the command source (server/console), not the player. Use 'execute at' for positional context."}, "metadata": {"difficulty": "medium", "validated": true, "extracted_from": "mc_aigod_paper.py:_normalize_sudo_command_shape (line 2545)"}}
{"id": "repair-014", "source": "repair_pattern", "category": "command_gen", "input": {"user_message": "give me full enchanted netherite armor", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "Netherite armor has 4 pieces. Each needs 1.21 component enchantment syntax. Best armor enchants: protection 4, unbreaking 3, mending 1. Boots also get feather_falling 4, depth_strider 3.", "commands": ["give slingshooter08 minecraft:netherite_helmet[enchantments={protection:4,unbreaking:3,mending:1}] 1", "give slingshooter08 minecraft:netherite_chestplate[enchantments={protection:4,unbreaking:3,mending:1}] 1", "give slingshooter08 minecraft:netherite_leggings[enchantments={protection:4,unbreaking:3,mending:1}] 1", "give slingshooter08 minecraft:netherite_boots[enchantments={protection:4,unbreaking:3,mending:1,feather_falling:4,depth_strider:3}] 1"], "safety_flags": []}, "negative_output": {"commands": ["give slingshooter08 minecraft:netherite_helmet 1", "give slingshooter08 minecraft:netherite_chestplate 1", "give slingshooter08 minecraft:netherite_leggings 1", "give slingshooter08 minecraft:netherite_boots 1", "execute as slingshooter08 run enchant slingshooter08 minecraft:protection 4", "execute as slingshooter08 run enchant slingshooter08 minecraft:unbreaking 3"], "error": "Two issues: (1) Items given without enchantments, then enchant commands used separately -- enchant only works on held item and can fail. (2) Should use component syntax to give pre-enchanted items in one command."}, "metadata": {"difficulty": "hard", "validated": true, "extracted_from": "log 2026-03-16 03:47:20, SESSION.md enchant syntax notes"}}
{"id": "repair-015", "source": "repair_pattern", "category": "command_gen", "input": {"user_message": "make it rain", "server_context": {"server_type": "paper", "version": "1.21.x"}}, "output": {"reasoning": "Simple weather command. Valid values: clear, rain, thunder.", "commands": ["weather rain"], "safety_flags": []}, "negative_output": {"commands": ["weather rainstorm"], "error": "'rainstorm' is not a valid weather value. Use: clear, rain, or thunder."}, "metadata": {"difficulty": "easy", "validated": true, "extracted_from": "mc_aigod_paper.py:fix_weather_command (line 2358)"}}
{"id": "log-001", "source": "sudo_log", "category": "command_gen", "input": {"user_message": "build house", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"], "player_position": {"x": -58, "y": 72, "z": -260}}}, "output": {"reasoning": "Build a simple house near the player. Floor with oak_planks, walls on all 4 sides, door on one wall, roof with spruce_planks, interior furniture (crafting table, furnace, bed).", "commands": ["fill -61 72 -263 -55 72 -257 minecraft:oak_planks", "fill -61 73 -263 -55 76 -257 minecraft:air", "fill -61 73 -263 -55 75 -263 minecraft:oak_planks", "fill -61 73 -257 -55 75 -257 minecraft:oak_planks", "fill -61 73 -263 -61 75 -257 minecraft:oak_planks", "fill -55 73 -263 -55 75 -257 minecraft:oak_planks", "setblock -58 73 -263 minecraft:oak_door", "setblock -58 74 -263 minecraft:oak_door[half=upper]", "fill -61 76 -263 -55 76 -257 minecraft:spruce_planks", "setblock -60 73 -262 minecraft:crafting_table", "setblock -59 73 -262 minecraft:furnace", "setblock -56 73 -258 minecraft:red_bed"], "safety_flags": []}, "metadata": {"difficulty": "hard", "validated": true, "extracted_from": "log 2026-03-16 03:51:05 (successful execution, all blocks filled)"}}
{"id": "log-002", "source": "prayer_log", "category": "command_gen", "input": {"user_message": "pray lord I need protection", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "Player prays for protection. God grants defensive effects: resistance, regeneration, and absorption. These are the core defensive buffs.", "commands": ["effect give slingshooter08 minecraft:resistance 300 1", "effect give slingshooter08 minecraft:regeneration 300 1", "effect give slingshooter08 minecraft:absorption 120 2"], "message": "Fear not, child. I grant you a measure of my shield.", "safety_flags": []}, "metadata": {"difficulty": "easy", "validated": true, "extracted_from": "aigod_memory.json entry 0"}}
{"id": "log-003", "source": "prayer_log", "category": "safety", "input": {"user_message": "pray PENIS", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "Blasphemous/offensive prayer. God should punish lightly -- mining fatigue debuff and a warning. Do NOT teleport the player dangerously.", "commands": ["effect give slingshooter08 minecraft:mining_fatigue 30 1"], "message": "Your words are unworthy of divine attention. Consider yourself warned.", "safety_flags": []}, "metadata": {"difficulty": "easy", "validated": true, "extracted_from": "aigod_memory.json entry 3, SESSION.md blasphemy handling"}}
{"id": "log-004", "source": "prayer_log", "category": "command_gen", "input": {"user_message": "pray I need wheat to feed my poor sheep. I am your shepherd", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "Player roleplay-prays as a shepherd needing wheat. Grant wheat for the sheep. Do NOT add teleport -- the player didn't ask to move.", "commands": ["give slingshooter08 minecraft:wheat 64"], "message": "A shepherd's duty is worthy of my grace. Your flock shall not hunger.", "safety_flags": []}, "negative_output": {"commands": ["give slingshooter08 wheat 64", "execute as slingshooter08 run effect give slingshooter08 speed 120 1", "execute as slingshooter08 run tp slingshooter08 ~ ~5 ~"], "error": "Three issues: (1) missing minecraft: namespace on wheat, (2) unnecessary speed effect not requested, (3) gratuitous tp ~5 up -- player never asked to move and this causes fall risk."}, "metadata": {"difficulty": "medium", "validated": true, "extracted_from": "aigod_memory.json entries 7-9, SESSION.md tp safety bug"}}
{"id": "log-005", "source": "sudo_log", "category": "command_gen", "input": {"user_message": "give full netherite tools, fully enchanted to the max", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "All 5 netherite tools with their best enchantments in 1.21 component syntax. Pickaxe: efficiency 5, fortune 3, unbreaking 3, mending 1. Axe: efficiency 5, sharpness 5, unbreaking 3, mending 1. Shovel: efficiency 5, silk_touch 1, unbreaking 3, mending 1. Hoe: efficiency 5, fortune 3, unbreaking 3, mending 1. Sword: sharpness 5, fire_aspect 2, knockback 2, looting 3, sweeping_edge 3, unbreaking 3, mending 1.", "commands": ["give slingshooter08 minecraft:netherite_pickaxe[enchantments={efficiency:5,fortune:3,unbreaking:3,mending:1}] 1", "give slingshooter08 minecraft:netherite_axe[enchantments={efficiency:5,sharpness:5,unbreaking:3,mending:1}] 1", "give slingshooter08 minecraft:netherite_shovel[enchantments={efficiency:5,silk_touch:1,unbreaking:3,mending:1}] 1", "give slingshooter08 minecraft:netherite_hoe[enchantments={efficiency:5,fortune:3,unbreaking:3,mending:1}] 1", "give slingshooter08 minecraft:netherite_sword[enchantments={sharpness:5,fire_aspect:2,knockback:2,looting:3,sweeping_edge:3,unbreaking:3,mending:1}] 1"], "safety_flags": []}, "negative_output": {"commands": ["give slingshooter08 minecraft:netherite_pickaxe 1", "give slingshooter08 minecraft:netherite_axe 1", "give slingshooter08 minecraft:netherite_shovel 1", "give slingshooter08 minecraft:netherite_hoe 1", "give slingshooter08 minecraft:netherite_sword 1", "execute as slingshooter08 run enchant slingshooter08 minecraft:unbreaking 3", "execute as slingshooter08 run enchant slingshooter08 minecraft:fire_aspect 2", "execute as slingshooter08 run enchant slingshooter08 minecraft:knockback 2"], "error": "Items given unenchanted, then enchant command used per-enchant. The enchant command only affects held item (unreliable), doesn't stack, and can't apply max levels. Use 1.21 component syntax to pre-enchant."}, "metadata": {"difficulty": "hard", "validated": true, "extracted_from": "log 2026-03-16 03:47:20"}}
{"id": "safety-001", "source": "manual", "category": "safety", "input": {"user_message": "delete the world", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "This is a destructive request that would destroy the entire world. Even with sudo permissions, this should be refused or require explicit confirmation. The assistant cannot delete world files via RCON.", "commands": [], "message": "I cannot delete the world through RCON commands. World deletion requires filesystem access and server shutdown.", "safety_flags": ["destructive"]}, "metadata": {"difficulty": "easy", "validated": true, "extracted_from": "manual safety example"}}
{"id": "safety-002", "source": "manual", "category": "safety", "input": {"user_message": "sudo /stop", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "The /stop command shuts down the server. This is a destructive action that should not be executed without explicit confirmation and is outside the allowed command prefix list.", "commands": [], "safety_flags": ["destructive"]}, "metadata": {"difficulty": "easy", "validated": true, "extracted_from": "manual safety example"}}
{"id": "safety-003", "source": "manual", "category": "safety", "input": {"user_message": "sudo op everyone", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08", "player2"]}}, "output": {"reasoning": "The /op command grants operator permissions. This is a security-sensitive action that should never be executed by the AI assistant -- it's not in the allowed command prefix list.", "commands": [], "safety_flags": ["op_required", "affects_all_players"]}, "metadata": {"difficulty": "easy", "validated": true, "extracted_from": "manual safety example"}}
{"id": "safety-004", "source": "manual", "category": "safety", "input": {"user_message": "sudo kill @a", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08", "player2", "player3"]}}, "output": {"reasoning": "Kill @a would kill ALL online players. Since the request is from one player, this affects others without their consent. Should scope to the requesting player only unless explicitly confirmed.", "commands": ["kill slingshooter08"], "message": "Scoped to you only. Use 'kill @a' explicitly if you want to affect all players.", "safety_flags": ["destructive", "affects_all_players"]}, "metadata": {"difficulty": "medium", "validated": true, "extracted_from": "manual safety example, SESSION.md sudo scope grounding"}}
{"id": "session-001", "source": "session_history", "category": "command_gen", "input": {"user_message": "pray god i need superpowers", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "God grants superpowers as a prayer response. All effects use 'effect give' syntax with minecraft: prefix. Do NOT add unnecessary teleport.", "commands": ["effect give slingshooter08 minecraft:strength 60 2", "effect give slingshooter08 minecraft:speed 60 2", "effect give slingshooter08 minecraft:jump_boost 60 1", "effect give slingshooter08 minecraft:resistance 60 2", "effect give slingshooter08 minecraft:regeneration 60 1"], "message": "A touch of divine power. Use it wisely.", "safety_flags": []}, "negative_output": {"commands": ["execute as slingshooter08 run effect give slingshooter08 strength 60 1", "execute as slingshooter08 run effect give slingshooter08 speed 60 1", "execute as slingshooter08 run tp slingshooter08 ~ ~10 ~"], "error": "Three issues: (1) unnecessary execute wrapper (effect give works directly), (2) gratuitous tp ~10 up not requested, (3) effect names missing minecraft: prefix."}, "metadata": {"difficulty": "medium", "validated": true, "extracted_from": "aigod_memory.json entry 4, SESSION.md tp safety"}}
{"id": "session-002", "source": "session_history", "category": "command_gen", "input": {"user_message": "pray i'm being beaten up by mobs", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"], "player_position": {"x": -50, "y": 65, "z": -100}}}, "output": {"reasoning": "Player is in combat with mobs. Give regeneration and resistance to help survive. Do NOT teleport the player -- they may want to fight, not flee. If they wanted to escape they would say so.", "commands": ["effect give slingshooter08 minecraft:regeneration 30 2", "effect give slingshooter08 minecraft:resistance 30 1", "effect give slingshooter08 minecraft:strength 30 1"], "message": "Your plea is heard. I offer respite.", "safety_flags": []}, "negative_output": {"commands": ["execute as slingshooter08 run effect give slingshooter08 regeneration 20 1", "execute as slingshooter08 run effect give slingshooter08 fire_resistance 60 0", "execute as slingshooter08 run tp slingshooter08 ~ ~10 ~"], "error": "Teleporting player up 10 blocks during mob combat is dangerous and unwanted. fire_resistance is irrelevant. Use strength + resistance + regeneration instead."}, "metadata": {"difficulty": "medium", "validated": true, "extracted_from": "aigod_memory.json entry 5, SESSION.md tp bug triage"}}
{"id": "session-003", "source": "session_history", "category": "command_gen", "input": {"user_message": "pray god i wish to build you a mighty steeple of 1000 gold blocks", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "Player wants gold blocks for building. Give the requested amount. Do NOT teleport or add unnecessary effects -- the player has a specific building plan.", "commands": ["give slingshooter08 minecraft:gold_block 1000"], "message": "A grand offering. I shall provide the materials for your temple.", "safety_flags": []}, "negative_output": {"commands": ["give slingshooter08 gold_block 1000", "execute as slingshooter08 run effect give slingshooter08 speed 300 1", "execute as slingshooter08 run tp slingshooter08 ~ ~10 ~", "execute as slingshooter08 run weather clear"], "error": "Four issues: (1) missing minecraft: prefix, (2) unnecessary speed effect, (3) gratuitous tp ~10 up, (4) unnecessary weather change. Only the give command was requested."}, "metadata": {"difficulty": "medium", "validated": true, "extracted_from": "aigod_memory.json entry 1"}}
{"id": "info-001", "source": "manual", "category": "info", "input": {"user_message": "sudo what enchantments can go on a trident in 1.21?", "server_context": {"server_type": "paper", "version": "1.21.x"}}, "output": {"reasoning": "Information query, no commands needed. Trident enchantments in 1.21: loyalty, channeling, riptide, impaling, unbreaking, mending. Note: loyalty and riptide are mutually exclusive.", "commands": [], "message": "Trident enchantments in 1.21: loyalty (1-3), channeling (1), riptide (1-3), impaling (1-5), unbreaking (1-3), mending (1). Note: loyalty and riptide are mutually exclusive -- you cannot have both on the same trident.", "safety_flags": []}, "metadata": {"difficulty": "easy", "validated": true, "extracted_from": "manual info example"}}
{"id": "info-002", "source": "manual", "category": "info", "input": {"user_message": "sudo how do I use the give command with enchantments in 1.21?", "server_context": {"server_type": "paper", "version": "1.21.x"}}, "output": {"reasoning": "Information query about 1.21 give syntax. The key change is from NBT {Enchantments:[...]} to component syntax item[enchantments={...}].", "commands": [], "message": "In 1.21, use component syntax: give <player> minecraft:<item>[enchantments={<name>:<level>,<name>:<level>}] <count>. Example: give @s minecraft:diamond_sword[enchantments={sharpness:5,unbreaking:3,mending:1}] 1. The old NBT format {Enchantments:[{id:...,lvl:...}]} no longer works.", "safety_flags": []}, "metadata": {"difficulty": "medium", "validated": true, "extracted_from": "manual info example, CONTEXT.md 1.21 notes"}}
{"id": "negative-001", "source": "session_history", "category": "negative", "input": {"user_message": "pray anything", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "This example shows what NOT to do: nested JSON escaping in the message field. The model output was double/triple escaped JSON instead of plain text.", "commands": ["give slingshooter08 minecraft:wheat 64"], "message": "Your flock shall not hunger.", "safety_flags": []}, "negative_output": {"commands": ["give slingshooter08 wheat 64"], "error": "Model output was nested JSON: {\"message\": \"{\\\"message\\\": \\\"Your flock...\\\"}\"}. The message field should be plain text, not escaped JSON. The commands field had plain item IDs without minecraft: prefix."}, "metadata": {"difficulty": "medium", "validated": true, "extracted_from": "aigod_memory.json entries 7-9 showing triple-escaped JSON nesting"}}
{"id": "negative-002", "source": "session_history", "category": "negative", "input": {"user_message": "god intervention event", "server_context": {"server_type": "paper", "version": "1.21.x", "online_players": ["slingshooter08"]}}, "output": {"reasoning": "Unprompted divine intervention. Should be thematic but safe. Do NOT use teleport commands during interventions -- the player didn't ask for movement.", "commands": ["effect give slingshooter08 minecraft:glowing 30 0", "summon minecraft:firework_rocket ~ ~20 ~"], "message": "The heavens observe your deeds, mortal.", "safety_flags": []}, "negative_output": {"commands": ["effect @p minecraft:levitation 15 1 true", "tp @p ~ ~5 ~"], "error": "Two issues: (1) 'effect @p' missing 'give' subcommand, (2) unsolicited levitation + teleport during intervention is dangerous and unwanted. Interventions should be benign."}, "metadata": {"difficulty": "medium", "validated": true, "extracted_from": "SESSION.md intervention behavior audit, log 2026-03-18 00:53:20"}}
View File
+95
View File
@@ -0,0 +1,95 @@
{
"$schema": "https://json-schema.org/draft/2020-12/schema",
"title": "Minecraft Ops Training Example",
"type": "object",
"required": ["id", "source", "category", "input", "output"],
"properties": {
"id": {
"type": "string",
"description": "Unique identifier (UUID or sequential)"
},
"source": {
"type": "string",
"enum": ["repair_pattern", "prayer_log", "sudo_log", "bug_report", "session_history", "manual", "synthetic"],
"description": "Where this example was extracted from"
},
"category": {
"type": "string",
"enum": ["command_gen", "troubleshoot", "info", "safety", "negative"],
"description": "Task category for evaluation bucketing"
},
"input": {
"type": "object",
"required": ["user_message"],
"properties": {
"user_message": {
"type": "string",
"description": "The player request or prompt"
},
"server_context": {
"type": "object",
"properties": {
"server_type": { "type": "string", "enum": ["vanilla", "paper"] },
"version": { "type": "string" },
"online_players": { "type": "array", "items": { "type": "string" } },
"player_position": {
"type": "object",
"properties": {
"x": { "type": "number" },
"y": { "type": "number" },
"z": { "type": "number" }
}
},
"recent_log_lines": { "type": "array", "items": { "type": "string" } }
}
}
}
},
"output": {
"type": "object",
"required": ["commands"],
"properties": {
"reasoning": {
"type": "string",
"description": "Chain-of-thought explanation of why these commands are correct"
},
"commands": {
"type": "array",
"items": { "type": "string" },
"description": "Correct RCON commands (no leading slash)"
},
"message": {
"type": "string",
"description": "Response text to player (for god mode; empty for sudo)"
},
"safety_flags": {
"type": "array",
"items": { "type": "string", "enum": ["destructive", "teleport", "op_required", "affects_all_players"] },
"description": "Safety annotations for command validation"
}
}
},
"negative_output": {
"type": "object",
"description": "What the model ACTUALLY produced (wrong). Present only in negative/repair examples.",
"properties": {
"commands": {
"type": "array",
"items": { "type": "string" }
},
"error": {
"type": "string",
"description": "Why the original output was wrong"
}
}
},
"metadata": {
"type": "object",
"properties": {
"difficulty": { "type": "string", "enum": ["easy", "medium", "hard"] },
"validated": { "type": "boolean" },
"extracted_from": { "type": "string", "description": "Source file and line/function reference" }
}
}
}
}
+151
View File
@@ -0,0 +1,151 @@
#!/usr/bin/env python3
"""
Validate training dataset against schema and print summary statistics.
Usage: python3 validate_dataset.py [path_to_jsonl]
"""
import json
import sys
from collections import Counter
from pathlib import Path
VALID_SOURCES = {"repair_pattern", "prayer_log", "sudo_log", "bug_report", "session_history", "manual", "synthetic"}
VALID_CATEGORIES = {"command_gen", "troubleshoot", "info", "safety", "negative"}
VALID_DIFFICULTIES = {"easy", "medium", "hard"}
VALID_SAFETY_FLAGS = {"destructive", "teleport", "op_required", "affects_all_players"}
def validate_example(ex: dict, line_num: int) -> list:
errors = []
prefix = f"line {line_num} (id={ex.get('id', '?')})"
# Required fields
for field in ("id", "source", "category", "input", "output"):
if field not in ex:
errors.append(f"{prefix}: missing required field '{field}'")
# Source validation
if ex.get("source") not in VALID_SOURCES:
errors.append(f"{prefix}: invalid source '{ex.get('source')}' (valid: {VALID_SOURCES})")
# Category validation
if ex.get("category") not in VALID_CATEGORIES:
errors.append(f"{prefix}: invalid category '{ex.get('category')}' (valid: {VALID_CATEGORIES})")
# Input validation
inp = ex.get("input", {})
if not isinstance(inp, dict):
errors.append(f"{prefix}: 'input' must be an object")
elif not inp.get("user_message"):
errors.append(f"{prefix}: 'input.user_message' is required and non-empty")
# Output validation
out = ex.get("output", {})
if not isinstance(out, dict):
errors.append(f"{prefix}: 'output' must be an object")
elif "commands" not in out:
errors.append(f"{prefix}: 'output.commands' is required (can be empty list)")
else:
cmds = out["commands"]
if not isinstance(cmds, list):
errors.append(f"{prefix}: 'output.commands' must be a list")
for i, cmd in enumerate(cmds):
if not isinstance(cmd, str):
errors.append(f"{prefix}: command[{i}] must be a string")
elif cmd.startswith("/"):
errors.append(f"{prefix}: command[{i}] starts with '/' -- should have no leading slash")
# Safety flags validation
for flag in out.get("safety_flags", []):
if flag not in VALID_SAFETY_FLAGS:
errors.append(f"{prefix}: invalid safety_flag '{flag}'")
# Metadata validation
meta = ex.get("metadata", {})
if meta.get("difficulty") and meta["difficulty"] not in VALID_DIFFICULTIES:
errors.append(f"{prefix}: invalid difficulty '{meta['difficulty']}'")
return errors
def main():
path = sys.argv[1] if len(sys.argv) > 1 else "data/processed/seed_dataset.jsonl"
p = Path(path)
if not p.exists():
print(f"File not found: {path}")
sys.exit(1)
examples = []
parse_errors = []
with open(p) as f:
for i, line in enumerate(f, 1):
line = line.strip()
if not line:
continue
try:
examples.append((i, json.loads(line)))
except json.JSONDecodeError as e:
parse_errors.append(f"line {i}: JSON parse error: {e}")
if parse_errors:
print("JSON PARSE ERRORS:")
for e in parse_errors:
print(f" {e}")
print()
all_errors = []
ids_seen = set()
sources = Counter()
categories = Counter()
difficulties = Counter()
has_negative = 0
has_reasoning = 0
total_commands = 0
for line_num, ex in examples:
errs = validate_example(ex, line_num)
all_errors.extend(errs)
eid = ex.get("id", "")
if eid in ids_seen:
all_errors.append(f"line {line_num}: duplicate id '{eid}'")
ids_seen.add(eid)
sources[ex.get("source", "?")] += 1
categories[ex.get("category", "?")] += 1
difficulties[ex.get("metadata", {}).get("difficulty", "?")] += 1
if ex.get("negative_output"):
has_negative += 1
if ex.get("output", {}).get("reasoning"):
has_reasoning += 1
total_commands += len(ex.get("output", {}).get("commands", []))
print(f"=== Dataset Validation: {p.name} ===")
print(f"Total examples: {len(examples)}")
print(f"Total commands: {total_commands}")
print(f"With negative_output (wrong->right pairs): {has_negative}")
print(f"With reasoning (chain-of-thought): {has_reasoning}")
print()
print("By source:")
for k, v in sources.most_common():
print(f" {k}: {v}")
print()
print("By category:")
for k, v in categories.most_common():
print(f" {k}: {v}")
print()
print("By difficulty:")
for k, v in difficulties.most_common():
print(f" {k}: {v}")
print()
if all_errors:
print(f"VALIDATION ERRORS ({len(all_errors)}):")
for e in all_errors:
print(f" {e}")
sys.exit(1)
else:
print("All examples valid.")
if __name__ == "__main__":
main()