a2ui-project / a2ui-project/a2ui

[BUG]: Validation Bypass via Mixed Client/Server Messages in A2uiValidator

オープン
#2,579 コメント 1 件 リアクション 0 件 担当者 1 名 @Varun-S10 が担当を希望しています GitHub で見る
P2 status: first-line-handled status: waiting-for-author-response type: bug
主要言語
TypeScript
スター
16.4k
フォーク
1.3k
平均マージ
2日 13時間
マージ済み PR(30日)
134

説明

# Location
agent_sdks/python/a2ui_core/src/a2ui/core/validating/validator.py:248

# Description
The A2uiValidator.validate method contains a logic flaw in its is_client_payload detection. It iterates over a list of messages and checks if any() message contains client-specific keys (action, error, or data). If this evaluates to True, the method immediately returns, skipping all protocol envelope, catalog schema, and topology integrity validation. An attacker controlling the A2UI JSON stream (e.g., a prompt-injected agent) can craft a payload containing both a dummy client message and malicious server messages (e.g., un-whitelisted components, recursive structures, or exploit payloads). The presence of the client message satisfies the any() condition, completely bypassing the SDK's validation checks and passing the unvalidated malicious payload to downstream processing.

# Impact
Bypass of the primary validation layer (TB-1). Malicious agents can deliver malformed or exploit-bearing A2UI JSON payloads that would otherwise be rejected, enabling downstream attacks such as Prototype Pollution or Resource Exhaustion depending on the renderer's sink behaviors.

# Mitigation
Modify the is_client_payload check to ensure all messages belong to the client namespace, e.g., using all(...) instead of any(...). Alternatively, enforce that payloads cannot mix client and server messages, raising an error if a mixed payload is detected.

# Reproduction Steps
Create an A2UI payload with multiple messages.
In the first message, include a client key: {\"action\": {\"functionCall\": {\"name\": \"dummy\"}}}.
In the second message, include an invalid or malicious server message, e.g., a createSurface message with invalid component schemas or recursive definitions.
Call A2uiValidator.validate() on this payload array.
Observe that the validator silently accepts the payload without raising an A2uiValidatorError.

# Evidence
```
is_client_payload = any(
isinstance(m, dict) and any(k in m for k in (\"action\", \"error\", \"data\"))
for m in messages
)
if is_client_payload:
return
```

# Reasoning
The A2uiValidator.validate method takes an a2ui_payload and processes it into a list of messages. It then contains a check: is_client_payload = any(isinstance(m, dict) and any(k in m for k in ("action", "error", "data")) for m in messages). If is_client_payload evaluates to True, the function immediately returns without validating any of the messages. An attacker can construct a payload consisting of a list of messages where at least one message contains an "action", "error", or "data" key, and the subsequent messages can be arbitrary unvalidated payloads. Because of the early return, the rest of the payload completely bypasses schema, topological, and protocol validation. This clearly allows maliciously crafted server messages to bypass validation if mixed with a dummy client message.

コントリビューションガイド

コントリビューションガイドを開く

評価

この issue はまだ評価されていません。

新しい issue をメールで受け取る

初心者向けの GitHub issue を短くまとめたダイジェスト。