-
Notifications
You must be signed in to change notification settings - Fork 746
Description
Problem Statement
Agent internally maintains two representations of the system prompt:
self._system_prompt(string) — exposed publicly via thesystem_promptpropertyself._system_prompt_content(list ofSystemContentBlock) — private, no public accessor
The content block representation is the richer, more complete one — it preserves cache control markers and non-text content blocks. The string is a lossy flattened projection kept for backwards compatibility.
Despite being private, _system_prompt_content is already accessed from multiple places outside agent.py:
event_loop.pypassesagent._system_prompt_contenttostream_messages()- Model tests (
test_bedrock.py,test_openai.py,test_litellm.py) testsystem_prompt_contentformatting test_agent_skills.pydirectly reads/writesagent._system_prompt_content~12 times to set up test state- PR feat(telemetry): emit system prompt on chat spans per GenAI semconv #1818 proposes passing
agent._system_prompt_contentto telemetry spans
This is a leaky abstraction — the private attribute is effectively part of the public contract already.
Proposed Solution
Add a public system_prompt_content property:
@property
def system_prompt_content(self) -> list[SystemContentBlock] | None:
"""Get the system prompt as content blocks.
Returns the full content block representation, preserving cache control
and non-text content. Returns None if no system prompt is set.
"""
return self._system_prompt_contentThen update internal consumers (event_loop.py, tests) to use the public property instead of the private attribute.
Use Case
The current system_prompt property returns str | None, which was the original API. When content block support was added (for features like prompt caching), _system_prompt_content was introduced as an internal detail. But the string-only public API is now insufficient for consumers that need the full representation — telemetry (#1818), the event loop, and model implementations all need the content blocks.
Alternatives Solutions
No response
Additional Context
No response