From 27b01a17d534acb874372dc5a49442cf60ccb591 Mon Sep 17 00:00:00 2001 From: venti <1308199824@qq.com> Date: Sat, 30 May 2026 15:00:06 +0800 Subject: [PATCH 1/2] docs: remove InvokePromptAgent from declarative workflows action types --- python/samples/03-workflows/declarative/README.md | 1 - 1 file changed, 1 deletion(-) diff --git a/python/samples/03-workflows/declarative/README.md b/python/samples/03-workflows/declarative/README.md index 1c48ef1e7a..9a24b741e7 100644 --- a/python/samples/03-workflows/declarative/README.md +++ b/python/samples/03-workflows/declarative/README.md @@ -64,7 +64,6 @@ actions: ### Agent Invocation - `InvokeAzureAgent` - Call an Azure AI agent -- `InvokePromptAgent` - Call a local prompt agent ### Tool Invocation - `InvokeFunctionTool` - Call a registered Python function From 63e7040c49126a217fa4fee062cc93d45186bbb8 Mon Sep 17 00:00:00 2001 From: venti <1308199824@qq.com> Date: Sat, 30 May 2026 15:08:36 +0800 Subject: [PATCH 2/2] [Python][sample] sanitize JSON output in reflection pattern before Pydantic parsing (fixes #4718) --- .../workflow_as_agent_reflection_pattern.py | 27 ++++++++++++++++++- 1 file changed, 26 insertions(+), 1 deletion(-) diff --git a/python/samples/03-workflows/agents/workflow_as_agent_reflection_pattern.py b/python/samples/03-workflows/agents/workflow_as_agent_reflection_pattern.py index 705b5bacb4..b895b1e7d2 100644 --- a/python/samples/03-workflows/agents/workflow_as_agent_reflection_pattern.py +++ b/python/samples/03-workflows/agents/workflow_as_agent_reflection_pattern.py @@ -64,6 +64,29 @@ class ReviewResponse: approved: bool +def _sanitize_json_text(text: str) -> str: + """Sanitize LLM output before JSON parsing. + + Handles common issues with gpt-4.1/gpt-5 structured output: + - Markdown code fences (```json ... ```) + - Tab characters inside string values + - Truncated JSON (missing closing brackets/quotes) + """ + text = text.strip() + if text.startswith("```"): + text = text.split("\n", 1)[-1] if "\n" in text else text[3:] + if text.endswith("```"): + text = text[:-3].rstrip() + text = text.replace("\t", " ") + open_brackets = text.count("{") - text.count("}") + if open_brackets > 0: + text += "}" * open_brackets + open_braces = text.count("[") - text.count("]") + if open_braces > 0: + text += "]" * open_braces + return text + + class Reviewer(Executor): """Executor that reviews agent responses and provides structured feedback.""" @@ -107,7 +130,9 @@ class _Response(BaseModel): print("Reviewer: Sending review request to LLM...") response = await self._chat_client.get_response(messages=messages, options={"response_format": _Response}) - parsed = _Response.model_validate_json(response.messages[-1].text) + raw = response.messages[-1].text + sanitized = _sanitize_json_text(raw) + parsed = _Response.model_validate_json(sanitized) print(f"Reviewer: Review complete - Approved: {parsed.approved}") print(f"Reviewer: Feedback: {parsed.feedback}")