Skip to content

Commit

Permalink
babyagi
Browse files Browse the repository at this point in the history
  • Loading branch information
hychen-naza committed Jul 2, 2023
1 parent ca822ae commit 2d50a74
Show file tree
Hide file tree
Showing 2 changed files with 96 additions and 40 deletions.
74 changes: 34 additions & 40 deletions camel/agents/babyagi_agent.py
Original file line number Diff line number Diff line change
Expand Up @@ -83,11 +83,7 @@ def execution_agent(self, objective: str, task: str) -> str:
str: The response generated by the AI for the given task.
"""

context = self.context_agent(query=objective, top_results_num=5)
# print("\n****RELEVANT CONTEXT****\n")
# print(context)
# print('')
prompt = f'Perform one task based on the objective: {objective}.\n'
if context:
prompt += 'Consider the previously completed tasks:' + '\n'.join(
Expand Down Expand Up @@ -127,8 +123,6 @@ def context_agent(self, query: str, top_results_num: int) -> List[dict]:
"""
results = self.results_storage.query(query=query,
top_results_num=top_results_num)
# print("****RESULTS****")
# print(results)
return results

def task_creation_agent(self, objective: str, result: Dict,
Expand All @@ -144,30 +138,31 @@ def task_creation_agent(self, objective: str, result: Dict,
Returns:
str: The new task list generated by the AI for the given task.
"""
prompt = f"""You are to use the result from an execution agent to create new tasks
with the following objective: {objective}.
The last completed task has the result: \n{result["data"]}
This result was based on this task description: {task_description}.\n"""
prompt = f"""
You are to use the result from an execution agent to create new tasks
with the following objective: {objective}.
The last completed task has the result: \n{result["data"]}
This result was based on this task description: {task_description}.\n"""

if task_list:
prompt += f"These are incomplete tasks: {', '.join(task_list)}\n"
prompt += "Based on the result, return a list of tasks to be completed in order to \
meet the objective. "
prompt += "Based on the result, return a list of tasks to be completed \
in order to meet the objective. "

if task_list:
prompt += "These new tasks must not overlap with incomplete tasks."

prompt += """
Return one task per line in your response.
The result must be a numbered list in the format:
Return one task per line in your response.
The result must be a numbered list in the format:
#. First task
#. Second task
#. First task
#. Second task
The number of each entry must be followed by a period.
If your list is empty, write "There are no tasks to add at this time."
Unless your list is empty, do not include any headers before numbered list
or follow your numbered list with any other output."""
The number of each entry must be followed by a period.
If your list is empty, write "There are no tasks to add at this time."
Unless your list is empty, do not include any headers before your numbered list
or follow your numbered list with any other output."""

print(f'\n*****TASK CREATION AGENT PROMPT****\n{prompt}\n')
response = openai.Completion.create(engine="text-davinci-003",
Expand All @@ -178,12 +173,11 @@ def task_creation_agent(self, objective: str, result: Dict,
for task_string in new_tasks:
task_parts = task_string.strip().split(".", 1)
if len(task_parts) == 2:
task_id = ''.join(s for s in task_parts[0] if s.isnumeric())
# this may cause error as LLM may generated # instead of number
# task_id = ''.join(s for s in task_parts[0] if s.isnumeric())
task_name = re.sub(r'[^\w\s_]+', '', task_parts[1]).strip()
if task_name.strip() and task_id.isnumeric():
if task_name.strip(): # and task_id.isnumeric():
new_tasks_list.append(task_name)
# print('New task created: ' + task_name)

out = [{"task_name": task_name} for task_name in new_tasks_list]
return out

Expand All @@ -198,22 +192,22 @@ def prioritization_agent(self) -> List[dict]:
bullet_string = '\n'

prompt = f"""
You are tasked with prioritizing the following tasks:
{bullet_string + bullet_string.join(task_names)}
Consider the ultimate objective of your team: {self.objective}.
Tasks should be sorted from highest to lowest priority,
where higher-priority tasks are those
that act as pre-requisites or are more essential for meeting the objective.
Do not remove any tasks.
Return the ranked tasks as a numbered list in the format:
#. First task
#. Second task
The entries must be consecutively numbered, starting with
1. The number of each entry must be followed by a period.
Do not include any headers before your ranked list or
follow your list with any other output."""
You are tasked with prioritizing the following tasks:
{bullet_string + bullet_string.join(task_names)}
Consider the ultimate objective of your team: {self.objective}.
Tasks should be sorted from highest to lowest priority,
where higher-priority tasks are those
that act as pre-requisites or are more essential for meeting the objective.
Do not remove any tasks.
Return the ranked tasks as a numbered list in the format:
#. First task
#. Second task
The entries must be consecutively numbered, starting with 1.
The number of each entry must be followed by a period.
Do not include any headers before your ranked list or
follow your list with any other output."""

print(f'\n****TASK PRIORITIZATION AGENT PROMPT****\n{prompt}\n')
response = response = openai.Completion.create(
Expand Down
62 changes: 62 additions & 0 deletions test/agents/test_babyagi_agent.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
import os

import pytest

from camel.agents import BabyAGIAgent
from camel.configs import ChatGPTConfig
from camel.typing import ModelType
from camel.utils import openai_api_key_required


@openai_api_key_required
@pytest.mark.parametrize('model', [ModelType.GPT_3_5_TURBO, ModelType.GPT_4])
def test_chat_agent(model):
assert os.environ.get(
"OPENAI_API_KEY") is not None, "Missing OPENAI_API_KEY"

model_config = ChatGPTConfig()
objective = "Solve world hunger."
first_task = {"task_id": 1, "task_name": "Develop a task list."}
babyagi = BabyAGIAgent(objective, model=model, model_config=model_config)
babyagi.init_tasks(first_task)
assert babyagi.tasks_storage.is_empty() is False

task = babyagi.tasks_storage.popleft()
assert babyagi.tasks_storage.is_empty() is True

result = babyagi.execution_agent(objective, task["task_name"])
assert isinstance(result, str)

result_id = f"result_{task['task_id']}"
babyagi.results_storage.add(task, result, result_id)

enriched_result = {"data": result}
new_tasks = babyagi.task_creation_agent(
objective,
enriched_result,
task["task_name"],
babyagi.tasks_storage.get_task_names(),
)
assert isinstance(new_tasks, list)
assert len(new_tasks) > 0
assert isinstance(new_tasks[0], dict)

for new_task in new_tasks:
new_task.update({"task_id": babyagi.tasks_storage.next_task_id()})
babyagi.tasks_storage.append(new_task)

prioritized_tasks = babyagi.prioritization_agent()
assert isinstance(prioritized_tasks, list)
assert len(prioritized_tasks) > 0
assert isinstance(prioritized_tasks[0], dict)

old_number_tasks = list(babyagi.tasks_storage.tasks)
old_number_tasks_names = [task['task_name'] for task in old_number_tasks]
if prioritized_tasks:
babyagi.tasks_storage.replace(prioritized_tasks)
new_number_tasks = list(babyagi.tasks_storage.tasks)
new_number_tasks_names = [task['task_name'] for task in new_number_tasks]
for task in old_number_tasks_names:
assert task in new_number_tasks_names
for task in new_number_tasks_names:
assert task in old_number_tasks_names

0 comments on commit 2d50a74

Please sign in to comment.