Skip to content

feat(hooks): support union types and list of types for add_hook#1719

Merged
Unshure merged 6 commits intomainfrom
agent-tasks/1714
Feb 19, 2026
Merged

feat(hooks): support union types and list of types for add_hook#1719
Unshure merged 6 commits intomainfrom
agent-tasks/1714

Conversation

@Unshure
Copy link
Member

@Unshure Unshure commented Feb 18, 2026

Motivation

Hook providers often need to register the same callback for multiple event types, such as logging events before and after model calls. Currently, this requires either:

  1. Multiple add_hook() calls for the same callback
  2. Creating separate callback functions

This change enables a cleaner API where a single callback can be registered for multiple event types by using union type hints or passing a list of types explicitly.

Resolves #1714

Public API Changes

Agent.add_hook() and HookRegistry.add_callback() now support union types and lists of event types:

from strands.hooks import BeforeModelCallEvent, AfterModelCallEvent

agent = Agent()

# Before: had to call add_hook twice
def log_event(event) -> None:
    print(f"Event: {type(event).__name__}")
agent.add_hook(log_event, BeforeModelCallEvent)
agent.add_hook(log_event, AfterModelCallEvent)

# After: union type hint registers for both automatically
def log_event(event: BeforeModelCallEvent | AfterModelCallEvent) -> None:
    print(f"Event: {type(event).__name__}")
agent.add_hook(log_event)  # Registered for BOTH event types

# After: explicit list of types
def log_event(event) -> None:
    print(f"Event: {type(event).__name__}")
agent.add_hook(log_event, [BeforeModelCallEvent, AfterModelCallEvent])

The **kwargs parameter was removed from Agent.add_hook() as it was unused.

Use Cases

  • Unified logging: Log both before and after events with a single callback
  • Analytics hooks: Track multiple lifecycle events with shared logic
  • Debugging: Instrument multiple event types simultaneously

@github-actions
Copy link

Assessment: Approve

Well-implemented feature that cleanly extends the hooks API to support union types and list-based event type registration. The implementation is clean, tests are comprehensive, and the change is backward compatible.

Review Notes
  • Code Quality: Implementation properly uses typing.get_origin() and typing.get_args() for union detection, with appropriate validation and error handling
  • Testing: Comprehensive coverage including both pipe syntax (A | B) and Union[A, B], edge cases (None in union, invalid types, empty lists), and callback invocation verification
  • Documentation: Clear docstrings with examples covering all usage patterns
  • API Design: The **kwargs removal is a good cleanup, and the new functionality follows the existing patterns

Note: Per API_BAR_RAISING.md, since this PR modifies the public Agent.add_hook() API, consider adding the needs-api-review label. The PR description already includes the required documentation (use cases, examples, API signatures), so this should be a quick review.

- Add union type support (A | B and Union[A, B]) for callback type hints
- Allow passing list of event types to add_hook/add_callback
- Remove unused **kwargs from Agent.add_hook()
- Deduplicate event types when registering callbacks
- Validate all types in unions and lists are BaseHookEvent subclasses
- Error on None or invalid types in unions

Resolves #1714
@codecov
Copy link

codecov bot commented Feb 18, 2026

Codecov Report

✅ All modified and coverable lines are covered by tests.

📢 Thoughts on this report? Let us know!

@Unshure
Copy link
Member Author

Unshure commented Feb 18, 2026

/strands

- Use set() for deduplication instead of manual loop
- Replace type: ignore with cast() for explicit type narrowing
- Restore missing test case
@github-actions github-actions bot added size/m and removed size/m labels Feb 18, 2026
@Unshure Unshure marked this pull request as ready for review February 18, 2026 21:19
@github-actions
Copy link

Assessment: Approve ✅

All review feedback has been addressed:

  • Simplified deduplication using set() directly
  • Replaced # type: ignore comments with explicit cast() calls

Code is clean, tests pass with 100% coverage on modified lines. Ready to merge.

@github-actions
Copy link

Review Update: All feedback has been addressed ✅

Changes verified:

  • Deduplication simplified to use set() directly
  • type: ignore comments replaced with explicit cast() calls
  • All 20 tests passing
  • Codecov confirms full coverage

LGTM - ready for merge.

mkmeral
mkmeral previously approved these changes Feb 18, 2026
@Unshure Unshure merged commit 2456b71 into main Feb 19, 2026
25 of 27 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[FEATURE] Allow union types and list of types for agent.add_hook

4 participants

Comments