zylon-ai/private-gpt · error · ValueError
Chat history contains multiple user blocks. This is not supp
Error message
Chat history contains multiple user blocks. This is not supported.
What it means
Raised by _assert_only_one_user_block when the history splits into more than one user block (multiple user turns separated by assistant replies). repair_with_tools is a single-turn reduction — it only accepts one user block — so multi-turn conversations must be reduced (e.g. condensed) before this repair path.
Source
Thrown at private_gpt/components/chat/processors/chat_history/memory/utils/repairs.py:209
)
def _assert_only_one_user_block(
chat_history: list[ChatMessage],
) -> None:
"""Assert that the chat history contains exactly one user block.
This is used to ensure that the chat history
is clean and contains only one user block.
"""
if not chat_history:
return
matrix = get_user_blocks(chat_history)
if not matrix:
raise ValueError("Chat history does not contain any user messages.")
if len(matrix) > 1:
raise ValueError(
"Chat history contains multiple user blocks. This is not supported."
)
View on GitHub (pinned to 4a030776a3)
Solutions
- Condense/trim history to the last user block before calling repair_with_tools()
- Use repair_without_tools() if multiple blocks are expected and tools are absent
- Split the session into per-turn requests and repair only the current turn
Example fix
# before repaired = repair_with_tools(conversation_messages) # after # keep only the last user block from private_gpt.components.chat.processors.chat_history.memory.utils.splitting import get_user_blocks blocks = get_user_blocks(conversation_messages) repaired = repair_with_tools(blocks[-1])
Defensive patterns
Strategy: validation
Validate before calling
blocks = get_user_blocks(conversation_messages)
if len(blocks) > 1:
conversation_messages = blocks[-1] # reduce to the last user block before repair_with_tools Type guard
def is_single_user_block(history: list[ChatMessage]) -> bool:
return len(get_user_blocks(history)) <= 1 Try / catch
try:
repaired = repair_with_tools(conversation_messages)
except ValueError as e:
if "multiple user blocks" in str(e):
repaired = repair_with_tools(get_user_blocks(conversation_messages)[-1])
else:
raise Prevention
- Condense multi-turn sessions to the last user block before the tools repair path
- Use repair_without_tools for general multi-turn histories
- Document the single-block contract of repair_with_tools at its call sites
When it happens
Trigger: Calling repair_with_tools() on a full multi-turn conversation containing two or more user messages with assistant replies between them.
Common situations: Feeding an entire chat session into the tools path without prior condensation; a session loader appending prior turns; conflating repair_with_tools with the general repair_without_tools path (which tolerates multiple blocks).
Related errors
- User block {i} is empty.
- User block {i} does not start with a user message: {block[0]
- User block {i} does not end with an assistant message: {bloc
- User block {i} does not end with an assistant or tool messag
- Tool message {j} in user block {i} does not follow an assist
AI-assisted analysis of zylon-ai/private-gpt@4a030776a3 (2026-08-15).
Data as JSON: /api/errors/285afca7c24b2996.
Report an issue: GitHub.