langchain-ai/deepagents · error · ValueError
PendingNotification {self.key!r} has {primaries} primary act
Error message
PendingNotification {self.key!r} has {primaries} primary actions; at most one is allowed What it means
At most one action in a `PendingNotification` may be marked `primary=True`; `__post_init__` counts primaries and raises a `ValueError` naming the key and the count when more than one is found. This enforces a single highlighted action in the UI.
Source
Thrown at libs/code/deepagents_code/notifications.py:132
"""Enforce basic invariants at construction time.
Raises:
ValueError: If `key` is empty, `actions` is empty, or more
than one action is marked `primary=True`.
"""
if not self.key:
msg = "PendingNotification.key must be non-empty"
raise ValueError(msg)
if not self.actions:
msg = f"PendingNotification {self.key!r} must declare at least one action"
raise ValueError(msg)
primaries = sum(1 for a in self.actions if a.primary)
if primaries > 1:
msg = (
f"PendingNotification {self.key!r} has {primaries} primary actions; "
"at most one is allowed"
)
raise ValueError(msg)
class NotificationRegistry:
"""In-memory store of pending notifications.
Instance-scoped (one per app) so test apps don't pollute each other.
Owns the bidirectional key-to-toast-identity binding so callers
cannot accidentally desynchronize the click-routing indices.
"""
def __init__(self) -> None:
"""Initialize an empty registry."""
self._entries: dict[str, PendingNotification] = {}
self._key_to_toast: dict[str, str] = {}
self._toast_to_key: dict[str, str] = {}
def add(self, notification: PendingNotification) -> None:
"""Register a new notification or replace an existing one with the same key.View on GitHub (pinned to a1af029e6e)
Solutions
- Set `primary=True` on exactly one action, demoting the rest to `primary=False`
- When merging lists, keep the first primary and clear the flag on the others
- Add a normalization step before construction: `for i, a in enumerate(actions): a.primary = a.primary and i == first_primary_index`
Example fix
// before note = PendingNotification(key="deploy", actions=[Approve(primary=True), Reject(primary=True)]) // after note = PendingNotification(key="deploy", actions=[Approve(primary=True), Reject(primary=False)])
Defensive patterns
Strategy: validation
Validate before calling
primaries = sum(1 for a in actions if a.primary)
if primaries > 1:
raise ValueError(f"at most one primary action allowed, got {primaries}") Try / catch
try:
note = PendingNotification(key=key, actions=actions)
except ValueError as e:
logging.warning("invalid notification %r: %s", key, e) Prevention
- Mark exactly one action primary when defining action sets
- Normalize the primary flag when merging action lists
- Encode the single-primary rule in a shared action-builder helper
When it happens
Trigger: Constructing a notification whose actions list contains two or more actions with `primary=True`, often after merging action lists or copying actions from another notification.
Common situations: Appending a default primary action to a list that already contains one; combining actions from multiple sources without deduplicating the primary flag; a config file that marks several buttons as primary.
Understand the failure class
Background: Schema validation failed / invalid input schema: payload rejected because its shape doesn't match the expected schema — this error's family across 28 libraries.
Related errors
- PendingNotification.key must be non-empty
- PendingNotification {self.key!r} must declare at least one a
- `unreadable_reason` implies the token is not usable; `logged
- `expires_at` must be set when `logged_in` is True.
- `expires_at` is only meaningful when `logged_in` is True.
AI-assisted analysis of langchain-ai/deepagents@a1af029e6e (2026-08-29).
Data as JSON: /api/errors/6ce497f516abfacc.
Report an issue: GitHub.