import json import sys from oni_api import api_post BLUEPRINTS = { 'spom': { 'name': 'SPOM (Self-Powered Oxygen Module)', 'description': 'Standard Rodriguez SPOM: electrolyzer + hydrogen generators', 'size': {'width': 8, 'height': 6}, 'dig': {'x': -1, 'y': -1, 'width': 10, 'height': 8}, 'buildings': [ {'id': 'Electrolyzer', 'x': 3, 'y': 2}, {'id': 'GasPump', 'x': 1, 'y': 2}, {'id': 'GasPump', 'x': 5, 'y': 2}, {'id': 'HydrogenGenerator', 'x': 1, 'y': 0}, {'id': 'HydrogenGenerator', 'x': 4, 'y': 0}, {'id': 'GasFilter', 'x': 3, 'y': 0}, ], }, 'spom_mini': { 'name': 'Mini SPOM', 'description': 'Compact electrolyzer + 1 hydrogen generator for early game', 'size': {'width': 5, 'height': 4}, 'dig': {'x': -1, 'y': -1, 'width': 7, 'height': 6}, 'buildings': [ {'id': 'Electrolyzer', 'x': 2, 'y': 1}, {'id': 'GasPump', 'x': 1, 'y': 1}, {'id': 'HydrogenGenerator', 'x': 2, 'y': 0}, ], }, 'toilet_loop': { 'name': 'Bathroom Water Loop', 'description': 'Lavatory -> Water Purifier -> Lavatory closed loop', 'size': {'width': 8, 'height': 4}, 'dig': {'x': -1, 'y': -1, 'width': 10, 'height': 6}, 'buildings': [ {'id': 'Lavatory', 'x': 1, 'y': 1}, {'id': 'Lavatory', 'x': 3, 'y': 1}, {'id': 'WaterPurifier', 'x': 6, 'y': 1}, {'id': 'LiquidPump', 'x': 6, 'y': 2}, ], }, 'ranch_hatch': { 'name': 'Hatch Ranch', 'description': 'Standard hatch ranching module with feeder and incubator', 'size': {'width': 10, 'height': 6}, 'dig': {'x': -1, 'y': -1, 'width': 12, 'height': 8}, 'buildings': [ {'id': 'RanchStation', 'x': 1, 'y': 1}, {'id': 'Incubator', 'x': 4, 'y': 1}, {'id': 'StorageLocker', 'x': 8, 'y': 1}, ], }, 'farm_mealwood': { 'name': 'Mealwood Farm', 'description': 'Basic mealwood farm: 5 planter boxes + storage', 'size': {'width': 6, 'height': 4}, 'dig': {'x': -1, 'y': -1, 'width': 8, 'height': 6}, 'buildings': [ {'id': 'PlanterBox', 'x': 1, 'y': 1}, {'id': 'PlanterBox', 'x': 3, 'y': 1}, {'id': 'PlanterBox', 'x': 5, 'y': 1}, {'id': 'PlanterBox', 'x': 1, 'y': 3}, {'id': 'PlanterBox', 'x': 3, 'y': 3}, {'id': 'StorageLocker', 'x': 5, 'y': 3}, ], }, 'cooling': { 'name': 'Steam Turbine Cooler', 'description': 'Liquid cooling loop with steam turbine + aquatuner', 'size': {'width': 8, 'height': 6}, 'dig': {'x': -1, 'y': -1, 'width': 10, 'height': 8}, 'buildings': [ {'id': 'SteamTurbine', 'x': 1, 'y': 4}, {'id': 'SteamTurbine', 'x': 5, 'y': 4}, {'id': 'Aquatuner', 'x': 2, 'y': 1}, {'id': 'LiquidPump', 'x': 5, 'y': 1}, ], }, 'bedroom': { 'name': 'Barracks / Bedroom', 'description': 'Basic bedroom module with cots and decorations', 'size': {'width': 8, 'height': 4}, 'dig': {'x': -1, 'y': -1, 'width': 10, 'height': 6}, 'buildings': [ {'id': 'Bed', 'x': 1, 'y': 1}, {'id': 'Bed', 'x': 3, 'y': 1}, {'id': 'Bed', 'x': 5, 'y': 1}, {'id': 'LadderBed', 'x': 1, 'y': 3}, {'id': 'LadderBed', 'x': 3, 'y': 3}, {'id': 'FlowerVase', 'x': 6, 'y': 1}, ], }, } def list_blueprints(): print(f"Available Blueprints ({len(BLUEPRINTS)}):") print("=" * 60) for key, bp in BLUEPRINTS.items(): print(f" {key:16s} {bp['name']:28s} {bp['size']['width']}x{bp['size']['height']}") print(f" {'':16s} {bp['description']}") print() def apply_blueprint(name, origin_x, origin_y): bp = BLUEPRINTS.get(name) if not bp: print(f"[!] Blueprint '{name}' not found") print(f" Use 'list' to see available blueprints") return False print(f"Applying blueprint: {bp['name']}") print(f" Origin: ({origin_x}, {origin_y})") print(f" Size: {bp['size']['width']} x {bp['size']['height']}") print() results = [] dig = bp.get('dig', {'x': -1, 'y': -1, 'width': bp['size']['width'] + 2, 'height': bp['size']['height'] + 2}) dig_result = api_post('/api/action/dig', { 'x': origin_x + dig['x'], 'y': origin_y + dig['y'], 'width': dig['width'], 'height': dig['height'], }) status = 'OK' if 'error' not in dig_result else dig_result.get('error', 'fail') print(f" [Dig] area ({dig['width']}x{dig['height']}): {status}") for b in bp['buildings']: x = origin_x + b['x'] y = origin_y + b['y'] result = api_post('/api/action/build', { 'buildingId': b['id'], 'x': x, 'y': y, }) ok = 'error' not in result results.append({'building': b['id'], 'x': x, 'y': y, 'ok': ok}) status = 'OK' if ok else result.get('error', 'fail') print(f" [Build] {b['id']:20s} at ({x:3d}, {y:3d}): {status}") ok_count = sum(1 for r in results if r['ok']) print() print(f" Result: {ok_count}/{len(results)} buildings placed") return ok_count == len(results) if __name__ == '__main__': cmd = sys.argv[1] if len(sys.argv) > 1 else 'list' if cmd == 'list': list_blueprints() elif cmd == 'build': if len(sys.argv) < 4: print("Usage: python oni_builder.py build ") print() list_blueprints() sys.exit(1) success = apply_blueprint(sys.argv[2], int(sys.argv[3]), int(sys.argv[4])) sys.exit(0 if success else 1) else: print("Usage: python oni_builder.py ")