from typing import Any, Dict import logging import httpx from mcp.server.fastmcp import FastMCP from dice import Dice from player import Player from item import Item from game import Game from npc import NPC mcp = FastMCP("wyvern-castle") game = Game() logging.basicConfig( level=logging.INFO, format='%(asctime)s - %(name)s - %(levelname)s - %(message)s', handlers=[ logging.StreamHandler(), ] ) @mcp.tool() async def throw_a_dice(n_faces: int) -> Any: """Throw a dice with n faces. If n==2 its a coin toss. Args: n_faces: Number of faces of the dice """ logging.info(f"Throwing a dice with {n_faces} faces") dice = Dice() if n_faces < 1: raise ValueError("Number of faces must be at least 1") elif n_faces == 1: return 1 elif n_faces == 2: return dice.head_or_tails() else: return dice.roll(n_faces) @mcp.tool() async def mult(a: int, b: int) -> int: """Multiply two numbers. Args: a: First number b: Second number """ logging.info(f"Calling mult with a={a}, b={b}") result = a * b logging.info(f"mult result: {result}") return result @mcp.tool() async def add(a: int, b: int) -> int: """Add two numbers. Args: a: First number b: Second number """ logging.info(f"Calling add with a={a}, b={b}") result = a + b logging.info(f"add result: {result}") return result @mcp.tool() async def create_player(name: str, strength: int, dexterity: int, intelligence: int, wisdom: int, charisma: int, hp: int, armor: int, speed: int, item: str = None) -> Dict[str, Any]: """Create a new player. Need all the stats to function properly. Throw a d20 for every stats you don't have, and a d6 for hp, armor and speed. Args: name: Name of the player strength: Strength of the player dexterity: Dexterity of the player intelligence: Intelligence of the player wisdom: Wisdom of the player charisma: Charisma of the player hp: Hit points of the player armor: Armor class of the player speed: Speed of the player item: Item carried by the player """ logging.info(f"Creating player with name={name}") player = Player(name, strength, dexterity, intelligence, wisdom, charisma, hp, armor, speed) logging.info(f"Created player: {player}") return player.serialize_dict() @mcp.tool() async def create_npc(name: str, strength: int, dexterity: int, intelligence: int, wisdom: int, charisma: int, hp: int, armor: int, speed: int, item: str = None) -> Dict[str, Any]: """Create a new NPC. Need all the stats to function properly. Throw a d20 for every stats you don't have, and a d6 for hp, armor and speed. Args: name: Name of the NPC strength: Strength of the NPC dexterity: Dexterity of the NPC intelligence: Intelligence of the NPC wisdom: Wisdom of the NPC charisma: Charisma of the NPC hp: Hit points of the NPC armor: Armor class of the NPC speed: Speed of the NPC item: Item carried by the NPC """ logging.info(f"Creating NPC with name={name}") npc = NPC(name, strength, dexterity, intelligence, wisdom, charisma, hp, armor, speed) logging.info(f"Created NPC: {npc}") return npc.serialize_dict() @mcp.tool() async def create_item(name: str, description: str, bonus: str) -> Dict[str, Any]: """Create a new item. Args: name: Name of the item description: Description of the item bonus: Bonus of the item ex: strength+1,hp+5 """ logging.info(f"Creating item with name={name}") item = Item(name, description, bonus) logging.info(f"Created item: {item}") return item.serialize_dict() @mcp.tool() async def add_item_to_player(player_name: str, item_name: str) -> Dict[str, Any]: """Add an item to a player's inventory. Args: player_name: The name of the player to add the item to item_name: The name of the item to add """ logging.info(f"Adding item {item_name} to player {player_name}") return {"status": "Item added"} def main(): # Initialize and run the server mcp.run(transport="stdio") if __name__ == "__main__": main()