Skip to content

feat: Add page lifecycle hooks to BrowserPool#1791

Open
Mantisus wants to merge 2 commits intoapify:masterfrom
Mantisus:browser-page-hooks
Open

feat: Add page lifecycle hooks to BrowserPool#1791
Mantisus wants to merge 2 commits intoapify:masterfrom
Mantisus:browser-page-hooks

Conversation

@Mantisus
Copy link
Collaborator

Description

Add four page lifecycle hooks to BrowserPool registered as decorators:

  • pre_page_create_hook — called before page creation; browser_new_context_options is mutable, so the hook can affect how the page context is configured.
  • post_page_create_hook — called after page creation.
  • pre_page_close_hook — called before page close.
  • post_page_close_hook — called after page close.

Issues

Testing

  • Added new tests for BrowserPool.

Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR adds four page lifecycle hooks to BrowserPoolpre_page_create_hook, post_page_create_hook, pre_page_close_hook, and post_page_close_hook — registered as decorators, aligning Python's BrowserPool closer to the JS Crawlee browser pool API as described in issue #1741.

Changes:

  • Four hook registration methods added to BrowserPool, each appending user-provided async callables to internal lists that are executed at the corresponding lifecycle point.
  • Close hooks are implemented by monkey-patching page.close via _override_page_close after page creation.
  • Comprehensive tests covering individual hook invocation, execution order, argument validation, and multiple hook registration.

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated 1 comment.

File Description
src/crawlee/browsers/_browser_pool.py Adds hook storage lists, _execute_hooks helper, _override_page_close for close hooks, and four public hook registration methods with docstrings.
tests/unit/browsers/test_browser_pool.py Adds six tests covering each hook type, execution order, and multiple hook registration.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines +386 to +394
if self._pre_page_close_hooks or self._post_page_close_hooks:
original_close = crawlee_page.page.close

async def close_with_hooks(*args: Any, **kwargs: Any) -> None:
await self._execute_hooks(self._pre_page_close_hooks, crawlee_page, browser_controller)
await original_close(*args, **kwargs)
await self._execute_hooks(self._post_page_close_hooks, crawlee_page.id, browser_controller)

crawlee_page.page.close: Callable[..., Awaitable[None]] = close_with_hooks
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It is not expected that a closing hook will be added after the page has already been opened.

@Mantisus Mantisus requested review from Pijukatel and vdusek March 13, 2026 02:15
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants