mirror of
https://github.com/temporal-community/temporal-ai-agent.git
synced 2026-03-17 06:58:09 +01:00
mucho fixes and prompt engineering
This commit is contained in:
@@ -2,10 +2,14 @@ from models.tool_definitions import AgentGoal
|
|||||||
from typing import Optional
|
from typing import Optional
|
||||||
import json
|
import json
|
||||||
|
|
||||||
MULTI_GOAL_MODE:bool = None
|
MULTI_GOAL_MODE: bool = None
|
||||||
|
|
||||||
|
|
||||||
def generate_genai_prompt(
|
def generate_genai_prompt(
|
||||||
agent_goal: AgentGoal, conversation_history: str, multi_goal_mode:bool, raw_json: Optional[str] = None
|
agent_goal: AgentGoal,
|
||||||
|
conversation_history: str,
|
||||||
|
multi_goal_mode: bool,
|
||||||
|
raw_json: Optional[str] = None,
|
||||||
) -> str:
|
) -> str:
|
||||||
"""
|
"""
|
||||||
Generates a concise prompt for producing or validating JSON instructions
|
Generates a concise prompt for producing or validating JSON instructions
|
||||||
@@ -25,10 +29,12 @@ def generate_genai_prompt(
|
|||||||
prompt_lines.append(
|
prompt_lines.append(
|
||||||
"This is the ongoing history to determine which tool and arguments to gather:"
|
"This is the ongoing history to determine which tool and arguments to gather:"
|
||||||
)
|
)
|
||||||
prompt_lines.append("BEGIN CONVERSATION HISTORY")
|
prompt_lines.append("*BEGIN CONVERSATION HISTORY*")
|
||||||
prompt_lines.append(json.dumps(conversation_history, indent=2))
|
prompt_lines.append(json.dumps(conversation_history, indent=2))
|
||||||
prompt_lines.append("END CONVERSATION HISTORY")
|
prompt_lines.append("*END CONVERSATION HISTORY*")
|
||||||
prompt_lines.append("")
|
prompt_lines.append(
|
||||||
|
"REMINDER: You can use the conversation history to infer arguments for the tools."
|
||||||
|
)
|
||||||
|
|
||||||
# Example Conversation History (from agent_goal)
|
# Example Conversation History (from agent_goal)
|
||||||
if agent_goal.example_conversation_history:
|
if agent_goal.example_conversation_history:
|
||||||
@@ -84,7 +90,20 @@ def generate_genai_prompt(
|
|||||||
"2) If all required arguments are known, set next='confirm' and specify the tool.\n"
|
"2) If all required arguments are known, set next='confirm' and specify the tool.\n"
|
||||||
" The user will confirm before the tool is run.\n"
|
" The user will confirm before the tool is run.\n"
|
||||||
f"3) {generate_toolchain_complete_guidance()}\n"
|
f"3) {generate_toolchain_complete_guidance()}\n"
|
||||||
"4) response should be short and user-friendly.\n"
|
"4) response should be short and user-friendly.\n\n"
|
||||||
|
"Guardrails (always remember!)\n"
|
||||||
|
"1) If any required argument is missing, set next='question' and ask the user.\n"
|
||||||
|
"1) ALWAYS ask a question in your response if next='question'.\n"
|
||||||
|
"2) ALWAYS set next='confirm' if you have arguments\n "
|
||||||
|
'And respond with "let\'s proceed with <tool> (and any other useful info)" \n '
|
||||||
|
"3) You can carry over arguments from one tool to another.\n "
|
||||||
|
"EXAMPLE: If you asked for an account ID, then use the conversation history to infer that argument "
|
||||||
|
"going forward."
|
||||||
|
"4) If ListAgents in the conversation history is force_confirm='False', you MUST check "
|
||||||
|
+ "if the current tool contains userConfirmation. If it does, please ask the user to confirm details "
|
||||||
|
+ "with the user. userConfirmation overrides force_confirm='False'.\n"
|
||||||
|
+ "EXAMPLE: (force_confirm='False' AND userConfirmation exists on tool) Would you like me to <run tool> "
|
||||||
|
+ "with the following details: <details>?\n"
|
||||||
)
|
)
|
||||||
|
|
||||||
# Validation Task (If raw_json is provided)
|
# Validation Task (If raw_json is provided)
|
||||||
@@ -110,14 +129,15 @@ def generate_genai_prompt(
|
|||||||
|
|
||||||
return "\n".join(prompt_lines)
|
return "\n".join(prompt_lines)
|
||||||
|
|
||||||
|
|
||||||
def generate_tool_completion_prompt(current_tool: str, dynamic_result: dict) -> str:
|
def generate_tool_completion_prompt(current_tool: str, dynamic_result: dict) -> str:
|
||||||
"""
|
"""
|
||||||
Generates a prompt for handling tool completion and determining next steps.
|
Generates a prompt for handling tool completion and determining next steps.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
current_tool: The name of the tool that just completed
|
current_tool: The name of the tool that just completed
|
||||||
dynamic_result: The result data from the tool execution
|
dynamic_result: The result data from the tool execution
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
str: A formatted prompt string for the agent to process the tool completion
|
str: A formatted prompt string for the agent to process the tool completion
|
||||||
"""
|
"""
|
||||||
@@ -132,15 +152,18 @@ def generate_tool_completion_prompt(current_tool: str, dynamic_result: dict) ->
|
|||||||
f"{generate_pick_new_goal_guidance()}"
|
f"{generate_pick_new_goal_guidance()}"
|
||||||
)
|
)
|
||||||
|
|
||||||
def generate_missing_args_prompt(current_tool: str, tool_data: dict, missing_args: list[str]) -> str:
|
|
||||||
|
def generate_missing_args_prompt(
|
||||||
|
current_tool: str, tool_data: dict, missing_args: list[str]
|
||||||
|
) -> str:
|
||||||
"""
|
"""
|
||||||
Generates a prompt for handling missing arguments for a tool.
|
Generates a prompt for handling missing arguments for a tool.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
current_tool: The name of the tool that needs arguments
|
current_tool: The name of the tool that needs arguments
|
||||||
tool_data: The current tool data containing the response
|
tool_data: The current tool data containing the response
|
||||||
missing_args: List of argument names that are missing
|
missing_args: List of argument names that are missing
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
str: A formatted prompt string for requesting missing arguments
|
str: A formatted prompt string for requesting missing arguments
|
||||||
"""
|
"""
|
||||||
@@ -150,13 +173,14 @@ def generate_missing_args_prompt(current_tool: str, tool_data: dict, missing_arg
|
|||||||
"Only provide a valid JSON response without any comments or metadata."
|
"Only provide a valid JSON response without any comments or metadata."
|
||||||
)
|
)
|
||||||
|
|
||||||
def set_multi_goal_mode_if_unset(mode:bool)->None:
|
|
||||||
|
def set_multi_goal_mode_if_unset(mode: bool) -> None:
|
||||||
"""
|
"""
|
||||||
Set multi-mode (used to pass workflow)
|
Set multi-mode (used to pass workflow)
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
None
|
None
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
bool: True if in multi-goal mode, false if not
|
bool: True if in multi-goal mode, false if not
|
||||||
"""
|
"""
|
||||||
@@ -164,44 +188,47 @@ def set_multi_goal_mode_if_unset(mode:bool)->None:
|
|||||||
if MULTI_GOAL_MODE is None:
|
if MULTI_GOAL_MODE is None:
|
||||||
MULTI_GOAL_MODE = mode
|
MULTI_GOAL_MODE = mode
|
||||||
|
|
||||||
def is_multi_goal_mode()-> bool:
|
|
||||||
|
def is_multi_goal_mode() -> bool:
|
||||||
"""
|
"""
|
||||||
Centralized logic for if we're in multi-goal mode.
|
Centralized logic for if we're in multi-goal mode.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
None
|
None
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
bool: True if in multi-goal mode, false if not
|
bool: True if in multi-goal mode, false if not
|
||||||
"""
|
"""
|
||||||
return MULTI_GOAL_MODE
|
return MULTI_GOAL_MODE
|
||||||
|
|
||||||
def generate_pick_new_goal_guidance()-> str:
|
|
||||||
|
def generate_pick_new_goal_guidance() -> str:
|
||||||
"""
|
"""
|
||||||
Generates a prompt for guiding the LLM to pick a new goal or be done depending on multi-goal mode.
|
Generates a prompt for guiding the LLM to pick a new goal or be done depending on multi-goal mode.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
None
|
None
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
str: A prompt string prompting the LLM to when to go to pick-new-goal
|
str: A prompt string prompting the LLM to when to go to pick-new-goal
|
||||||
"""
|
"""
|
||||||
if is_multi_goal_mode():
|
if is_multi_goal_mode():
|
||||||
return 'Next should only be "pick-new-goal" if all tools have been run for the current goal (use the system prompt to figure that out), or the user explicitly requested to pick a new goal.'
|
return 'Next should only be "pick-new-goal" if all tools have been run for the current goal (use the system prompt to figure that out), or the user explicitly requested to pick a new goal.'
|
||||||
else:
|
else:
|
||||||
return 'Next should never be "pick-new-goal".'
|
return 'Next should never be "pick-new-goal".'
|
||||||
|
|
||||||
|
|
||||||
def generate_toolchain_complete_guidance() -> str:
|
def generate_toolchain_complete_guidance() -> str:
|
||||||
"""
|
"""
|
||||||
Generates a prompt for guiding the LLM to handle the end of the toolchain.
|
Generates a prompt for guiding the LLM to handle the end of the toolchain.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
None
|
None
|
||||||
|
|
||||||
Returns:
|
Returns:
|
||||||
str: A prompt string prompting the LLM to prompt for a new goal, or be done
|
str: A prompt string prompting the LLM to prompt for a new goal, or be done
|
||||||
"""
|
"""
|
||||||
if is_multi_goal_mode():
|
if is_multi_goal_mode():
|
||||||
return "If no more tools are needed (user_confirmed_tool_run has been run for all), set next='confirm' and tool='ListAgents'."
|
return "If no more tools are needed (user_confirmed_tool_run has been run for all), set next='confirm' and tool='ListAgents'."
|
||||||
else :
|
else:
|
||||||
return "If no more tools are needed (user_confirmed_tool_run has been run for all), set next='done' and tool=''."
|
return "If no more tools are needed (user_confirmed_tool_run has been run for all), set next='done' and tool=''."
|
||||||
|
|||||||
@@ -56,17 +56,17 @@ def get_handler(tool_name: str):
|
|||||||
if tool_name == "FinCheckAccountIsValid":
|
if tool_name == "FinCheckAccountIsValid":
|
||||||
return check_account_valid
|
return check_account_valid
|
||||||
if tool_name == "FinCheckAccountBalance":
|
if tool_name == "FinCheckAccountBalance":
|
||||||
return get_account_balance
|
return get_account_balance
|
||||||
if tool_name == "FinMoveMoneyOrder":
|
if tool_name == "FinMoveMoney":
|
||||||
return move_money
|
return move_money
|
||||||
if tool_name == "FinCheckAccountSubmitLoanApproval":
|
if tool_name == "FinCheckAccountSubmitLoanApproval":
|
||||||
return submit_loan_application
|
return submit_loan_application
|
||||||
if tool_name == "GetOrder":
|
if tool_name == "GetOrder":
|
||||||
return get_order
|
return get_order
|
||||||
if tool_name == "TrackPackage":
|
if tool_name == "TrackPackage":
|
||||||
return track_package
|
return track_package
|
||||||
if tool_name == "ListOrders":
|
if tool_name == "ListOrders":
|
||||||
return list_orders
|
return list_orders
|
||||||
if tool_name == "GiveHint":
|
if tool_name == "GiveHint":
|
||||||
return give_hint
|
return give_hint
|
||||||
if tool_name == "GuessLocation":
|
if tool_name == "GuessLocation":
|
||||||
|
|||||||
@@ -1,10 +1,10 @@
|
|||||||
{
|
{
|
||||||
"accounts": [
|
"accounts": [
|
||||||
{
|
{
|
||||||
"name": "Matt Murdock",
|
"name": "Matt Murdock",
|
||||||
"email": "matt.murdock@nelsonmurdock.com",
|
"email": "matt.murdock@nelsonmurdock.com",
|
||||||
"account_id": "11235",
|
"account_id": "11235",
|
||||||
"checking_balance": 875.40,
|
"checking_balance": 875.4,
|
||||||
"savings_balance": 3200.15,
|
"savings_balance": 3200.15,
|
||||||
"bitcoin_balance": 0.1378,
|
"bitcoin_balance": 0.1378,
|
||||||
"account_creation_date": "2014-03-10"
|
"account_creation_date": "2014-03-10"
|
||||||
@@ -13,8 +13,8 @@
|
|||||||
"name": "Foggy Nelson",
|
"name": "Foggy Nelson",
|
||||||
"email": "foggy.nelson@nelsonmurdock.com",
|
"email": "foggy.nelson@nelsonmurdock.com",
|
||||||
"account_id": "112358",
|
"account_id": "112358",
|
||||||
"checking_balance": 1523.67,
|
"checking_balance": "1523.66",
|
||||||
"savings_balance": 4875.90,
|
"savings_balance": "4875.89",
|
||||||
"bitcoin_balance": 0.0923,
|
"bitcoin_balance": 0.0923,
|
||||||
"account_creation_date": "2014-03-10"
|
"account_creation_date": "2014-03-10"
|
||||||
},
|
},
|
||||||
@@ -23,7 +23,7 @@
|
|||||||
"email": "karen.page@nelsonmurdock.com",
|
"email": "karen.page@nelsonmurdock.com",
|
||||||
"account_id": "112",
|
"account_id": "112",
|
||||||
"checking_balance": 645.25,
|
"checking_balance": 645.25,
|
||||||
"savings_balance": 1830.50,
|
"savings_balance": "830.5",
|
||||||
"bitcoin_balance": 0.0456,
|
"bitcoin_balance": 0.0456,
|
||||||
"account_creation_date": "2015-01-15"
|
"account_creation_date": "2015-01-15"
|
||||||
},
|
},
|
||||||
@@ -31,7 +31,7 @@
|
|||||||
"name": "Wilson Fisk",
|
"name": "Wilson Fisk",
|
||||||
"email": "wilson.fisk@fiskcorp.com",
|
"email": "wilson.fisk@fiskcorp.com",
|
||||||
"account_id": "11",
|
"account_id": "11",
|
||||||
"checking_balance": 25000.00,
|
"checking_balance": 25000.0,
|
||||||
"savings_balance": 150000.75,
|
"savings_balance": 150000.75,
|
||||||
"bitcoin_balance": 5987.6721,
|
"bitcoin_balance": 5987.6721,
|
||||||
"account_creation_date": "2013-09-20"
|
"account_creation_date": "2013-09-20"
|
||||||
@@ -40,8 +40,8 @@
|
|||||||
"name": "Frank Castle",
|
"name": "Frank Castle",
|
||||||
"email": "frank.castle@vigilante.net",
|
"email": "frank.castle@vigilante.net",
|
||||||
"account_id": "1",
|
"account_id": "1",
|
||||||
"checking_balance": 320.10,
|
"checking_balance": 320.1,
|
||||||
"savings_balance": 0.30,
|
"savings_balance": 0.3,
|
||||||
"bitcoin_balance": 15.2189,
|
"bitcoin_balance": 15.2189,
|
||||||
"account_creation_date": "2016-02-05"
|
"account_creation_date": "2016-02-05"
|
||||||
},
|
},
|
||||||
@@ -49,8 +49,8 @@
|
|||||||
"name": "Joshua Smith",
|
"name": "Joshua Smith",
|
||||||
"email": "joshmsmith@gmail.com",
|
"email": "joshmsmith@gmail.com",
|
||||||
"account_id": "11235813",
|
"account_id": "11235813",
|
||||||
"checking_balance": 3021.90,
|
"checking_balance": 3021.9,
|
||||||
"savings_balance": 500.50,
|
"savings_balance": 500.5,
|
||||||
"bitcoin_balance": 0.001,
|
"bitcoin_balance": 0.001,
|
||||||
"account_creation_date": "2020-03-19"
|
"account_creation_date": "2020-03-19"
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -11,7 +11,7 @@ from shared.config import get_temporal_client
|
|||||||
|
|
||||||
from enum import Enum, auto
|
from enum import Enum, auto
|
||||||
|
|
||||||
#enums for the java enum
|
# enums for the java enum
|
||||||
# class ExecutionScenarios(Enum):
|
# class ExecutionScenarios(Enum):
|
||||||
# HAPPY_PATH = 0
|
# HAPPY_PATH = 0
|
||||||
# ADVANCED_VISIBILITY = auto() # 1
|
# ADVANCED_VISIBILITY = auto() # 1
|
||||||
@@ -20,6 +20,7 @@ from enum import Enum, auto
|
|||||||
# BUG_IN_WORKFLOW = auto() # 4
|
# BUG_IN_WORKFLOW = auto() # 4
|
||||||
# INVALID_ACCOUNT = auto() # 5
|
# INVALID_ACCOUNT = auto() # 5
|
||||||
|
|
||||||
|
|
||||||
# these dataclasses are for calling the Temporal Workflow
|
# these dataclasses are for calling the Temporal Workflow
|
||||||
# Python equivalent of the workflow we're calling's Java WorkflowParameterObj
|
# Python equivalent of the workflow we're calling's Java WorkflowParameterObj
|
||||||
@dataclass
|
@dataclass
|
||||||
@@ -27,103 +28,130 @@ class MoneyMovementWorkflowParameterObj:
|
|||||||
amount: int # Using snake_case as per Python conventions
|
amount: int # Using snake_case as per Python conventions
|
||||||
scenario: str
|
scenario: str
|
||||||
|
|
||||||
|
|
||||||
# this is made to demonstrate functionality but it could just as durably be an API call
|
# this is made to demonstrate functionality but it could just as durably be an API call
|
||||||
# this assumes it's a valid account - use check_account_valid() to verify that first
|
# this assumes it's a valid account - use check_account_valid() to verify that first
|
||||||
async def move_money(args: dict) -> dict:
|
async def move_money(args: dict) -> dict:
|
||||||
|
|
||||||
account_key = args.get("email_address_or_account_ID")
|
account_key = args.get("email_address_or_account_ID")
|
||||||
account_type: str = args.get("accounttype")
|
account_type: str = args.get("accounttype")
|
||||||
amount = args.get("amount")
|
amount = args.get("amount")
|
||||||
destinationaccount = args.get("destinationaccount")
|
destinationaccount = args.get("destinationaccount")
|
||||||
|
|
||||||
file_path = Path(__file__).resolve().parent.parent / "data" / "customer_account_data.json"
|
file_path = (
|
||||||
|
Path(__file__).resolve().parent.parent / "data" / "customer_account_data.json"
|
||||||
|
)
|
||||||
if not file_path.exists():
|
if not file_path.exists():
|
||||||
return {"error": "Data file not found."}
|
return {"error": "Data file not found."}
|
||||||
|
|
||||||
# todo validate there's enough money in the account
|
|
||||||
with open(file_path, "r") as file:
|
with open(file_path, "r") as file:
|
||||||
data = json.load(file)
|
data = json.load(file)
|
||||||
account_list = data["accounts"]
|
account_list = data["accounts"]
|
||||||
|
|
||||||
for account in account_list:
|
for account in account_list:
|
||||||
if account["email"] == account_key or account["account_id"] == account_key:
|
if account["email"] == account_key or account["account_id"] == account_key:
|
||||||
amount_str: str = str(amount) # LLM+python gets sassy about types but we need it to be str
|
amount_str: str = str(amount)
|
||||||
from_account_combo = account_key + account_type
|
from_account_combo = account_key + account_type
|
||||||
|
|
||||||
transfer_workflow_id = await start_workflow(amount_cents=str_dollars_to_cents(amount_str),from_account_name=from_account_combo, to_account_name=destinationaccount)
|
transfer_workflow_id = await start_workflow(
|
||||||
|
amount_cents=str_dollars_to_cents(amount_str),
|
||||||
account_type_key = 'checking_balance'
|
from_account_name=from_account_combo,
|
||||||
if(account_type.casefold() == "checking" ):
|
to_account_name=destinationaccount,
|
||||||
account_type = "checking"
|
)
|
||||||
account_type_key = 'checking_balance'
|
|
||||||
|
if account_type.casefold() == "checking":
|
||||||
elif(account_type.casefold() == "savings" ):
|
from_key = "checking_balance"
|
||||||
account_type = "savings"
|
elif account_type.casefold() == "savings":
|
||||||
account_type_key = 'savings_balance'
|
from_key = "savings_balance"
|
||||||
else:
|
else:
|
||||||
raise NotImplementedError("money order for account types other than checking or savings is not implemented.")
|
return_msg = "Money order for account types other than checking or savings is not implemented."
|
||||||
|
return {"error": return_msg}
|
||||||
new_balance: float = float(str_dollars_to_cents(str(account[account_type_key])))
|
|
||||||
new_balance = new_balance - float(str_dollars_to_cents(amount_str))
|
to_key = (
|
||||||
account[account_type_key] = str(new_balance / 100 ) #to dollars
|
"savings_balance"
|
||||||
with open(file_path, 'w') as file:
|
if destinationaccount.casefold() == "savings"
|
||||||
json.dump(data, file, indent=4)
|
else "checking_balance"
|
||||||
|
)
|
||||||
|
|
||||||
|
# Update from-account balance
|
||||||
|
from_balance = float(str_dollars_to_cents(str(account[from_key])))
|
||||||
|
from_balance -= float(str_dollars_to_cents(amount_str))
|
||||||
|
account[from_key] = str(from_balance / 100)
|
||||||
|
|
||||||
|
# Update destination-account balance
|
||||||
|
to_balance = float(str_dollars_to_cents(str(account[to_key])))
|
||||||
|
to_balance += float(str_dollars_to_cents(amount_str))
|
||||||
|
account[to_key] = str(to_balance / 100)
|
||||||
|
|
||||||
|
with open(file_path, "w") as file:
|
||||||
|
json.dump(data, file, indent=4)
|
||||||
|
|
||||||
|
return {
|
||||||
|
"status": "money movement complete",
|
||||||
|
"confirmation id": transfer_workflow_id,
|
||||||
|
"new_balance": account[from_key],
|
||||||
|
"destination_balance": account[to_key],
|
||||||
|
}
|
||||||
|
|
||||||
return {'status': "money movement complete", 'confirmation id': transfer_workflow_id, 'new_balance': account[account_type_key]}
|
|
||||||
|
|
||||||
return_msg = "Account not found with for " + account_key
|
return_msg = "Account not found with for " + account_key
|
||||||
return {"error": return_msg}
|
return {"error": return_msg}
|
||||||
|
|
||||||
|
|
||||||
# Async function to start workflow
|
# Async function to start workflow
|
||||||
async def start_workflow(amount_cents: int, from_account_name: str, to_account_name: str)-> str:
|
async def start_workflow(
|
||||||
|
amount_cents: int, from_account_name: str, to_account_name: str
|
||||||
|
) -> str:
|
||||||
|
|
||||||
start_real_workflow = os.getenv("FIN_START_REAL_WORKFLOW")
|
start_real_workflow = os.getenv("FIN_START_REAL_WORKFLOW")
|
||||||
if start_real_workflow is not None and start_real_workflow.lower() == "false":
|
if start_real_workflow is not None and start_real_workflow.lower() == "false":
|
||||||
START_REAL_WORKFLOW = False
|
START_REAL_WORKFLOW = False
|
||||||
else:
|
else:
|
||||||
START_REAL_WORKFLOW = True
|
START_REAL_WORKFLOW = True
|
||||||
|
|
||||||
if START_REAL_WORKFLOW:
|
if START_REAL_WORKFLOW:
|
||||||
# Connect to Temporal
|
# Connect to Temporal
|
||||||
client = await get_temporal_client()
|
client = await get_temporal_client()
|
||||||
# Create the parameter object
|
# Create the parameter object
|
||||||
params = MoneyMovementWorkflowParameterObj(
|
params = MoneyMovementWorkflowParameterObj(
|
||||||
amount=amount_cents,
|
amount=amount_cents, scenario="HAPPY_PATH"
|
||||||
scenario="HAPPY_PATH"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
workflow_id="TRANSFER-ACCT-" + from_account_name + "-TO-" + to_account_name # business-relevant workflow ID
|
workflow_id = (
|
||||||
|
"TRANSFER-ACCT-" + from_account_name + "-TO-" + to_account_name
|
||||||
|
) # business-relevant workflow ID
|
||||||
|
|
||||||
try:
|
try:
|
||||||
handle = await client.start_workflow(
|
handle = await client.start_workflow(
|
||||||
"moneyTransferWorkflow", # Workflow name
|
"moneyTransferWorkflow", # Workflow name
|
||||||
params, # Workflow parameters
|
params, # Workflow parameters
|
||||||
id=workflow_id,
|
id=workflow_id,
|
||||||
task_queue="MoneyTransferJava" # Task queue name
|
task_queue="MoneyTransferJava", # Task queue name
|
||||||
)
|
)
|
||||||
return handle.id
|
return handle.id
|
||||||
except WorkflowAlreadyStartedError as e:
|
except WorkflowAlreadyStartedError as e:
|
||||||
existing_handle = client.get_workflow_handle(workflow_id=workflow_id)
|
existing_handle = client.get_workflow_handle(workflow_id=workflow_id)
|
||||||
return existing_handle.id
|
return existing_handle.id
|
||||||
else:
|
else:
|
||||||
return "TRANSFER-ACCT-" + from_account_name + "-TO-" + to_account_name + "not-real"
|
return (
|
||||||
|
"TRANSFER-ACCT-" + from_account_name + "-TO-" + to_account_name + "not-real"
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
#cleans a string dollar amount description to cents value
|
# cleans a string dollar amount description to cents value
|
||||||
def str_dollars_to_cents(dollar_str: str) -> int:
|
def str_dollars_to_cents(dollar_str: str) -> int:
|
||||||
try:
|
try:
|
||||||
# Remove '$' and any whitespace
|
# Remove '$' and any whitespace
|
||||||
cleaned_str = dollar_str.replace('$', '').strip()
|
cleaned_str = dollar_str.replace("$", "").strip()
|
||||||
|
|
||||||
# Handle empty string or invalid input
|
# Handle empty string or invalid input
|
||||||
if not cleaned_str:
|
if not cleaned_str:
|
||||||
raise ValueError("Empty amount provided")
|
raise ValueError("Empty amount provided")
|
||||||
|
|
||||||
# Convert to float and then to cents
|
# Convert to float and then to cents
|
||||||
amount = float(cleaned_str)
|
amount = float(cleaned_str)
|
||||||
if amount < 0:
|
if amount < 0:
|
||||||
raise ValueError("Negative amounts not allowed")
|
raise ValueError("Negative amounts not allowed")
|
||||||
|
|
||||||
return int(amount * 100)
|
return int(amount * 100)
|
||||||
except ValueError as e:
|
except ValueError as e:
|
||||||
raise ValueError(f"Invalid dollar amount format: {dollar_str}") from e
|
raise ValueError(f"Invalid dollar amount format: {dollar_str}") from e
|
||||||
|
|||||||
@@ -1,4 +1,5 @@
|
|||||||
from models.tool_definitions import ToolDefinition, ToolArgument
|
from models.tool_definitions import ToolDefinition, ToolArgument
|
||||||
|
|
||||||
# ----- System tools -----
|
# ----- System tools -----
|
||||||
list_agents_tool = ToolDefinition(
|
list_agents_tool = ToolDefinition(
|
||||||
name="ListAgents",
|
name="ListAgents",
|
||||||
@@ -21,12 +22,13 @@ change_goal_tool = ToolDefinition(
|
|||||||
give_hint_tool = ToolDefinition(
|
give_hint_tool = ToolDefinition(
|
||||||
name="GiveHint",
|
name="GiveHint",
|
||||||
description="Give a hint to the user regarding the location of the pirate treasure. Use previous conversation to determine the hint_total, it should initially be 0 ",
|
description="Give a hint to the user regarding the location of the pirate treasure. Use previous conversation to determine the hint_total, it should initially be 0 ",
|
||||||
arguments=[
|
arguments=[
|
||||||
ToolArgument(
|
ToolArgument(
|
||||||
name="hint_total",
|
name="hint_total",
|
||||||
type="number",
|
type="number",
|
||||||
description="How many hints have been given",
|
description="How many hints have been given",
|
||||||
),],
|
),
|
||||||
|
],
|
||||||
)
|
)
|
||||||
|
|
||||||
guess_location_tool = ToolDefinition(
|
guess_location_tool = ToolDefinition(
|
||||||
@@ -54,7 +56,8 @@ guess_location_tool = ToolDefinition(
|
|||||||
# ----- Travel use cases tools -----
|
# ----- Travel use cases tools -----
|
||||||
search_flights_tool = ToolDefinition(
|
search_flights_tool = ToolDefinition(
|
||||||
name="SearchFlights",
|
name="SearchFlights",
|
||||||
description="Search for return flights from an origin to a destination within a date range (dateDepart, dateReturn).",
|
description="Search for return flights from an origin to a destination within a date range (dateDepart, dateReturn). "
|
||||||
|
"You are allowed to suggest dates from the conversation history, but ALWAYS ask the user if ok.",
|
||||||
arguments=[
|
arguments=[
|
||||||
ToolArgument(
|
ToolArgument(
|
||||||
name="origin",
|
name="origin",
|
||||||
@@ -76,6 +79,12 @@ search_flights_tool = ToolDefinition(
|
|||||||
type="ISO8601",
|
type="ISO8601",
|
||||||
description="End of date range in human readable format, when you want to return",
|
description="End of date range in human readable format, when you want to return",
|
||||||
),
|
),
|
||||||
|
ToolArgument(
|
||||||
|
name="userConfirmation",
|
||||||
|
type="string",
|
||||||
|
description="Indication of the user's desire to search flights, and to confirm the details "
|
||||||
|
+ "before moving on to the next step",
|
||||||
|
),
|
||||||
],
|
],
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -115,6 +124,11 @@ book_trains_tool = ToolDefinition(
|
|||||||
type="string",
|
type="string",
|
||||||
description="The IDs of the trains to book, comma separated",
|
description="The IDs of the trains to book, comma separated",
|
||||||
),
|
),
|
||||||
|
ToolArgument(
|
||||||
|
name="userConfirmation",
|
||||||
|
type="string",
|
||||||
|
description="Indication of user's desire to book train tickets",
|
||||||
|
),
|
||||||
],
|
],
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -132,6 +146,11 @@ create_invoice_tool = ToolDefinition(
|
|||||||
type="string",
|
type="string",
|
||||||
description="A description of the item details to be invoiced, inferred from the conversation history.",
|
description="A description of the item details to be invoiced, inferred from the conversation history.",
|
||||||
),
|
),
|
||||||
|
ToolArgument(
|
||||||
|
name="userConfirmation",
|
||||||
|
type="string",
|
||||||
|
description="Indication of user's desire to create an invoice",
|
||||||
|
),
|
||||||
],
|
],
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -278,7 +297,6 @@ financial_get_account_balances = ToolDefinition(
|
|||||||
name="FinCheckAccountBalance",
|
name="FinCheckAccountBalance",
|
||||||
description="Get account balance for your accounts. "
|
description="Get account balance for your accounts. "
|
||||||
"Returns the account balances of your accounts. ",
|
"Returns the account balances of your accounts. ",
|
||||||
|
|
||||||
arguments=[
|
arguments=[
|
||||||
ToolArgument(
|
ToolArgument(
|
||||||
name="email_address_or_account_ID",
|
name="email_address_or_account_ID",
|
||||||
@@ -289,10 +307,9 @@ financial_get_account_balances = ToolDefinition(
|
|||||||
)
|
)
|
||||||
|
|
||||||
financial_move_money = ToolDefinition(
|
financial_move_money = ToolDefinition(
|
||||||
name="FinMoveMoneyOrder",
|
name="FinMoveMoney",
|
||||||
description="Execute a money movement order. "
|
description="Send money from one account to another under the same acount ID (e.g. checking to savings). "
|
||||||
"Returns the status of the order and the account balance of the account money was moved from. ",
|
"Returns the status of the order and the new balances in each account. ",
|
||||||
|
|
||||||
arguments=[
|
arguments=[
|
||||||
ToolArgument(
|
ToolArgument(
|
||||||
name="email_address_or_account_ID",
|
name="email_address_or_account_ID",
|
||||||
@@ -303,16 +320,16 @@ financial_move_money = ToolDefinition(
|
|||||||
name="accounttype",
|
name="accounttype",
|
||||||
type="string",
|
type="string",
|
||||||
description="account type, such as checking or savings",
|
description="account type, such as checking or savings",
|
||||||
),
|
),
|
||||||
ToolArgument(
|
ToolArgument(
|
||||||
name="amount",
|
name="amount",
|
||||||
type="string",
|
type="string",
|
||||||
description="amount to move in the order",
|
description="amount to move in the order (e.g. checking or savings)",
|
||||||
),
|
),
|
||||||
ToolArgument(
|
ToolArgument(
|
||||||
name="destinationaccount",
|
name="destinationaccount",
|
||||||
type="string",
|
type="string",
|
||||||
description="account number to move the money to",
|
description="account to move the money to (e.g. checking or savings)",
|
||||||
),
|
),
|
||||||
ToolArgument(
|
ToolArgument(
|
||||||
name="userConfirmation",
|
name="userConfirmation",
|
||||||
@@ -324,16 +341,14 @@ financial_move_money = ToolDefinition(
|
|||||||
|
|
||||||
financial_submit_loan_approval = ToolDefinition(
|
financial_submit_loan_approval = ToolDefinition(
|
||||||
name="FinCheckAccountSubmitLoanApproval",
|
name="FinCheckAccountSubmitLoanApproval",
|
||||||
description="Submit a loan application. "
|
description="Submit a loan application. " "Returns the loan status. ",
|
||||||
"Returns the loan status. ",
|
|
||||||
|
|
||||||
arguments=[
|
arguments=[
|
||||||
ToolArgument(
|
ToolArgument(
|
||||||
name="email_address_or_account_ID",
|
name="email_address_or_account_ID",
|
||||||
type="string",
|
type="string",
|
||||||
description="email address or account ID of user",
|
description="email address or account ID of user",
|
||||||
),
|
),
|
||||||
ToolArgument(
|
ToolArgument(
|
||||||
name="amount",
|
name="amount",
|
||||||
type="string",
|
type="string",
|
||||||
description="amount requested for the loan",
|
description="amount requested for the loan",
|
||||||
@@ -381,4 +396,4 @@ ecomm_track_package = ToolDefinition(
|
|||||||
description="Indication of user's desire to get package tracking information",
|
description="Indication of user's desire to get package tracking information",
|
||||||
),
|
),
|
||||||
],
|
],
|
||||||
)
|
)
|
||||||
|
|||||||
Reference in New Issue
Block a user