From 9dd3a73c2d12ed7ed3dbf1a1536483fab8486ebb Mon Sep 17 00:00:00 2001 From: Sean Sube Date: Wed, 5 Jun 2024 19:05:21 -0500 Subject: [PATCH] add more prompt filters, pass more data to initial prompt, test making characters aware of the game --- prompts/llama-base.yml | 16 +++++++++--- taleweave/actions/base.py | 2 +- taleweave/actions/optional.py | 2 +- taleweave/actions/planning.py | 2 +- taleweave/actions/quest.py | 2 +- taleweave/bot/discord.py | 2 +- taleweave/generate.py | 10 ++++++-- taleweave/main.py | 2 +- taleweave/simulate.py | 2 +- taleweave/state.py | 6 ++++- taleweave/systems/digest.py | 2 +- taleweave/utils/conversation.py | 2 +- taleweave/utils/{prompt.py => template.py} | 30 ++++++++++++++++++++++ worlds.yml | 4 +-- 14 files changed, 66 insertions(+), 18 deletions(-) rename taleweave/utils/{prompt.py => template.py} (58%) diff --git a/prompts/llama-base.yml b/prompts/llama-base.yml index d1d8bc9..c04d4b4 100644 --- a/prompts/llama-base.yml +++ b/prompts/llama-base.yml @@ -192,6 +192,14 @@ prompts: action_check_calendar_each: | {{name}} will happen in {{turns}} turn + # agent stuff + world_agent_backstory: | + {{ character.backstory }} + world_agent_backstory_other: | + You are {{character | name}}, a character in a text-based role-playing game. Your character's backstory is: + {{ character.backstory }} + Explore the world, interact with other characters, and complete quests to advance the story. + # default dungeon master world_default_dungeon_master: | You are the dungeon master in charge of creating an engaging fantasy world full of interesting characters who @@ -201,10 +209,10 @@ prompts: # world generation world_generate_dungeon_master: | - You are an experienced dungeon master creating a visually detailed world for a new adventure. Be creative and - original, creating a world that is visually detailed and full of curious details. Do not repeat yourself unless you - are given the same prompt with the same characters, room, and context. {{flavor}}. The theme is: - {{theme}}. + You are an experienced dungeon master creating a visually detailed world for a new adventure set in {{theme}}. Be + creative and original, creating a world that is visually detailed and full of curious details. Do not repeat + yourself unless you are given the same prompt with the same characters, room, and context. {{flavor}}. The theme of + the world must be: {{theme}}. world_generate_world_broadcast_theme: | Generating a {{theme}} with {{room_count}} rooms diff --git a/taleweave/actions/base.py b/taleweave/actions/base.py index 0ebf0e7..9105942 100644 --- a/taleweave/actions/base.py +++ b/taleweave/actions/base.py @@ -11,7 +11,6 @@ from taleweave.context import ( ) from taleweave.errors import ActionError from taleweave.utils.conversation import loop_conversation -from taleweave.utils.prompt import format_prompt from taleweave.utils.search import ( find_character_in_room, find_item_in_character, @@ -20,6 +19,7 @@ from taleweave.utils.search import ( find_room, ) from taleweave.utils.string import normalize_name +from taleweave.utils.template import format_prompt logger = getLogger(__name__) diff --git a/taleweave/actions/optional.py b/taleweave/actions/optional.py index 35ebfcc..1dafbc9 100644 --- a/taleweave/actions/optional.py +++ b/taleweave/actions/optional.py @@ -22,9 +22,9 @@ from taleweave.generate import ( link_rooms, ) from taleweave.utils.effect import apply_effects, is_effect_ready -from taleweave.utils.prompt import format_prompt from taleweave.utils.search import find_character_in_room from taleweave.utils.string import normalize_name +from taleweave.utils.template import format_prompt from taleweave.utils.world import describe_entity logger = getLogger(__name__) diff --git a/taleweave/actions/planning.py b/taleweave/actions/planning.py index 006bacc..5321193 100644 --- a/taleweave/actions/planning.py +++ b/taleweave/actions/planning.py @@ -8,7 +8,7 @@ from taleweave.context import ( from taleweave.errors import ActionError from taleweave.models.planning import CalendarEvent from taleweave.utils.planning import get_recent_notes -from taleweave.utils.prompt import format_prompt +from taleweave.utils.template import format_prompt def take_note(fact: str): diff --git a/taleweave/actions/quest.py b/taleweave/actions/quest.py index c27e9a1..d85d6a9 100644 --- a/taleweave/actions/quest.py +++ b/taleweave/actions/quest.py @@ -7,8 +7,8 @@ from taleweave.systems.quest import ( get_quests_for_character, set_active_quest, ) -from taleweave.utils.prompt import format_prompt from taleweave.utils.search import find_character_in_room +from taleweave.utils.template import format_prompt def accept_quest(character: str, quest: str) -> str: diff --git a/taleweave/bot/discord.py b/taleweave/bot/discord.py index 97d3083..d5047ed 100644 --- a/taleweave/bot/discord.py +++ b/taleweave/bot/discord.py @@ -36,8 +36,8 @@ from taleweave.player import ( set_player, ) from taleweave.render.comfy import render_event -from taleweave.utils.prompt import format_prompt from taleweave.utils.search import list_characters +from taleweave.utils.template import format_prompt logger = getLogger(__name__) client = None diff --git a/taleweave/generate.py b/taleweave/generate.py index cc179ec..56707dc 100644 --- a/taleweave/generate.py +++ b/taleweave/generate.py @@ -25,7 +25,6 @@ from taleweave.models.entity import Character, Item, Portal, Room, World, WorldE from taleweave.models.event import GenerateEvent from taleweave.utils import try_parse_float, try_parse_int from taleweave.utils.effect import resolve_int_range -from taleweave.utils.prompt import format_prompt from taleweave.utils.search import ( list_characters, list_characters_in_room, @@ -35,6 +34,7 @@ from taleweave.utils.search import ( list_rooms, ) from taleweave.utils.string import normalize_name +from taleweave.utils.template import format_prompt logger = getLogger(__name__) @@ -571,7 +571,13 @@ def generate_world( world_config = get_world_config() room_count = room_count or resolve_int_range(world_config.size.rooms) or 0 - broadcast_generated(message=format_prompt("world_generate_world_broadcast_theme")) + broadcast_generated( + message=format_prompt( + "world_generate_world_broadcast_theme", + theme=theme, + room_count=room_count, + ) + ) world = World(name=name, rooms=[], theme=theme, order=[]) set_current_world(world) diff --git a/taleweave/main.py b/taleweave/main.py index 06b64b2..402afa2 100644 --- a/taleweave/main.py +++ b/taleweave/main.py @@ -50,7 +50,7 @@ if True: from taleweave.plugins import load_plugin from taleweave.simulate import simulate_world from taleweave.state import create_agents, save_world, save_world_state - from taleweave.utils.prompt import format_prompt + from taleweave.utils.template import format_prompt # start the debugger, if needed if environ.get("DEBUG", "false").lower() == "true": diff --git a/taleweave/simulate.py b/taleweave/simulate.py index 4700b7b..3e6f8a9 100644 --- a/taleweave/simulate.py +++ b/taleweave/simulate.py @@ -51,8 +51,8 @@ from taleweave.models.event import ActionEvent, ResultEvent from taleweave.utils.conversation import make_keyword_condition, summarize_room from taleweave.utils.effect import expire_effects from taleweave.utils.planning import expire_events, get_upcoming_events -from taleweave.utils.prompt import format_prompt from taleweave.utils.search import find_containing_room +from taleweave.utils.template import format_prompt from taleweave.utils.world import format_attributes logger = getLogger(__name__) diff --git a/taleweave/state.py b/taleweave/state.py index 7be9353..fb9b927 100644 --- a/taleweave/state.py +++ b/taleweave/state.py @@ -14,6 +14,7 @@ from taleweave.context import ( ) from taleweave.models.entity import World from taleweave.player import LocalPlayer +from taleweave.utils.template import format_prompt def create_agents( @@ -31,7 +32,10 @@ def create_agents( agent_memory = restore_memory(memory.get(character.name, [])) agent.load_history(agent_memory) else: - agent = Agent(character.name, character.backstory, {}, llm) + backstory = format_prompt( + "world_agent_backstory", character=character, world=world + ) + agent = Agent(character.name, backstory, {}, llm) agent.memory = restore_memory(memory.get(character.name, [])) set_character_agent(character.name, character, agent) diff --git a/taleweave/systems/digest.py b/taleweave/systems/digest.py index 6e3d206..e81e0e5 100644 --- a/taleweave/systems/digest.py +++ b/taleweave/systems/digest.py @@ -5,8 +5,8 @@ from taleweave.context import get_current_world, get_prompt_library, subscribe from taleweave.game_system import FormatPerspective, GameSystem from taleweave.models.entity import Character, Room, World, WorldEntity from taleweave.models.event import ActionEvent, GameEvent -from taleweave.utils.prompt import format_str from taleweave.utils.search import find_containing_room, find_portal, find_room +from taleweave.utils.template import format_str logger = getLogger(__name__) diff --git a/taleweave/utils/conversation.py b/taleweave/utils/conversation.py index 229a2f5..c072471 100644 --- a/taleweave/utils/conversation.py +++ b/taleweave/utils/conversation.py @@ -11,7 +11,7 @@ from packit.utils import could_be_json from taleweave.context import broadcast, get_game_config from taleweave.models.entity import Character, Room from taleweave.models.event import ReplyEvent -from taleweave.utils.prompt import format_str +from taleweave.utils.template import format_str from .string import and_list, normalize_name diff --git a/taleweave/utils/prompt.py b/taleweave/utils/template.py similarity index 58% rename from taleweave/utils/prompt.py rename to taleweave/utils/template.py index 5c4e836..0ad65ac 100644 --- a/taleweave/utils/prompt.py +++ b/taleweave/utils/template.py @@ -8,11 +8,41 @@ from taleweave.utils.world import describe_entity, name_entity logger = getLogger(__name__) + +def a_prefix(name: str) -> str: + first_word = name.split(" ")[0] + if first_word.lower() in ["a", "an", "the"]: + return name + + if name[0].lower() in "aeiou": + return f"an {name}" + + return f"a {name}" + + +def the_prefix(name: str) -> str: + first_word = name.split(" ")[0] + if first_word.lower() in ["a", "an", "the"]: + return name + + return f"the {name}" + + +def punctuate(name: str, suffix: str) -> str: + if name[-1] in [".", "!", "?", suffix]: + return name + + return f"{name}{suffix}" + + jinja_env = Environment() jinja_env.filters["describe"] = describe_entity jinja_env.filters["name"] = name_entity jinja_env.filters["and_list"] = and_list jinja_env.filters["or_list"] = or_list +jinja_env.filters["a_prefix"] = a_prefix +jinja_env.filters["the_prefix"] = the_prefix +jinja_env.filters["punctuate"] = punctuate def format_prompt(prompt_key: str, **kwargs) -> str: diff --git a/worlds.yml b/worlds.yml index 4c9f6e3..022aaa2 100644 --- a/worlds.yml +++ b/worlds.yml @@ -12,9 +12,9 @@ templates: include colorful characters and make sure they will fully utilize all of the actions available to them in this world, exploring and interacting with each other - name: jurassic-park - theme: opening scenes from Jurassic Park + theme: opening scenes from the 1993 film Jurassic Park flavor: | - follow the script of the film Jurassic Park exactly. do not deviate from the script in any way. + follow the script of the 1993 film Jurassic Park exactly. do not deviate from the script in any way. include accurate characters and instruct them to utilize all of the actions available to them in this world - name: star-wars theme: opening scenes from the 1977 film Star Wars