Skip to content

Commit 750fb10

Browse files
feat: add self-reflection support with configurable prompt to achat method
- Implement complete self-reflection logic in achat method to match chat method - Support configurable reflect_prompt parameter in async operations - Add reflection loop with min/max limits and error handling - Update method docstring to reflect new self-reflection capability - Ensure consistent behavior between chat and achat methods Co-authored-by: Mervin Praison <MervinPraison@users.noreply.github.com>
1 parent 4b913a7 commit 750fb10

File tree

1 file changed

+71
-2
lines changed
  • src/praisonai-agents/praisonaiagents/agent

1 file changed

+71
-2
lines changed

src/praisonai-agents/praisonaiagents/agent/agent.py

Lines changed: 71 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1415,7 +1415,7 @@ def clean_json_output(self, output: str) -> str:
14151415
return cleaned
14161416

14171417
async def achat(self, prompt: str, temperature=0.2, tools=None, output_json=None, output_pydantic=None, reasoning_steps=False):
1418-
"""Async version of chat method. TODO: Requires Syncing with chat method."""
1418+
"""Async version of chat method with self-reflection support."""
14191419
# Log all parameter values when in debug mode
14201420
if logging.getLogger().getEffectiveLevel() == logging.DEBUG:
14211421
param_info = {
@@ -1588,10 +1588,79 @@ async def achat(self, prompt: str, temperature=0.2, tools=None, output_json=None
15881588
messages=messages,
15891589
temperature=temperature
15901590
)
1591+
1592+
response_text = response.choices[0].message.content
1593+
1594+
# Handle self-reflection if enabled
1595+
if self.self_reflect:
1596+
reflection_count = 0
1597+
1598+
while True:
1599+
reflection_prompt = f"""
1600+
Reflect on your previous response: '{response_text}'.
1601+
{self.reflect_prompt if self.reflect_prompt else "Identify any flaws, improvements, or actions."}
1602+
Provide a "satisfactory" status ('yes' or 'no').
1603+
Output MUST be JSON with 'reflection' and 'satisfactory'.
1604+
"""
1605+
1606+
# Add reflection prompt to messages
1607+
reflection_messages = messages + [
1608+
{"role": "assistant", "content": response_text},
1609+
{"role": "user", "content": reflection_prompt}
1610+
]
1611+
1612+
try:
1613+
reflection_response = await async_client.beta.chat.completions.parse(
1614+
model=self.reflect_llm if self.reflect_llm else self.llm,
1615+
messages=reflection_messages,
1616+
temperature=temperature,
1617+
response_format=ReflectionOutput
1618+
)
1619+
1620+
reflection_output = reflection_response.choices[0].message.parsed
1621+
1622+
if self.verbose:
1623+
display_self_reflection(f"Agent {self.name} self reflection (using {self.reflect_llm if self.reflect_llm else self.llm}): reflection='{reflection_output.reflection}' satisfactory='{reflection_output.satisfactory}'", console=self.console)
1624+
1625+
# Only consider satisfactory after minimum reflections
1626+
if reflection_output.satisfactory == "yes" and reflection_count >= self.min_reflect - 1:
1627+
if self.verbose:
1628+
display_self_reflection("Agent marked the response as satisfactory after meeting minimum reflections", console=self.console)
1629+
break
1630+
1631+
# Check if we've hit max reflections
1632+
if reflection_count >= self.max_reflect - 1:
1633+
if self.verbose:
1634+
display_self_reflection("Maximum reflection count reached, returning current response", console=self.console)
1635+
break
1636+
1637+
# Regenerate response based on reflection
1638+
regenerate_messages = reflection_messages + [
1639+
{"role": "assistant", "content": f"Self Reflection: {reflection_output.reflection} Satisfactory?: {reflection_output.satisfactory}"},
1640+
{"role": "user", "content": "Now regenerate your response using the reflection you made"}
1641+
]
1642+
1643+
new_response = await async_client.chat.completions.create(
1644+
model=self.llm,
1645+
messages=regenerate_messages,
1646+
temperature=temperature
1647+
)
1648+
response_text = new_response.choices[0].message.content
1649+
reflection_count += 1
1650+
1651+
except Exception as e:
1652+
if self.verbose:
1653+
display_error(f"Error in parsing self-reflection json {e}. Retrying", console=self.console)
1654+
logging.error("Reflection parsing failed.", exc_info=True)
1655+
reflection_count += 1
1656+
if reflection_count >= self.max_reflect:
1657+
break
1658+
continue
1659+
15911660
if logging.getLogger().getEffectiveLevel() == logging.DEBUG:
15921661
total_time = time.time() - start_time
15931662
logging.debug(f"Agent.achat completed in {total_time:.2f} seconds")
1594-
return response.choices[0].message.content
1663+
return response_text
15951664
except Exception as e:
15961665
display_error(f"Error in chat completion: {e}")
15971666
if logging.getLogger().getEffectiveLevel() == logging.DEBUG:

0 commit comments

Comments
 (0)