stagehand 4.4.0a0.dev1676__tar.gz → 4.4.1a0.dev1688__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (41) hide show
  1. stagehand-4.4.1a0.dev1688/PKG-INFO +256 -0
  2. stagehand-4.4.1a0.dev1688/README.md +224 -0
  3. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/pyproject.toml +1 -1
  4. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/_extension/manifest.json +1 -1
  5. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/_extension/service-worker.js +7 -4
  6. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/_generated/protocol_version.py +1 -1
  7. stagehand-4.4.0a0.dev1676/PKG-INFO +0 -205
  8. stagehand-4.4.0a0.dev1676/README.md +0 -173
  9. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/__init__.py +0 -0
  10. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/_extension/blank.html +0 -0
  11. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/_extension/content-script.js +0 -0
  12. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/_extension/offscreen/service-worker-heartbeat.html +0 -0
  13. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/_extension/offscreen/service-worker-heartbeat.js +0 -0
  14. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/_extension/wake-service-worker.html +0 -0
  15. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/_extension/wake-service-worker.js +0 -0
  16. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/_generated/__init__.py +0 -0
  17. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/_generated/input_types.py +0 -0
  18. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/_generated/models.py +0 -0
  19. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/_sdk_identity.py +0 -0
  20. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/_validation.py +0 -0
  21. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/browser.py +0 -0
  22. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/browser_clipboard.py +0 -0
  23. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/browser_context.py +0 -0
  24. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/browserbase_connection.py +0 -0
  25. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/browserbase_rpc.py +0 -0
  26. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/browserbase_services.py +0 -0
  27. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/browserbase_session.py +0 -0
  28. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/browserbase_transport.py +0 -0
  29. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/cdp_client.py +0 -0
  30. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/client_models.py +0 -0
  31. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/client_types.py +0 -0
  32. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/extension_assets.py +0 -0
  33. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/file_upload.py +0 -0
  34. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/locator.py +0 -0
  35. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/page.py +0 -0
  36. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/py.typed +0 -0
  37. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/response.py +0 -0
  38. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/rpc_client.py +0 -0
  39. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/stagehand.py +0 -0
  40. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/timeouts.py +0 -0
  41. {stagehand-4.4.0a0.dev1676 → stagehand-4.4.1a0.dev1688}/src/stagehand/webmcp.py +0 -0
@@ -0,0 +1,256 @@
1
+ Metadata-Version: 2.4
2
+ Name: stagehand
3
+ Version: 4.4.1a0.dev1688
4
+ Summary: Browserbase's SDK for building browser agents
5
+ Keywords: ai,agent,ai-agent,browser,browser-agent,browser-automation,computer-use,headless,playwright,cdp,llm,automation,web-scraping,testing
6
+ Author: Browserbase
7
+ License-Expression: MIT
8
+ Classifier: Development Status :: 5 - Production/Stable
9
+ Classifier: Intended Audience :: Developers
10
+ Classifier: Operating System :: OS Independent
11
+ Classifier: Programming Language :: Python :: 3
12
+ Classifier: Programming Language :: Python :: 3 :: Only
13
+ Classifier: Programming Language :: Python :: 3.11
14
+ Classifier: Topic :: Internet :: WWW/HTTP :: Browsers
15
+ Classifier: Topic :: Scientific/Engineering :: Artificial Intelligence
16
+ Classifier: Topic :: Software Development :: Libraries :: Python Modules
17
+ Classifier: Topic :: Software Development :: Testing
18
+ Classifier: Typing :: Typed
19
+ Classifier: Framework :: AsyncIO
20
+ Requires-Dist: browserbase>=1.15,<2
21
+ Requires-Dist: httpx>=0.23,<1
22
+ Requires-Dist: opentelemetry-api>=1.35,<2
23
+ Requires-Dist: pydantic>=2.12,<3
24
+ Requires-Dist: typing-extensions>=4.12,<5
25
+ Requires-Dist: websockets>=16.1.1
26
+ Requires-Python: >=3.11
27
+ Project-URL: Homepage, https://stagehand.dev
28
+ Project-URL: Documentation, https://docs.stagehand.dev
29
+ Project-URL: Repository, https://github.com/browserbase/stagehand
30
+ Project-URL: Issues, https://github.com/browserbase/stagehand/issues
31
+ Description-Content-Type: text/markdown
32
+
33
+ <div id="toc" align="center" style="margin-bottom: 0;">
34
+ <ul style="list-style: none; margin: 0; padding: 0;">
35
+ <a href="https://stagehand.dev">
36
+ <picture>
37
+ <source media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/browserbase/stagehand/main/media/dark_logo.png" />
38
+ <img alt="Stagehand" src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/light_logo.png" width="200" style="margin-right: 30px;" />
39
+ </picture>
40
+ </a>
41
+ </ul>
42
+ </div>
43
+ <p align="center">
44
+ <strong>Stagehand is the SDK for browser agents</strong><br>
45
+ </p>
46
+
47
+ <p align="center">
48
+ <a href="https://trendshift.io/repositories/12122" target="_blank"><img src="https://trendshift.io/api/badge/repositories/12122" alt="browserbase%2Fstagehand | Trendshift" style="width: 250px; height: 55px;" width="250" height="55"/></a>
49
+ </p>
50
+
51
+ <p align="center">
52
+ <a href="https://docs.stagehand.dev"><strong>Docs</strong></a> ·
53
+ <a href="https://docs.stagehand.dev/v4/first-steps/quickstart"><strong>Quickstart</strong></a> ·
54
+ <a href="https://github.com/browserbase/stagehand"><strong>⭐ Star this repo</strong></a>
55
+ </p>
56
+
57
+ <p align="center">
58
+ <a href="https://github.com/browserbase/stagehand/tree/main?tab=MIT-1-ov-file#MIT-1-ov-file">
59
+ <picture>
60
+ <source media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/browserbase/stagehand/main/media/dark_license.svg" />
61
+ <img alt="MIT License" src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/light_license.svg" />
62
+ </picture>
63
+ </a>
64
+ <a href="https://discord.gg/stagehand">
65
+ <picture>
66
+ <source media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/browserbase/stagehand/main/media/dark_discord.svg" />
67
+ <img alt="Discord Community" src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/light_discord.svg" />
68
+ </picture>
69
+ </a>
70
+ <a href="https://deepwiki.com/browserbase/stagehand">
71
+ <img alt="Ask DeepWiki" src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/deepwiki.svg" width="156" height="32" />
72
+ </a>
73
+ </p>
74
+
75
+ <p align="center">
76
+ <a href="https://stagehand.dev">
77
+ <img src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/stagehand-website-banner.png" alt="Stagehand homepage showing browser automation in TypeScript, Python, and Go and a speed comparison with Playwright" width="100%" />
78
+ </a>
79
+ </p>
80
+
81
+ # Stagehand Python SDK
82
+
83
+ ## AI that uses the browser like humans.
84
+
85
+ Sign in once, keep the session, and pull structured data out the other side.
86
+
87
+ Replace `app.example.com` with your application's URL and set `OPENAI_API_KEY`, `APP_EMAIL`, and
88
+ `APP_PASSWORD` before running this example.
89
+
90
+ ```python
91
+ import asyncio
92
+ import os
93
+
94
+ from pydantic import BaseModel
95
+ from stagehand import Stagehand, local_browser
96
+
97
+
98
+ class Invoice(BaseModel):
99
+ number: str
100
+ amount: float
101
+ paid: bool
102
+
103
+
104
+ class Invoices(BaseModel):
105
+ invoices: list[Invoice]
106
+
107
+
108
+ async def main() -> None:
109
+ # Cookies persist in ./browser-data, so the next run starts already signed in
110
+ browser = await local_browser.launch(user_data_dir="./browser-data")
111
+ try:
112
+ stagehand = await Stagehand.create(
113
+ browser=browser,
114
+ model="openai/gpt-5.4-mini",
115
+ model_api_key=os.environ["OPENAI_API_KEY"],
116
+ )
117
+ try:
118
+ page = (await browser.context.pages())[0]
119
+ await page.goto("https://app.example.com/login")
120
+
121
+ # observe() returns real selectors, so credentials never reach the model
122
+ email = await stagehand.observe("find the email input")
123
+ password = await stagehand.observe("find the password input")
124
+ await page.locator(email.data[0].selector).fill(os.environ["APP_EMAIL"])
125
+ await page.locator(password.data[0].selector).fill(os.environ["APP_PASSWORD"])
126
+
127
+ # act() self-heals when the site redesigns its form
128
+ await stagehand.act("click the sign in button")
129
+ await stagehand.act("open the billing page")
130
+
131
+ # extract() returns schema-validated data
132
+ result = await stagehand.extract(
133
+ "extract every invoice in the table",
134
+ Invoices,
135
+ )
136
+ print(result.data.invoices)
137
+ finally:
138
+ await stagehand.close()
139
+ finally:
140
+ await browser.close()
141
+
142
+
143
+ asyncio.run(main())
144
+ ```
145
+
146
+ ## Install
147
+
148
+ ```bash
149
+ pip install stagehand
150
+ ```
151
+
152
+ Requires Python 3.11 or later. Local runs need [Chrome](https://www.google.com/chrome/) installed.
153
+ Full setup: [Quickstart](https://docs.stagehand.dev/v4/first-steps/quickstart).
154
+
155
+ ## Why Stagehand
156
+
157
+ - **Familiar APIs:** The Playwright-style methods you and your agents already know: `goto`, `click`, `locator`, `screenshot`.
158
+ - **Token efficiency:** Hybrid accessibility-tree trimming gives agents exactly the page context they need and nothing more.
159
+ - **Faster in production:** Stagehand runs as an extension next to the browser, cutting round-trip latency on every action.
160
+ - **Self-healing:** `act`, `observe`, and `extract` refresh how an action happens when the site changes underneath it.
161
+ - **Built for agents:** WebMCP, clipboard support, batch commands, deep locators for nested iframes and closed Shadow DOMs, OTel traces.
162
+ - **Three languages:** One complete browser driver across TypeScript, Python, and Go.
163
+
164
+ ## Run it on Browserbase
165
+
166
+ Point the same script at [Browserbase](https://www.browserbase.com). The
167
+ [Model Gateway](https://docs.stagehand.dev/v4/configuration/models#model-gateway) handles model
168
+ routing, and [server-side caching](https://docs.stagehand.dev/v4/best-practices/caching) reuses
169
+ results for repeated actions.
170
+
171
+ Import `browserbase` from `stagehand`, then use these browser and client setup calls inside the
172
+ async `main()` above, keeping its `try`/`finally` cleanup:
173
+
174
+ ```python
175
+ from stagehand import browserbase
176
+
177
+ browser = await browserbase.launch(api_key=os.environ["BROWSERBASE_API_KEY"])
178
+ stagehand = await Stagehand.create(browser=browser, cache=True)
179
+ ```
180
+
181
+ Use `browserbase.connect(api_key=..., session_id=...)` to attach to an existing session.
182
+ `browser.close()` releases the Browserbase session. For a `keep_alive=True` session, use
183
+ `await browser.disconnect()` to close the client and connection while keeping the session for later.
184
+ See [browser configuration](https://docs.stagehand.dev/v4/configuration/browser) for more options.
185
+
186
+ ## Search and fetch without a browser
187
+
188
+ [Fetch](https://docs.stagehand.dev/v4/add-ons/fetch) grabs the content of a URL as markdown.
189
+ [Search](https://docs.stagehand.dev/v4/add-ons/search) provides fast, token-efficient web search
190
+ results. Both complement browser sessions without launching a browser.
191
+
192
+ ```python
193
+ import asyncio
194
+ import os
195
+
196
+ from stagehand import browserbase
197
+
198
+
199
+ async def search_and_fetch() -> None:
200
+ results = await browserbase.search(
201
+ api_key=os.environ["BROWSERBASE_API_KEY"],
202
+ query="browser agent frameworks",
203
+ num_results=5,
204
+ )
205
+ fetched = await browserbase.fetch(
206
+ api_key=os.environ["BROWSERBASE_API_KEY"],
207
+ url=results.results[0].url,
208
+ format="markdown",
209
+ )
210
+ print(fetched.content)
211
+
212
+
213
+ asyncio.run(search_and_fetch())
214
+ ```
215
+
216
+ ## Python API notes
217
+
218
+ `Stagehand.act()`, `Stagehand.observe()`, and `Stagehand.extract()` use the active page by
219
+ default. Pass `page=page` to target a specific SDK `Page`.
220
+
221
+ `Page.goto()`, `reload()`, `go_back()`, and `go_forward()` return the main-document `Response`,
222
+ or `None` when navigation does not produce one. Response bodies and complete headers are retrieved
223
+ lazily while the Stagehand session remains open.
224
+
225
+ When contributing examples or tests, keep browser ownership explicit: launch or connect a
226
+ browser handle, pass it to `Stagehand.create()`, close Stagehand first, and close the browser in
227
+ the outermost `finally` block.
228
+
229
+ ## Docs and resources
230
+
231
+ - [Python examples](https://github.com/browserbase/stagehand/tree/main/packages/sdk-python/examples): actions, extraction, observation, and custom LLM usage.
232
+ - [Page](https://docs.stagehand.dev/v4/reference/page) and [locator](https://docs.stagehand.dev/v4/reference/locator): Playwright-style browser and element APIs.
233
+ - [Integrations](https://docs.stagehand.dev/v4/integrations/overview): agent frameworks and coding agents.
234
+ - [Main README](https://github.com/browserbase/stagehand/blob/main/README.md): project overview, MCP setup, and community links.
235
+
236
+ ## Contributing
237
+
238
+ Clone the [Stagehand repository](https://github.com/browserbase/stagehand) and run these commands
239
+ from its root. All Python projects share the root uv workspace, `uv.lock`, and `.venv`.
240
+ `just install` installs all workspace members, and consumers use this SDK from source.
241
+ See [the contributing guide](https://github.com/browserbase/stagehand/blob/main/CONTRIBUTING.md)
242
+ for workspace membership and package-specific commands.
243
+
244
+ ```bash
245
+ # Install uv
246
+ curl -LsSf https://astral.sh/uv/install.sh | sh
247
+
248
+ # Install just
249
+ brew install just
250
+
251
+ just install
252
+ just generate
253
+ just check
254
+ just test
255
+ just build
256
+ ```
@@ -0,0 +1,224 @@
1
+ <div id="toc" align="center" style="margin-bottom: 0;">
2
+ <ul style="list-style: none; margin: 0; padding: 0;">
3
+ <a href="https://stagehand.dev">
4
+ <picture>
5
+ <source media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/browserbase/stagehand/main/media/dark_logo.png" />
6
+ <img alt="Stagehand" src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/light_logo.png" width="200" style="margin-right: 30px;" />
7
+ </picture>
8
+ </a>
9
+ </ul>
10
+ </div>
11
+ <p align="center">
12
+ <strong>Stagehand is the SDK for browser agents</strong><br>
13
+ </p>
14
+
15
+ <p align="center">
16
+ <a href="https://trendshift.io/repositories/12122" target="_blank"><img src="https://trendshift.io/api/badge/repositories/12122" alt="browserbase%2Fstagehand | Trendshift" style="width: 250px; height: 55px;" width="250" height="55"/></a>
17
+ </p>
18
+
19
+ <p align="center">
20
+ <a href="https://docs.stagehand.dev"><strong>Docs</strong></a> ·
21
+ <a href="https://docs.stagehand.dev/v4/first-steps/quickstart"><strong>Quickstart</strong></a> ·
22
+ <a href="https://github.com/browserbase/stagehand"><strong>⭐ Star this repo</strong></a>
23
+ </p>
24
+
25
+ <p align="center">
26
+ <a href="https://github.com/browserbase/stagehand/tree/main?tab=MIT-1-ov-file#MIT-1-ov-file">
27
+ <picture>
28
+ <source media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/browserbase/stagehand/main/media/dark_license.svg" />
29
+ <img alt="MIT License" src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/light_license.svg" />
30
+ </picture>
31
+ </a>
32
+ <a href="https://discord.gg/stagehand">
33
+ <picture>
34
+ <source media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/browserbase/stagehand/main/media/dark_discord.svg" />
35
+ <img alt="Discord Community" src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/light_discord.svg" />
36
+ </picture>
37
+ </a>
38
+ <a href="https://deepwiki.com/browserbase/stagehand">
39
+ <img alt="Ask DeepWiki" src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/deepwiki.svg" width="156" height="32" />
40
+ </a>
41
+ </p>
42
+
43
+ <p align="center">
44
+ <a href="https://stagehand.dev">
45
+ <img src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/stagehand-website-banner.png" alt="Stagehand homepage showing browser automation in TypeScript, Python, and Go and a speed comparison with Playwright" width="100%" />
46
+ </a>
47
+ </p>
48
+
49
+ # Stagehand Python SDK
50
+
51
+ ## AI that uses the browser like humans.
52
+
53
+ Sign in once, keep the session, and pull structured data out the other side.
54
+
55
+ Replace `app.example.com` with your application's URL and set `OPENAI_API_KEY`, `APP_EMAIL`, and
56
+ `APP_PASSWORD` before running this example.
57
+
58
+ ```python
59
+ import asyncio
60
+ import os
61
+
62
+ from pydantic import BaseModel
63
+ from stagehand import Stagehand, local_browser
64
+
65
+
66
+ class Invoice(BaseModel):
67
+ number: str
68
+ amount: float
69
+ paid: bool
70
+
71
+
72
+ class Invoices(BaseModel):
73
+ invoices: list[Invoice]
74
+
75
+
76
+ async def main() -> None:
77
+ # Cookies persist in ./browser-data, so the next run starts already signed in
78
+ browser = await local_browser.launch(user_data_dir="./browser-data")
79
+ try:
80
+ stagehand = await Stagehand.create(
81
+ browser=browser,
82
+ model="openai/gpt-5.4-mini",
83
+ model_api_key=os.environ["OPENAI_API_KEY"],
84
+ )
85
+ try:
86
+ page = (await browser.context.pages())[0]
87
+ await page.goto("https://app.example.com/login")
88
+
89
+ # observe() returns real selectors, so credentials never reach the model
90
+ email = await stagehand.observe("find the email input")
91
+ password = await stagehand.observe("find the password input")
92
+ await page.locator(email.data[0].selector).fill(os.environ["APP_EMAIL"])
93
+ await page.locator(password.data[0].selector).fill(os.environ["APP_PASSWORD"])
94
+
95
+ # act() self-heals when the site redesigns its form
96
+ await stagehand.act("click the sign in button")
97
+ await stagehand.act("open the billing page")
98
+
99
+ # extract() returns schema-validated data
100
+ result = await stagehand.extract(
101
+ "extract every invoice in the table",
102
+ Invoices,
103
+ )
104
+ print(result.data.invoices)
105
+ finally:
106
+ await stagehand.close()
107
+ finally:
108
+ await browser.close()
109
+
110
+
111
+ asyncio.run(main())
112
+ ```
113
+
114
+ ## Install
115
+
116
+ ```bash
117
+ pip install stagehand
118
+ ```
119
+
120
+ Requires Python 3.11 or later. Local runs need [Chrome](https://www.google.com/chrome/) installed.
121
+ Full setup: [Quickstart](https://docs.stagehand.dev/v4/first-steps/quickstart).
122
+
123
+ ## Why Stagehand
124
+
125
+ - **Familiar APIs:** The Playwright-style methods you and your agents already know: `goto`, `click`, `locator`, `screenshot`.
126
+ - **Token efficiency:** Hybrid accessibility-tree trimming gives agents exactly the page context they need and nothing more.
127
+ - **Faster in production:** Stagehand runs as an extension next to the browser, cutting round-trip latency on every action.
128
+ - **Self-healing:** `act`, `observe`, and `extract` refresh how an action happens when the site changes underneath it.
129
+ - **Built for agents:** WebMCP, clipboard support, batch commands, deep locators for nested iframes and closed Shadow DOMs, OTel traces.
130
+ - **Three languages:** One complete browser driver across TypeScript, Python, and Go.
131
+
132
+ ## Run it on Browserbase
133
+
134
+ Point the same script at [Browserbase](https://www.browserbase.com). The
135
+ [Model Gateway](https://docs.stagehand.dev/v4/configuration/models#model-gateway) handles model
136
+ routing, and [server-side caching](https://docs.stagehand.dev/v4/best-practices/caching) reuses
137
+ results for repeated actions.
138
+
139
+ Import `browserbase` from `stagehand`, then use these browser and client setup calls inside the
140
+ async `main()` above, keeping its `try`/`finally` cleanup:
141
+
142
+ ```python
143
+ from stagehand import browserbase
144
+
145
+ browser = await browserbase.launch(api_key=os.environ["BROWSERBASE_API_KEY"])
146
+ stagehand = await Stagehand.create(browser=browser, cache=True)
147
+ ```
148
+
149
+ Use `browserbase.connect(api_key=..., session_id=...)` to attach to an existing session.
150
+ `browser.close()` releases the Browserbase session. For a `keep_alive=True` session, use
151
+ `await browser.disconnect()` to close the client and connection while keeping the session for later.
152
+ See [browser configuration](https://docs.stagehand.dev/v4/configuration/browser) for more options.
153
+
154
+ ## Search and fetch without a browser
155
+
156
+ [Fetch](https://docs.stagehand.dev/v4/add-ons/fetch) grabs the content of a URL as markdown.
157
+ [Search](https://docs.stagehand.dev/v4/add-ons/search) provides fast, token-efficient web search
158
+ results. Both complement browser sessions without launching a browser.
159
+
160
+ ```python
161
+ import asyncio
162
+ import os
163
+
164
+ from stagehand import browserbase
165
+
166
+
167
+ async def search_and_fetch() -> None:
168
+ results = await browserbase.search(
169
+ api_key=os.environ["BROWSERBASE_API_KEY"],
170
+ query="browser agent frameworks",
171
+ num_results=5,
172
+ )
173
+ fetched = await browserbase.fetch(
174
+ api_key=os.environ["BROWSERBASE_API_KEY"],
175
+ url=results.results[0].url,
176
+ format="markdown",
177
+ )
178
+ print(fetched.content)
179
+
180
+
181
+ asyncio.run(search_and_fetch())
182
+ ```
183
+
184
+ ## Python API notes
185
+
186
+ `Stagehand.act()`, `Stagehand.observe()`, and `Stagehand.extract()` use the active page by
187
+ default. Pass `page=page` to target a specific SDK `Page`.
188
+
189
+ `Page.goto()`, `reload()`, `go_back()`, and `go_forward()` return the main-document `Response`,
190
+ or `None` when navigation does not produce one. Response bodies and complete headers are retrieved
191
+ lazily while the Stagehand session remains open.
192
+
193
+ When contributing examples or tests, keep browser ownership explicit: launch or connect a
194
+ browser handle, pass it to `Stagehand.create()`, close Stagehand first, and close the browser in
195
+ the outermost `finally` block.
196
+
197
+ ## Docs and resources
198
+
199
+ - [Python examples](https://github.com/browserbase/stagehand/tree/main/packages/sdk-python/examples): actions, extraction, observation, and custom LLM usage.
200
+ - [Page](https://docs.stagehand.dev/v4/reference/page) and [locator](https://docs.stagehand.dev/v4/reference/locator): Playwright-style browser and element APIs.
201
+ - [Integrations](https://docs.stagehand.dev/v4/integrations/overview): agent frameworks and coding agents.
202
+ - [Main README](https://github.com/browserbase/stagehand/blob/main/README.md): project overview, MCP setup, and community links.
203
+
204
+ ## Contributing
205
+
206
+ Clone the [Stagehand repository](https://github.com/browserbase/stagehand) and run these commands
207
+ from its root. All Python projects share the root uv workspace, `uv.lock`, and `.venv`.
208
+ `just install` installs all workspace members, and consumers use this SDK from source.
209
+ See [the contributing guide](https://github.com/browserbase/stagehand/blob/main/CONTRIBUTING.md)
210
+ for workspace membership and package-specific commands.
211
+
212
+ ```bash
213
+ # Install uv
214
+ curl -LsSf https://astral.sh/uv/install.sh | sh
215
+
216
+ # Install just
217
+ brew install just
218
+
219
+ just install
220
+ just generate
221
+ just check
222
+ just test
223
+ just build
224
+ ```
@@ -1,6 +1,6 @@
1
1
  [project]
2
2
  name = "stagehand"
3
- version = "4.4.0a0.dev1676"
3
+ version = "4.4.1a0.dev1688"
4
4
  description = "Browserbase's SDK for building browser agents"
5
5
  readme = "README.md"
6
6
  requires-python = ">=3.11"
@@ -32,5 +32,5 @@
32
32
  }
33
33
  ],
34
34
  "options_page": "wake-service-worker.html",
35
- "version": "1.3.0"
35
+ "version": "1.3.1"
36
36
  }
@@ -9206,7 +9206,7 @@ function isRecord$2(value) {
9206
9206
  }
9207
9207
  var package_default$1 = {
9208
9208
  name: "@browserbasehq/stagehand-protocol",
9209
- version: "3.1.1-alpha-c82e6170c29ab6fb17c4a10e44812bd29507e7d4",
9209
+ version: "3.1.1",
9210
9210
  "private": true,
9211
9211
  type: "module",
9212
9212
  exports: {
@@ -66119,7 +66119,7 @@ var WebTracerProvider = class extends BasicTracerProvider {
66119
66119
  };
66120
66120
  var package_default = {
66121
66121
  name: "@browserbasehq/stagehand-extension",
66122
- version: "1.3.0-alpha-c82e6170c29ab6fb17c4a10e44812bd29507e7d4",
66122
+ version: "1.3.1-alpha-b29016565dc83dc4f0e56948fb11210dce7e4df0",
66123
66123
  "private": true,
66124
66124
  type: "module",
66125
66125
  scripts: {
@@ -67067,9 +67067,12 @@ function createDeferred$1() {
67067
67067
  function normaliseHeaderName(name) {
67068
67068
  return name.toLowerCase();
67069
67069
  }
67070
- /** Split multi-value header strings into discrete values while trimming. */
67070
+ /**
67071
+ * Split multi-value header strings into discrete values while trimming. An
67072
+ * empty value is kept: the header was still sent, so it must stay visible.
67073
+ */
67071
67074
  function splitHeaderValues(value) {
67072
- return value.split(/\r?\n/).map((part) => part.trim()).filter(Boolean);
67075
+ return value.split(/\r?\n/).map((part) => part.trim());
67073
67076
  }
67074
67077
  /**
67075
67078
  * Parse an HTTP header text block (as emitted by CDP) into an ordered array of
@@ -1,4 +1,4 @@
1
1
  """Generated from packages/protocol/package.json. Do not edit."""
2
2
 
3
3
  PROTOCOL_SEMVER_PATTERN = '^(0|[1-9]\\d*)\\.(0|[1-9]\\d*)\\.(0|[1-9]\\d*)(?:-((?:0|[1-9]\\d*|\\d*[A-Za-z-][0-9A-Za-z-]*)(?:\\.(?:0|[1-9]\\d*|\\d*[A-Za-z-][0-9A-Za-z-]*))*))?(?:\\+([0-9A-Za-z-]+(?:\\.[0-9A-Za-z-]+)*))?$'
4
- STAGEHAND_PROTOCOL_VERSION = '3.1.1-alpha-c82e6170c29ab6fb17c4a10e44812bd29507e7d4'
4
+ STAGEHAND_PROTOCOL_VERSION = '3.1.1'
@@ -1,205 +0,0 @@
1
- Metadata-Version: 2.4
2
- Name: stagehand
3
- Version: 4.4.0a0.dev1676
4
- Summary: Browserbase's SDK for building browser agents
5
- Keywords: ai,agent,ai-agent,browser,browser-agent,browser-automation,computer-use,headless,playwright,cdp,llm,automation,web-scraping,testing
6
- Author: Browserbase
7
- License-Expression: MIT
8
- Classifier: Development Status :: 5 - Production/Stable
9
- Classifier: Intended Audience :: Developers
10
- Classifier: Operating System :: OS Independent
11
- Classifier: Programming Language :: Python :: 3
12
- Classifier: Programming Language :: Python :: 3 :: Only
13
- Classifier: Programming Language :: Python :: 3.11
14
- Classifier: Topic :: Internet :: WWW/HTTP :: Browsers
15
- Classifier: Topic :: Scientific/Engineering :: Artificial Intelligence
16
- Classifier: Topic :: Software Development :: Libraries :: Python Modules
17
- Classifier: Topic :: Software Development :: Testing
18
- Classifier: Typing :: Typed
19
- Classifier: Framework :: AsyncIO
20
- Requires-Dist: browserbase>=1.15,<2
21
- Requires-Dist: httpx>=0.23,<1
22
- Requires-Dist: opentelemetry-api>=1.35,<2
23
- Requires-Dist: pydantic>=2.12,<3
24
- Requires-Dist: typing-extensions>=4.12,<5
25
- Requires-Dist: websockets>=16.1.1
26
- Requires-Python: >=3.11
27
- Project-URL: Homepage, https://stagehand.dev
28
- Project-URL: Documentation, https://docs.stagehand.dev
29
- Project-URL: Repository, https://github.com/browserbase/stagehand
30
- Project-URL: Issues, https://github.com/browserbase/stagehand/issues
31
- Description-Content-Type: text/markdown
32
-
33
- <div id="toc" align="center" style="margin-bottom: 0;">
34
- <ul style="list-style: none; margin: 0; padding: 0;">
35
- <a href="https://stagehand.dev">
36
- <picture>
37
- <source media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/browserbase/stagehand/main/media/dark_logo.png" />
38
- <img alt="Stagehand" src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/light_logo.png" width="200" style="margin-right: 30px;" />
39
- </picture>
40
- </a>
41
- </ul>
42
- </div>
43
- <p align="center">
44
- <strong>Stagehand is the SDK for browser agents.</strong><br>
45
- <a href="https://docs.stagehand.dev">Read the Docs</a>
46
- </p>
47
-
48
- <p align="center">
49
- <a href="https://github.com/browserbase/stagehand/tree/main?tab=MIT-1-ov-file#MIT-1-ov-file">
50
- <picture>
51
- <source media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/browserbase/stagehand/main/media/dark_license.svg" />
52
- <img alt="MIT License" src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/light_license.svg" />
53
- </picture>
54
- </a>
55
- <a href="https://discord.gg/stagehand">
56
- <picture>
57
- <source media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/browserbase/stagehand/main/media/dark_discord.svg" />
58
- <img alt="Discord Community" src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/light_discord.svg" />
59
- </picture>
60
- </a>
61
- </p>
62
-
63
- <p align="center">
64
- <a href="https://trendshift.io/repositories/12122" target="_blank"><img src="https://trendshift.io/api/badge/repositories/12122" alt="browserbase%2Fstagehand | Trendshift" style="width: 250px; height: 55px;" width="250" height="55"/></a>
65
- </p>
66
-
67
- <p align="center">
68
- <a href="https://deepwiki.com/browserbase/stagehand">
69
- <img alt="Ask DeepWiki" src="https://deepwiki.com/badge.svg" />
70
- </a>
71
- </p>
72
-
73
- # Stagehand Python SDK
74
-
75
- ## What is Stagehand?
76
-
77
- Stagehand is the SDK for browser agents. Playwright was built for testing, Stagehand is built for agents. Use familiar APIs, self-healing actions, and network-level security across TypeScript, Python, and Go.
78
-
79
- ## Why Stagehand?
80
-
81
- Stagehand gives browser agents an interface built for how they actually work. It combines familiar Playwright-style APIs with self-healing actions, agent-optimized page context, and native support for complex DOM structures like out-of-process iframes and closed Shadow DOMs.
82
-
83
- Agents use fewer tokens, recover when websites change, and complete tasks more reliably. With a complete browser driver across TypeScript, Python, and Go, Stagehand delivers the flexibility of AI without sacrificing the speed, control, determinism, reliability, and observability required in production.
84
-
85
- For the full overview, examples, and contributing guide, see the [main README](https://github.com/browserbase/stagehand/blob/main/README.md).
86
-
87
- ## Example
88
-
89
- The async Python SDK for Stagehand browser automation:
90
-
91
- ```python
92
- import asyncio
93
- import os
94
-
95
- from pydantic import BaseModel
96
-
97
- from stagehand import Stagehand, browserbase, local_browser
98
-
99
-
100
- class PullRequest(BaseModel):
101
- author: str
102
- title: str
103
-
104
-
105
- async def main() -> None:
106
- browser = await local_browser.launch(headless=True)
107
- try:
108
- stagehand = await Stagehand.create(
109
- browser=browser,
110
- model="openai/gpt-5.4-mini",
111
- model_api_key=os.environ["OPENAI_API_KEY"],
112
- )
113
- try:
114
- page = (await browser.context.pages())[0]
115
- await page.goto("https://github.com/browserbase")
116
-
117
- # act() executes individual actions
118
- await stagehand.act("click on the stagehand repo")
119
-
120
- # observe() reports what is actionable on the page
121
- observed = await stagehand.observe("find the latest PR")
122
-
123
- # Locators give deterministic, Playwright-style actions
124
- await page.locator(observed.data[0].selector).click()
125
-
126
- # extract() returns structured data validated by a pydantic model
127
- result = await stagehand.extract(
128
- "extract the author and title of the PR",
129
- PullRequest,
130
- )
131
- print(result.data.author, result.data.title)
132
- finally:
133
- await stagehand.close()
134
- finally:
135
- await browser.close()
136
-
137
-
138
- asyncio.run(main())
139
- ```
140
-
141
- See [`examples`](examples) for action, extraction, observation, and custom LLM usage.
142
-
143
- For hosted browsers, import `browserbase` from `stagehand` and use
144
- `browserbase.launch(api_key=...)` or `browserbase.connect(api_key=..., session_id=...)` instead of
145
- `local_browser`. Calling `close()` on the browser handle releases the Browserbase session. To keep
146
- a `keep_alive=True` session for later, call `stagehand.close()` without `browser.close()`.
147
-
148
- The same `browserbase` facade exposes Browserbase Search and Fetch without launching a browser:
149
-
150
- ```python
151
- import asyncio
152
- import os
153
-
154
- from stagehand import browserbase
155
-
156
-
157
- async def search_and_fetch() -> None:
158
- results = await browserbase.search(
159
- api_key=os.environ["BROWSERBASE_API_KEY"],
160
- query="browser agent frameworks",
161
- num_results=5,
162
- )
163
- fetched = await browserbase.fetch(
164
- api_key=os.environ["BROWSERBASE_API_KEY"],
165
- url=results.results[0].url,
166
- format="markdown",
167
- )
168
- print(fetched.content)
169
-
170
-
171
- asyncio.run(search_and_fetch())
172
- ```
173
-
174
- `Stagehand.act()`, `Stagehand.observe()`, and `Stagehand.extract()` use the active page by
175
- default. Pass `page=page` to target a specific SDK `Page`.
176
-
177
- `Page.goto()`, `reload()`, `go_back()`, and `go_forward()` return the main-document `Response`,
178
- or `None` when navigation does not produce one. Response bodies and complete headers are retrieved
179
- lazily while the Stagehand session remains open.
180
-
181
- When contributing examples or tests, keep browser ownership explicit: launch or connect a
182
- browser handle, pass it to `Stagehand.create()`, close Stagehand first, and close the browser in
183
- the outermost `finally` block.
184
-
185
- ## Contributing
186
-
187
- Clone the [Stagehand repository](https://github.com/browserbase/stagehand) and run these commands
188
- from its root. All Python projects share the root uv workspace, `uv.lock`, and `.venv`.
189
- `just install` installs all workspace members, and consumers use this SDK from source.
190
- See [the contributing guide](https://github.com/browserbase/stagehand/blob/main/CONTRIBUTING.md)
191
- for workspace membership and package-specific commands.
192
-
193
- ```bash
194
- # Install uv
195
- curl -LsSf https://astral.sh/uv/install.sh | sh
196
-
197
- # Install just
198
- brew install just
199
-
200
- just install
201
- just generate
202
- just check
203
- just test
204
- just build
205
- ```
@@ -1,173 +0,0 @@
1
- <div id="toc" align="center" style="margin-bottom: 0;">
2
- <ul style="list-style: none; margin: 0; padding: 0;">
3
- <a href="https://stagehand.dev">
4
- <picture>
5
- <source media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/browserbase/stagehand/main/media/dark_logo.png" />
6
- <img alt="Stagehand" src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/light_logo.png" width="200" style="margin-right: 30px;" />
7
- </picture>
8
- </a>
9
- </ul>
10
- </div>
11
- <p align="center">
12
- <strong>Stagehand is the SDK for browser agents.</strong><br>
13
- <a href="https://docs.stagehand.dev">Read the Docs</a>
14
- </p>
15
-
16
- <p align="center">
17
- <a href="https://github.com/browserbase/stagehand/tree/main?tab=MIT-1-ov-file#MIT-1-ov-file">
18
- <picture>
19
- <source media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/browserbase/stagehand/main/media/dark_license.svg" />
20
- <img alt="MIT License" src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/light_license.svg" />
21
- </picture>
22
- </a>
23
- <a href="https://discord.gg/stagehand">
24
- <picture>
25
- <source media="(prefers-color-scheme: dark)" srcset="https://raw.githubusercontent.com/browserbase/stagehand/main/media/dark_discord.svg" />
26
- <img alt="Discord Community" src="https://raw.githubusercontent.com/browserbase/stagehand/main/media/light_discord.svg" />
27
- </picture>
28
- </a>
29
- </p>
30
-
31
- <p align="center">
32
- <a href="https://trendshift.io/repositories/12122" target="_blank"><img src="https://trendshift.io/api/badge/repositories/12122" alt="browserbase%2Fstagehand | Trendshift" style="width: 250px; height: 55px;" width="250" height="55"/></a>
33
- </p>
34
-
35
- <p align="center">
36
- <a href="https://deepwiki.com/browserbase/stagehand">
37
- <img alt="Ask DeepWiki" src="https://deepwiki.com/badge.svg" />
38
- </a>
39
- </p>
40
-
41
- # Stagehand Python SDK
42
-
43
- ## What is Stagehand?
44
-
45
- Stagehand is the SDK for browser agents. Playwright was built for testing, Stagehand is built for agents. Use familiar APIs, self-healing actions, and network-level security across TypeScript, Python, and Go.
46
-
47
- ## Why Stagehand?
48
-
49
- Stagehand gives browser agents an interface built for how they actually work. It combines familiar Playwright-style APIs with self-healing actions, agent-optimized page context, and native support for complex DOM structures like out-of-process iframes and closed Shadow DOMs.
50
-
51
- Agents use fewer tokens, recover when websites change, and complete tasks more reliably. With a complete browser driver across TypeScript, Python, and Go, Stagehand delivers the flexibility of AI without sacrificing the speed, control, determinism, reliability, and observability required in production.
52
-
53
- For the full overview, examples, and contributing guide, see the [main README](https://github.com/browserbase/stagehand/blob/main/README.md).
54
-
55
- ## Example
56
-
57
- The async Python SDK for Stagehand browser automation:
58
-
59
- ```python
60
- import asyncio
61
- import os
62
-
63
- from pydantic import BaseModel
64
-
65
- from stagehand import Stagehand, browserbase, local_browser
66
-
67
-
68
- class PullRequest(BaseModel):
69
- author: str
70
- title: str
71
-
72
-
73
- async def main() -> None:
74
- browser = await local_browser.launch(headless=True)
75
- try:
76
- stagehand = await Stagehand.create(
77
- browser=browser,
78
- model="openai/gpt-5.4-mini",
79
- model_api_key=os.environ["OPENAI_API_KEY"],
80
- )
81
- try:
82
- page = (await browser.context.pages())[0]
83
- await page.goto("https://github.com/browserbase")
84
-
85
- # act() executes individual actions
86
- await stagehand.act("click on the stagehand repo")
87
-
88
- # observe() reports what is actionable on the page
89
- observed = await stagehand.observe("find the latest PR")
90
-
91
- # Locators give deterministic, Playwright-style actions
92
- await page.locator(observed.data[0].selector).click()
93
-
94
- # extract() returns structured data validated by a pydantic model
95
- result = await stagehand.extract(
96
- "extract the author and title of the PR",
97
- PullRequest,
98
- )
99
- print(result.data.author, result.data.title)
100
- finally:
101
- await stagehand.close()
102
- finally:
103
- await browser.close()
104
-
105
-
106
- asyncio.run(main())
107
- ```
108
-
109
- See [`examples`](examples) for action, extraction, observation, and custom LLM usage.
110
-
111
- For hosted browsers, import `browserbase` from `stagehand` and use
112
- `browserbase.launch(api_key=...)` or `browserbase.connect(api_key=..., session_id=...)` instead of
113
- `local_browser`. Calling `close()` on the browser handle releases the Browserbase session. To keep
114
- a `keep_alive=True` session for later, call `stagehand.close()` without `browser.close()`.
115
-
116
- The same `browserbase` facade exposes Browserbase Search and Fetch without launching a browser:
117
-
118
- ```python
119
- import asyncio
120
- import os
121
-
122
- from stagehand import browserbase
123
-
124
-
125
- async def search_and_fetch() -> None:
126
- results = await browserbase.search(
127
- api_key=os.environ["BROWSERBASE_API_KEY"],
128
- query="browser agent frameworks",
129
- num_results=5,
130
- )
131
- fetched = await browserbase.fetch(
132
- api_key=os.environ["BROWSERBASE_API_KEY"],
133
- url=results.results[0].url,
134
- format="markdown",
135
- )
136
- print(fetched.content)
137
-
138
-
139
- asyncio.run(search_and_fetch())
140
- ```
141
-
142
- `Stagehand.act()`, `Stagehand.observe()`, and `Stagehand.extract()` use the active page by
143
- default. Pass `page=page` to target a specific SDK `Page`.
144
-
145
- `Page.goto()`, `reload()`, `go_back()`, and `go_forward()` return the main-document `Response`,
146
- or `None` when navigation does not produce one. Response bodies and complete headers are retrieved
147
- lazily while the Stagehand session remains open.
148
-
149
- When contributing examples or tests, keep browser ownership explicit: launch or connect a
150
- browser handle, pass it to `Stagehand.create()`, close Stagehand first, and close the browser in
151
- the outermost `finally` block.
152
-
153
- ## Contributing
154
-
155
- Clone the [Stagehand repository](https://github.com/browserbase/stagehand) and run these commands
156
- from its root. All Python projects share the root uv workspace, `uv.lock`, and `.venv`.
157
- `just install` installs all workspace members, and consumers use this SDK from source.
158
- See [the contributing guide](https://github.com/browserbase/stagehand/blob/main/CONTRIBUTING.md)
159
- for workspace membership and package-specific commands.
160
-
161
- ```bash
162
- # Install uv
163
- curl -LsSf https://astral.sh/uv/install.sh | sh
164
-
165
- # Install just
166
- brew install just
167
-
168
- just install
169
- just generate
170
- just check
171
- just test
172
- just build
173
- ```