browser-use-sdk changedagents-and-tools/tool-use/browser-use-sdk
Nearest release: v2.1.312, published under an hour before this site recorded the change. Shown because the two are within 24 hours of each other. Nothing here says the release caused the edit.
Recorded here
Lines+96added
Lines−96removed
From line
8
where the diff opens
First seen
15 Oct 2026
this site's first read of the page
Recorded edits6to this page, all time
The whole hunk
from line 8, old and new numbered
/
from line 8
88
99The SDK connects Claude to your browser or desktop. It runs the checks you configure, such as a URL policy for `navigate` or an approval callback. It sends each call that passes to your driver and builds the `tool_result` from what the driver returns. The [tool runner](https://platform.claude.com/docs/en/agents-and-tools/tool-use/tool-runner) can run the agentic loop for you.
1010
11You supply the driver, which operates the browser or desktop. Start from a [provider's driver](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#use-a-driver-from-a-provider). With one, an agent takes a few lines of code. If none fits, write your own with a browser automation library such as Playwright.
11You supply the driver, which operates the browser or desktop. Start from a [provider’s driver](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#use-a-driver-from-a-provider). With one, an agent takes a few lines of code. If none fits, write your own with a browser automation library such as Playwright.
1212
1313Most of this page is about the browser toolset. [Computer toolset](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#computer-toolset) covers what differs.
1414
15Writing your own driver is an advanced case, covered in [Implement a driver](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#implement-a-driver). The claude-quickstarts repository also has an [example browser driver](https://github.com/anthropics/claude-quickstarts/tree/main/browser-toolset) in Python and TypeScript. It controls Chromium through the Chrome DevTools Protocol (CDP), and it isn't production code.
15Writing your own driver is an advanced case, covered in [Implement a driver](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#implement-a-driver). The claude-quickstarts repository also has an [example browser driver](https://github.com/anthropics/claude-quickstarts/tree/main/browser-toolset) in Python and TypeScript. It controls Chromium through the Chrome DevTools Protocol (CDP), and it isn’t production code.
1616
1717<Note>
1818 The browser toolset class is in beta and available in the [Python SDK](https://github.com/anthropics/anthropic-sdk-python/blob/main/browser-toolset.md) and the [TypeScript SDK](https://github.com/anthropics/anthropic-sdk-typescript/blob/main/browser-toolset.md). The computer toolset class is in beta in the same SDKs, which have a [Python computer toolset guide](https://github.com/anthropics/anthropic-sdk-python/blob/main/computer-toolset.md) and a [TypeScript computer toolset guide](https://github.com/anthropics/anthropic-sdk-typescript/blob/main/computer-toolset.md).
from line 20
2020
2121## Use a driver from a provider
2222
23With a driver from a provider, such as one under [Partner integrations](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#partner-integrations), you can build an agent in a few lines of code. The provider in this example is made up. Replace `example_browser_provider` (typescript: `example-browser-provider`) and `ExampleBrowser` with a real provider's package and driver class, and set them up as the provider's docs describe.
23With a driver from a provider, such as one under [Partner integrations](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#partner-integrations), you can build an agent in a few lines of code. The provider in this example is made up. Replace `example_browser_provider` (typescript: `example-browser-provider`) and `ExampleBrowser` with a real provider’s package and driver class, and set them up as the provider’s docs describe.
2424
2525<CodeGroup exclude="shell:cURL, shell:CLI, csharp, go, java, php, ruby">
2626 ```python Python
from line 63
6363 ```
6464</CodeGroup>
6565
66Pass the driver instance itself as the `tools` entry. The runner never closes the toolset, so one instance can serve several runs. Close it when you're done.
66Pass the driver instance itself as the `tools` entry. The runner never closes the toolset, so one instance can serve several runs. Close it when you’re done.
6767
6868To write your own driver, see [Implement a driver](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#implement-a-driver).
6969
from line 95
9595 Do these two things before you run a driver against anything but a throwaway browser:
9696
9797 * [Write a URL policy](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#write-a-url-policy). Without one, the SDK checks no URL. For a browser that a provider hosts, also read [Remote and hosted browsers](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#remote-and-hosted-browsers).
98 * Use a browser profile that isn't signed in to any account whose data or actions you wouldn't hand to Claude. See [Isolate the browser host](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#isolate-the-browser-host).
98 * Use a browser profile that isn’t signed in to any account whose data or actions you wouldn’t hand to Claude. See [Isolate the browser host](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#isolate-the-browser-host).
9999
100100 [Run the toolset safely](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#run-the-toolset-safely) covers the rest.
101101</Warning>
from line 124
124124 ```
125125</CodeGroup>
126126
127The SDK refuses a call to a disabled member before your code runs. Enabling a member your class doesn't implement is a configuration error, unless the class overrides `execute`.
127The SDK refuses a call to a disabled member before your code runs. Enabling a member your class doesn’t implement is a configuration error, unless the class overrides `execute`.
128128
129129### Add before and after hooks
130130
131Override `execute` and call the parent's `execute`. Code before that call runs after the [URL policy](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#write-a-url-policy), the [file policy](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#confine-uploads-and-downloads), and [`confirm`](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#gate-consequential-members), and it can change the input. The SDK doesn't check the changed input again. Code after the call receives the result, and it can change the result. Raise `ToolError` (throw it in TypeScript) to refuse the call.
131Override `execute` and call the parent’s `execute`. Code before that call runs after the [URL policy](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#write-a-url-policy), the [file policy](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#confine-uploads-and-downloads), and [`confirm`](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#gate-consequential-members), and it can change the input. The SDK doesn’t check the changed input again. Code after the call receives the result, and it can change the result. Raise `ToolError` (throw it in TypeScript) to refuse the call.
132132
133Overriding `execute` changes which members Claude is offered. The SDK counts every member as implemented, so Claude is offered every member that's on by default. The `MyBrowser` in the [advanced example](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#quick-start) serves three members, so the following `TracedBrowser` offers Claude members it can't serve. Turn those members off with `configs` before you use it.
133Overriding `execute` changes which members Claude is offered. The SDK counts every member as implemented, so Claude is offered every member that’s on by default. The `MyBrowser` in the [advanced example](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#quick-start) serves three members, so the following `TracedBrowser` offers Claude members it can’t serve. Turn those members off with `configs` before you use it.
134134
135135<CodeGroup exclude="shell:cURL, shell:CLI, csharp, go, java, php, ruby">
136136 ```python Python
from line 171
171171
172172## Implement a driver
173173
174A driver is your subclass of `BetaAbstractBrowserToolset20260801`. In it, override the members your browser supports. A member you don't implement is sent to the API as disabled. If Claude calls it anyway, the SDK returns an error, and the run continues. Overriding `execute` changes which members are sent as disabled ([Add before and after hooks](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#add-before-and-after-hooks)). Each member receives the call context and the member's input as a typed object, such as `BetaBrowserNavigateInput`. The input types come from `anthropic.types.beta` (typescript: `@anthropic-ai/sdk/resources/beta`). [Member tools](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-tool#member-tools) lists each input's fields.
174A driver is your subclass of `BetaAbstractBrowserToolset20260801`. In it, override the members your browser supports. A member you don’t implement is sent to the API as disabled. If Claude calls it anyway, the SDK returns an error, and the run continues. Overriding `execute` changes which members are sent as disabled ([Add before and after hooks](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#add-before-and-after-hooks)). Each member receives the call context and the member’s input as a typed object, such as `BetaBrowserNavigateInput`. The input types come from `anthropic.types.beta` (typescript: `@anthropic-ai/sdk/resources/beta`). [Member tools](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-tool#member-tools) lists each input’s fields.
175175
176176In TypeScript, spell the `type` member `type_`, and write members as methods, not arrow-function fields, because the SDK finds them on the prototype.
177177
from line 197
197197
198198Put all of these in `state_changes`. A refused navigation is `anthropic.tools.browser.BetaNavigationRefused()` (typescript: `{ type: "navigation_refused" }`), and a dismissed dialog is `anthropic.tools.browser.BetaDialogDismissed(kind=..., message=...)` (typescript: `{ type: "dialog_dismissed", kind, message }`).
199199
200The last two aren't API state changes. The SDK reports them to Claude as text outside the `browser_state` block: one line for all refused navigations, which doesn't include a URL, and a line for each of the first three dismissed dialogs, then a count of any others.
200The last two aren’t API state changes. The SDK reports them to Claude as text outside the `browser_state` block: one line for all refused navigations, which doesn’t include a URL, and a line for each of the first three dismissed dialogs, then a count of any others.
201201
202When any tab is open, exactly one must be active. Every member that takes a `tab_id` must act on the tab it names. The API's limits on the report are listed under [Track tabs with `browser_state`](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-tool#track-tabs-and-page-state).
202When any tab is open, exactly one must be active. Every member that takes a `tab_id` must act on the tab it names. The API’s limits on the report are listed under [Track tabs with `browser_state`](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-tool#track-tabs-and-page-state).
203203
204Claude reads each tab's URL, each download's URL, and the URL that your `navigate` returns, as your driver wrote them. The SDK doesn't parse these URLs. It turns line breaks and other control characters into spaces, trims the ends, and cuts each URL at 4,096 characters. So a `data:` URL's contents, a `file:` URL's path, and a username or password in a URL all reach Claude.
204Claude reads each tab’s URL, each download’s URL, and the URL that your `navigate` returns, as your driver wrote them. The SDK doesn’t parse these URLs. It turns line breaks and other control characters into spaces, trims the ends, and cuts each URL at 4,096 characters. So a `data:` URL’s contents, a `file:` URL’s path, and a username or password in a URL all reach Claude.
205205
206206### Handle errors
207207
from line 211
211211| `ToolsetUsageError` | Nothing | Stops |
212212| Any other exception | `ClassName: message` (typescript: `Error: message`), as an error result | Continues |
213213
214The SDK raises `ToolsetUsageError` for a configuration error, a misuse of the SDK during a call, or a call after `close`. It also raises one when `_browser_state` (typescript: `browserState`) raises any exception, even a `ToolError`. The tool runner and `tool_result` (typescript: `toolResult`) don't catch it, so it reaches their caller.
214The SDK raises `ToolsetUsageError` for a configuration error, a misuse of the SDK during a call, or a call after `close`. It also raises one when `_browser_state` (typescript: `browserState`) raises any exception, even a `ToolError`. The tool runner and `tool_result` (typescript: `toolResult`) don’t catch it, so it reaches their caller.
215215
216The SDK doesn't hide local paths in a member's error text, in the line an action such as `left_click` returns, in a failed download's error, or in a dismissed dialog's message.
216The SDK doesn’t hide local paths in a member’s error text, in the line an action such as `left_click` returns, in a failed download’s error, or in a dismissed dialog’s message.
217217
218218A `ToolError` from your URL policy, file policy, or `confirm` callable reaches Claude as written, so leave local paths out of its text. Catch exceptions in your members, and raise `ToolError` (throw it in TypeScript) with your own text.
219219
220220### Start calls while the response streams
221221
222By default, the tool runner runs a turn's calls after Claude's response ends. With early start, it can start a browser or computer call while the response is still streaming.
222By default, the tool runner runs a turn’s calls after Claude’s response ends. With early start, it can start a browser or computer call while the response is still streaming.
223223
224224To turn it on, pass `stream=True` (typescript: `stream: true`) and `run_tools_eagerly=True` (typescript: `runToolsEagerly: true`) to the tool runner, as the [advanced example](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#quick-start) does. With `stream`, each pass through your loop over the runner gives you a stream instead of a message.
225225
from line 226
226226Early start changes when a call can start, not how the toolset runs it:
227227
228228* **The checks still run first:** The SDK calls your URL policy, your file policy, and `confirm` before a call runs. With early start, it can call `confirm` while the response is still streaming.
229* **Calls still run one at a time:** A toolset runs its calls in the order Claude wrote them. A failed call still stops that toolset's later calls in the turn.
230* **A call that has started can't be taken back:** If the response is then cut off, for example at `max_tokens`, or your loop stops early, the action still occurs, and Claude never reads its result.
229* **Calls still run one at a time:** A toolset runs its calls in the order Claude wrote them. A failed call still stops that toolset’s later calls in the turn.
230* **A call that has started can’t be taken back:** If the response is then cut off, for example at `max_tokens`, or your loop stops early, the action still occurs, and Claude never reads its result.
231231
232232### Run without the tool runner
233233
234234Pass `browser` (typescript: `browser.toJSON()`) in `tools`, and answer each member call with `tool_result` (typescript: `toolResult`). The browser use tool requires you to stop at the first failed call ([Batch actions](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-tool#batch-actions)).
235235
236This loop uses `MyBrowser` and the URL policy from the [advanced example](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#quick-start). After a failed call, it answers the turn's later calls without running them:
236This loop uses `MyBrowser` and the URL policy from the [advanced example](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#quick-start). After a failed call, it answers the turn’s later calls without running them:
237237
238238<CodeGroup exclude="shell:cURL, shell:CLI, csharp, go, java, php, ruby">
239239 ```python Python
from line 330
330330 ```
331331</CodeGroup>
332332
333Each answer to a skipped call carries `is_error`, the call's `toolset_name`, and the exact text that [Batch actions](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-tool#batch-actions) requires. The tool runner sends the same answer.
333Each answer to a skipped call carries `is_error`, the call’s `toolset_name`, and the exact text that [Batch actions](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-tool#batch-actions) requires. The tool runner sends the same answer.
334334
335335## Advanced example: write your own driver
336336
from line 567
567567
568568## Run the toolset safely
569569
570Claude's next action depends on the pages it reads. A page, or text injected into one, can attempt to reach internal services or pull files off the host. It can also attempt to trigger actions with real effects. Before you run a driver against anything but a throwaway browser, take these six steps:
570Claude’s next action depends on the pages it reads. A page, or text injected into one, can attempt to reach internal services or pull files off the host. It can also attempt to trigger actions with real effects. Before you run a driver against anything but a throwaway browser, take these six steps:
571571
5721. [Write a URL policy](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#write-a-url-policy) that refuses every `navigate` URL the task doesn't need.
5721. [Write a URL policy](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#write-a-url-policy) that refuses every `navigate` URL the task doesn’t need.
5735732. [Intercept requests in the driver](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#intercept-requests-in-the-driver), and check each request with the same rules.
5743. [Put egress policy on the container](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#put-egress-policy-on-the-container), so the network blocks what the driver can't see.
5743. [Put egress policy on the container](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#put-egress-policy-on-the-container), so the network blocks what the driver can’t see.
5755754. [Confine uploads and downloads](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#confine-uploads-and-downloads), or leave uploads off.
5765765. [Gate consequential members](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#gate-consequential-members) with `confirm`.
5775776. [Isolate the browser host](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#isolate-the-browser-host) in a dedicated container or VM for each session.
from line 579
579579The SDK applies steps 1, 4, and 5 through the policies and the callable you pass. Steps 2, 3, and 6 are up to your driver and your deployment. The precautions under [Security considerations](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-tool#security-considerations) apply as well.
580580
581581<Note>
582 Anthropic's prompt-injection classifiers, described under [Security considerations](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-tool#security-considerations), don't currently run on browser toolset requests sent through Amazon Bedrock.
582 Anthropic’s prompt-injection classifiers, described under [Security considerations](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-tool#security-considerations), don’t currently run on browser toolset requests sent through Amazon Bedrock.
583583</Note>
584584
585585### Write a URL policy
586586
587587<Warning>
588 Without a URL policy, the SDK checks no URL, and the API doesn't filter the URLs Claude opens. Even with a policy, a link Claude clicks or a redirect can take the browser to loopback (`localhost`, `127.0.0.1`), to link-local addresses such as the cloud metadata address `169.254.169.254`, and to private network ranges. [Egress rules on the container](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#put-egress-policy-on-the-container) can block the link-local and private addresses. Rules enforced outside the container can't block loopback.
588 Without a URL policy, the SDK checks no URL, and the API doesn’t filter the URLs Claude opens. Even with a policy, a link Claude clicks or a redirect can take the browser to loopback (`localhost`, `127.0.0.1`), to link-local addresses such as the cloud metadata address `169.254.169.254`, and to private network ranges. [Egress rules on the container](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#put-egress-policy-on-the-container) can block the link-local and private addresses. Rules enforced outside the container can’t block loopback.
589589
590 The SDK doesn't check a URL's scheme, so your driver must refuse every scheme that you don't intend it to open, such as `javascript:`, `view-source:`, `data:`, and `file:`. Most drivers need only `http` and `https`. The example policy later in this section allows only `http` and `https` URLs, plus `about:blank`.
590 The SDK doesn’t check a URL’s scheme, so your driver must refuse every scheme that you don’t intend it to open, such as `javascript:`, `view-source:`, `data:`, and `file:`. Most drivers need only `http` and `https`. The example policy later in this section allows only `http` and `https` URLs, plus `about:blank`.
591591
592 A `file:` URL lets Claude read files on the browser host. A `javascript:` URL runs script in the current page, even when `javascript_exec` is off. Egress rules don't stop either one.
592 A `file:` URL lets Claude read files on the browser host. A `javascript:` URL runs script in the current page, even when `javascript_exec` is off. Egress rules don’t stop either one.
593593</Warning>
594594
595A URL policy is a function that you pass as `url_policy` (typescript: `urlPolicy`). You write the policy, and you're responsible for making it ready for production. Before your `navigate` runs, the SDK calls the policy with the call's context and the URL as Claude wrote it.
595A URL policy is a function that you pass as `url_policy` (typescript: `urlPolicy`). You write the policy, and you’re responsible for making it ready for production. Before your `navigate` runs, the SDK calls the policy with the call’s context and the URL as Claude wrote it.
596596
597Return nothing to allow the URL. To refuse it, raise `ToolError` (throw it in TypeScript). Claude reads the error's message, and `navigate` doesn't run. The policy checks only the URL in each `navigate` call. It isn't a network control.
597Return nothing to allow the URL. To refuse it, raise `ToolError` (throw it in TypeScript). Claude reads the error’s message, and `navigate` doesn’t run. The policy checks only the URL in each `navigate` call. It isn’t a network control.
598598
599599This is the policy from the [advanced example](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#quick-start). It allows `about:blank`, plus two sites and their subdomains over `http` and `https`:
600600
from line 662
662662 ```
663663</CodeGroup>
664664
665The SDK calls the policy only for `navigate`, and not for `"back"`, `"forward"`, or `"reload"`. Claude can leave out the scheme, as in `example.com`, so before it reads the host, the example adds `https://` to a URL that doesn't start with a scheme. Your `navigate` gets the URL as Claude wrote it. Add the scheme there with the same test, so that the browser opens the URL your policy checked.
665The SDK calls the policy only for `navigate`, and not for `"back"`, `"forward"`, or `"reload"`. Claude can leave out the scheme, as in `example.com`, so before it reads the host, the example adds `https://` to a URL that doesn’t start with a scheme. Your `navigate` gets the URL as Claude wrote it. Add the scheme there with the same test, so that the browser opens the URL your policy checked.
666666
667The example isn't production grade. A production policy needs much more, in areas such as these:
667The example isn’t production grade. A production policy needs much more, in areas such as these:
668668
669669* Links Claude clicks, forms it submits, redirects, and the requests a page makes on its own. Only your driver sees them. See [Intercept requests in the driver](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#intercept-requests-in-the-driver).
670670* Hostnames and URLs that come from page content, which an attacker can choose.
671671* Parsing each URL the way the browser does, not finding the hostname with a plain string split.
672* URL schemes. The SDK doesn't check them, so refuse every scheme that you don't intend your driver to open.
672* URL schemes. The SDK doesn’t check them, so refuse every scheme that you don’t intend your driver to open.
673673* Egress rules on the container, for what no URL check can see. See [Put egress policy on the container](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#put-egress-policy-on-the-container).
674674
675If you pass `url_policy=None` (typescript: `urlPolicy: null`), the SDK refuses every `navigate` to a URL, so a `None` (typescript: `null`) read from your configuration can't leave URLs unchecked by accident. In TypeScript, `undefined` leaves the option unset, the same as not passing it.
675If you pass `url_policy=None` (typescript: `urlPolicy: null`), the SDK refuses every `navigate` to a URL, so a `None` (typescript: `null`) read from your configuration can’t leave URLs unchecked by accident. In TypeScript, `undefined` leaves the option unset, the same as not passing it.
676676
677677### Intercept requests in the driver
678678
from line 702
702702 ```
703703</CodeGroup>
704704
705A request hook like this one doesn't see WebSocket handshakes, service-worker requests, or redirect hops. Block service workers. Check WebSocket handshakes and redirect hops with a hook that sees them. The example policy refuses `ws://` and `wss://` URLs, so change `ws://` to `http://` and `wss://` to `https://` before you pass a WebSocket URL to `is_allowed()` (typescript: `isAllowed()`).
705A request hook like this one doesn’t see WebSocket handshakes, service-worker requests, or redirect hops. Block service workers. Check WebSocket handshakes and redirect hops with a hook that sees them. The example policy refuses `ws://` and `wss://` URLs, so change `ws://` to `http://` and `wss://` to `https://` before you pass a WebSocket URL to `is_allowed()` (typescript: `isAllowed()`).
706706
707707### Put egress policy on the container
708708
709Interception can't see every request the browser makes, and the URL policy doesn't see where a name resolves. An egress policy that the container's network enforces covers both:
709Interception can’t see every request the browser makes, and the URL policy doesn’t see where a name resolves. An egress policy that the container’s network enforces covers both:
710710
711711* Block link-local and private address ranges in IPv4 and IPv6. That includes the cloud metadata address `169.254.169.254`.
712712* Allow outbound connections only to the hosts the task needs. If your rules match IP addresses, resolve the hostnames you allow when the container starts.
713* Allow DNS only to the container's resolver.
713* Allow DNS only to the container’s resolver.
714714
715Rules enforced outside the browser's container, such as a Kubernetes NetworkPolicy or a cloud firewall, don't see loopback inside it. With only those rules, a page can reach anything listening there, including a DevTools port, which shows a list of the browser's open tabs and the address that controls each one.
715Rules enforced outside the browser’s container, such as a Kubernetes NetworkPolicy or a cloud firewall, don’t see loopback inside it. With only those rules, a page can reach anything listening there, including a DevTools port, which shows a list of the browser’s open tabs and the address that controls each one.
716716
717717### Confine uploads and downloads
718718
719`file_upload` is off by default. With no `file_policy` (typescript: `filePolicy`), the SDK refuses every upload that gives a path or a [document ID](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-tool#upload-files). To enable uploads, pass a `BetaLocalFilePolicy` (typescript: `BetaNodeFilePolicy`) with one upload directory that holds only the task's files:
719`file_upload` is off by default. With no `file_policy` (typescript: `filePolicy`), the SDK refuses every upload that gives a path or a [document ID](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-tool#upload-files). To enable uploads, pass a `BetaLocalFilePolicy` (typescript: `BetaNodeFilePolicy`) with one upload directory that holds only the task’s files:
720720
721721<CodeGroup exclude="shell:cURL, shell:CLI, csharp, go, java, php, ruby">
722722 ```python Python
from line 753
753753 ```
754754</CodeGroup>
755755
756The SDK resolves each upload path, following symlinks, and refuses any path outside the upload roots. The file policy raises a configuration error for a download directory that is an upload root, is inside one, or contains one. That check can miss a symlink, so don't let one make the download directory the same as an upload root, or put one inside the other. The SDK includes a download's `path` in the state report only when `expose_download_paths` (typescript: `exposeDownloadPaths`) is true and the file is inside the download directory.
756The SDK resolves each upload path, following symlinks, and refuses any path outside the upload roots. The file policy raises a configuration error for a download directory that is an upload root, is inside one, or contains one. That check can miss a symlink, so don’t let one make the download directory the same as an upload root, or put one inside the other. The SDK includes a download’s `path` in the state report only when `expose_download_paths` (typescript: `exposeDownloadPaths`) is true and the file is inside the download directory.
757757
758758The shipped file policy checks paths on the filesystem of the process that runs the SDK. It protects only a browser that shares that filesystem. For a remote browser, follow [Remote and hosted browsers](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#remote-and-hosted-browsers) instead.
759759
from line 761
761761
762762* Create the download directory yourself with mode `0700`, and mount it `noexec,nosuid,nodev`.
763763* Keep the directory out of reach of other tools that Claude can call, such as a shell or a file tool.
764* In a `download_failed` state change, write `error` as a fixed phrase. An exception's text can contain the path or the URL.
765* Don't read a downloaded file into the conversation, or run it, until a person decides to.
764* In a `download_failed` state change, write `error` as a fixed phrase. An exception’s text can contain the path or the URL.
765* Don’t read a downloaded file into the conversation, or run it, until a person decides to.
766766
767767### Gate consequential members
768768
769`javascript_exec` and `file_upload` are off by default. If you enable either one without a `confirm` callable, the constructor raises a configuration error. With a `confirm` callable, the SDK calls it before every call that's about to run. Without one, nothing is asked. In TypeScript, `confirm: null` doesn't raise the configuration error, and the SDK refuses every call to any member.
769`javascript_exec` and `file_upload` are off by default. If you enable either one without a `confirm` callable, the constructor raises a configuration error. With a `confirm` callable, the SDK calls it before every call that’s about to run. Without one, nothing is asked. In TypeScript, `confirm: null` doesn’t raise the configuration error, and the SDK refuses every call to any member.
770770
771Return `True` (typescript: `true`) to run the call, or `False` (typescript: `false`) to refuse it. When your callable asks a person, show them the member, the page's URL, and the call's input. First, escape every character outside printable ASCII in the URL and the input, because both can carry text from the page.
771Return `True` (typescript: `true`) to run the call, or `False` (typescript: `false`) to refuse it. When your callable asks a person, show them the member, the page’s URL, and the call’s input. First, escape every character outside printable ASCII in the URL and the input, because both can carry text from the page.
772772
773773This example asks about the two gated members through your own `ask_user()` (typescript: `askUser()`) function, and approves the rest:
774774
from line 868
868868
869869Each call to `make_confirm()` (typescript: `makeConfirm()`) returns a callable with no approvals. Call it once for each toolset, and give each user their own toolset.
870870
871An approval covers the page as the last state report showed it, and the page can change before the call runs. Purchases, sent messages, and accepted terms go through ordinary members such as `left_click` and `type`, so `confirm` can't pick them out by name. To have a person approve them, ask about those members too.
871An approval covers the page as the last state report showed it, and the page can change before the call runs. Purchases, sent messages, and accepted terms go through ordinary members such as `left_click` and `type`, so `confirm` can’t pick them out by name. To have a person approve them, ask about those members too.
872872
873Don't enable `javascript_exec` unless [egress rules](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#put-egress-policy-on-the-container) limit the browser's outbound connections to the hosts the task needs. A script can send the page's content to any address that the browser can reach.
873Don’t enable `javascript_exec` unless [egress rules](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#put-egress-policy-on-the-container) limit the browser’s outbound connections to the hosts the task needs. A script can send the page’s content to any address that the browser can reach.
874874
875A `javascript:` URL in a `navigate` call also runs script in the current page, even when `javascript_exec` is off. `confirm` sees that call as a `navigate`, so the example's `confirm` callable would approve it. Your driver must refuse `javascript:` URLs. In the example, the [URL policy](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#write-a-url-policy) refuses them before `confirm` runs.
875A `javascript:` URL in a `navigate` call also runs script in the current page, even when `javascript_exec` is off. `confirm` sees that call as a `navigate`, so the example’s `confirm` callable would approve it. Your driver must refuse `javascript:` URLs. In the example, the [URL policy](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#write-a-url-policy) refuses them before `confirm` runs.
876876
877877### Isolate the browser host
878878
from line 884
884884* Share no filesystem with other tools Claude can call.
885885
886886<Warning>
887 The browser profile must not be signed in to any account whose data or actions you wouldn't hand to Claude. `javascript_exec` runs with the page's own authority: its cookies, its storage, and its signed-in sessions.
887 The browser profile must not be signed in to any account whose data or actions you wouldn’t hand to Claude. `javascript_exec` runs with the page’s own authority: its cookies, its storage, and its signed-in sessions.
888888</Warning>
889889
890Run the code that calls the API outside the browser's container, because that code holds your API key and the conversation. The tool runner and `tool_result` (typescript: `toolResult`) both run the toolset in that code's process, so the browser doesn't share the toolset's filesystem. Treat the browser as remote: [Remote and hosted browsers](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#remote-and-hosted-browsers) applies.
890Run the code that calls the API outside the browser’s container, because that code holds your API key and the conversation. The tool runner and `tool_result` (typescript: `toolResult`) both run the toolset in that code’s process, so the browser doesn’t share the toolset’s filesystem. Treat the browser as remote: [Remote and hosted browsers](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#remote-and-hosted-browsers) applies.
891891
892892Treat everything a page returns as untrusted, including page text, screenshots, console and network entries, tab titles, and download names.
893893
894894### Remote and hosted browsers
895895
896Some browsers don't share a filesystem with the process that runs the SDK. Examples are a browser in another container, one you reach at a DevTools URL, and one from a hosted browser service. With these, the URL policy, request interception, and `confirm` still run in your process.
896Some browsers don’t share a filesystem with the process that runs the SDK. Examples are a browser in another container, one you reach at a DevTools URL, and one from a hosted browser service. With these, the URL policy, request interception, and `confirm` still run in your process.
897897
898With a hosted browser, the provider controls egress and host isolation. Your own egress policy doesn't apply there, so the driver's request hook is your only check on the browser's requests. Find out what the browser's network can reach.
898With a hosted browser, the provider controls egress and host isolation. Your own egress policy doesn’t apply there, so the driver’s request hook is your only check on the browser’s requests. Find out what the browser’s network can reach.
899899
900The shipped path checks don't protect a remote browser. `BetaLocalFilePolicy` (typescript: `BetaNodeFilePolicy`) checks paths on the filesystem of the process that runs the SDK, and the browser reads and writes its own filesystem.
900The shipped path checks don’t protect a remote browser. `BetaLocalFilePolicy` (typescript: `BetaNodeFilePolicy`) checks paths on the filesystem of the process that runs the SDK, and the browser reads and writes its own filesystem.
901901
902The SDK can't detect that a browser is remote. So for a remote browser, keep `file_upload` off unless your driver checks upload paths where the browser runs, with a `BetaFilePolicy` of its own. A `BetaFilePolicy` vets each upload's paths and document IDs, and determines whether Claude sees a download's path.
902The SDK can’t detect that a browser is remote. So for a remote browser, keep `file_upload` off unless your driver checks upload paths where the browser runs, with a `BetaFilePolicy` of its own. A `BetaFilePolicy` vets each upload’s paths and document IDs, and determines whether Claude sees a download’s path.
903903
904904Have a remote browser refuse downloads, unless its own host has the download setup from [Confine uploads and downloads](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#confine-uploads-and-downloads).
905905
906Keep the provider's API key and the session's connection URL, which can contain a key, out of logs, tool results, and error text. If the provider records sessions, the recording is another copy of everything Claude saw and typed, and the provider's retention terms apply to it.
906Keep the provider’s API key and the session’s connection URL, which can contain a key, out of logs, tool results, and error text. If the provider records sessions, the recording is another copy of everything Claude saw and typed, and the provider’s retention terms apply to it.
907907
908908## Computer toolset
909909
910`BetaAbstractComputerToolset20260801` is the class for the [computer use tool](https://platform.claude.com/docs/en/agents-and-tools/tool-use/computer-use-tool). A driver is a subclass with one method for each tool, such as `screenshot` or `left_click`. Start from a partner's driver under [Partner integrations](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#partner-integrations). To write your own, the claude-quickstarts repository has a [minimal VNC example](https://github.com/anthropics/claude-quickstarts/tree/main/computer-toolset) in Python and TypeScript. It controls a desktop over VNC, and it isn't production code.
910`BetaAbstractComputerToolset20260801` is the class for the [computer use tool](https://platform.claude.com/docs/en/agents-and-tools/tool-use/computer-use-tool). A driver is a subclass with one method for each tool, such as `screenshot` or `left_click`. Start from a partner’s driver under [Partner integrations](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#partner-integrations). To write your own, the claude-quickstarts repository has a [minimal VNC example](https://github.com/anthropics/claude-quickstarts/tree/main/computer-toolset) in Python and TypeScript. It controls a desktop over VNC, and it isn’t production code.
911911
912912The class takes `configs`, `confirm`, and `tool_configs` (typescript: `toolConfigs`), and you pass them as you do for the browser class. [Customize a driver](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#customize-a-driver), [Handle errors](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#handle-errors), [Start calls while the response streams](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#start-calls-while-the-response-streams), and [Run without the tool runner](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#run-without-the-tool-runner) apply to it too, with these differences:
913913
from line 914
914914* **Browser-only options:** The class has no [URL policy](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#write-a-url-policy), no [file policy](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#confine-uploads-and-downloads), and no [state report](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#report-browser-state).
915915* **`configs`:** Every tool you implement is on by default. The per-tool settings are listed under [Tool parameters](https://platform.claude.com/docs/en/agents-and-tools/tool-use/computer-use-tool#tool-parameters).
916916* **`confirm`:** If your class implements `type`, `key`, or `hold_key`, the constructor raises a configuration error unless you pass a `confirm` callable or turn those tools off with `configs`. A class that overrides `execute` counts as implementing all three.
917* **Skipped calls:** After a failed computer call, the tool runner answers the turn's later computer calls with `Not executed: an earlier computer action in this turn failed.` Browser calls get a different text. In a loop you write, answer the skipped computer calls with that exact text ([Batch actions in the computer use tool](https://platform.claude.com/docs/en/agents-and-tools/tool-use/computer-use-tool#batch-actions)).
917* **Skipped calls:** After a failed computer call, the tool runner answers the turn’s later computer calls with `Not executed: an earlier computer action in this turn failed.` Browser calls get a different text. In a loop you write, answer the skipped computer calls with that exact text ([Batch actions in the computer use tool](https://platform.claude.com/docs/en/agents-and-tools/tool-use/computer-use-tool#batch-actions)).
918918* **`execute`:** In TypeScript, an `execute` override types `name` as `BetaComputerMemberName` and `input` as `BetaComputerMemberInput`. Both come from `@anthropic-ai/sdk/resources/beta`.
919* **Error text:** The SDK doesn't hide local paths in a computer tool's error text or in the text a tool returns. Claude reads both, cut at 4,096 characters. Catch exceptions in your tools, and raise `ToolError` (throw it in TypeScript) with your own text.
919* **Error text:** The SDK doesn’t hide local paths in a computer tool’s error text or in the text a tool returns. Claude reads both, cut at 4,096 characters. Catch exceptions in your tools, and raise `ToolError` (throw it in TypeScript) with your own text.
920920
921921### Write a desktop driver
922922
923This driver implements five of the 17 tools listed under [Available actions](https://platform.claude.com/docs/en/agents-and-tools/tool-use/computer-use-tool#available-actions). A tool you don't implement is sent to the API as disabled, as [Implement a driver](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#implement-a-driver) explains. In the example, `display` stands for your own wrapper around whatever controls the desktop, such as a VNC client or `xdotool`, and `ask_user()` (typescript: `askUser()`) stands for your own function that asks a person.
923This driver implements five of the 17 tools listed under [Available actions](https://platform.claude.com/docs/en/agents-and-tools/tool-use/computer-use-tool#available-actions). A tool you don’t implement is sent to the API as disabled, as [Implement a driver](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#implement-a-driver) explains. In the example, `display` stands for your own wrapper around whatever controls the desktop, such as a VNC client or `xdotool`, and `ask_user()` (typescript: `askUser()`) stands for your own function that asks a person.
924924
925925<CodeGroup exclude="shell:cURL, shell:CLI, csharp, go, java, php, ruby">
926926 ```python Python
from line 1100
11001100
11011101Every point Claude sends is a pixel position in the screenshots you return: each `coordinate` and `start_coordinate`, and both corners of a `zoom` `region`. The SDK passes them to your tools unchanged.
11021102
1103If your screenshots are a different size from the display, convert in both directions in your driver: Claude's points to display pixels, and the cursor position you report to screenshot pixels. Keep the screenshot size the same for the whole session, and give it the display's aspect ratio:
1103If your screenshots are a different size from the display, convert in both directions in your driver: Claude’s points to display pixels, and the cursor position you report to screenshot pixels. Keep the screenshot size the same for the whole session, and give it the display’s aspect ratio:
11041104
11051105<CodeGroup exclude="shell:cURL, shell:CLI, csharp, go, java, php, ruby">
11061106 ```python Python
from line 1157
11571157 ```
11581158</CodeGroup>
11591159
1160Call `to_display()` (typescript: `toDisplay()`) on each `coordinate` and `start_coordinate` before you act on it, and `to_screenshot()` (typescript: `toScreenshot()`) on the position that `cursor_position` reports. A click or scroll with no `coordinate` acts at the cursor, so it has nothing to convert. Scale a `zoom` `region` by the same factor. A `zoom` image doesn't change this: the next points Claude sends are still pixel positions in the full screenshot.
1160Call `to_display()` (typescript: `toDisplay()`) on each `coordinate` and `start_coordinate` before you act on it, and `to_screenshot()` (typescript: `toScreenshot()`) on the position that `cursor_position` reports. A click or scroll with no `coordinate` acts at the cursor, so it has nothing to convert. Scale a `zoom` `region` by the same factor. A `zoom` image doesn’t change this: the next points Claude sends are still pixel positions in the full screenshot.
11611161
1162The SDK never reads or resizes an image. The API rejects an image over the model's limits, which ends the run. Scale each screenshot and `zoom` image in the driver. See [Size screenshots to fit image limits](https://platform.claude.com/docs/en/agents-and-tools/tool-use/computer-use-tool#handle-coordinate-scaling-for-higher-resolutions). On a long run, one request can hold more than 20 images, and the API then holds each one to a stricter limit. See [Manage screenshot history](https://platform.claude.com/docs/en/agents-and-tools/tool-use/computer-use-tool#manage-screenshot-history).
1162The SDK never reads or resizes an image. The API rejects an image over the model’s limits, which ends the run. Scale each screenshot and `zoom` image in the driver. See [Size screenshots to fit image limits](https://platform.claude.com/docs/en/agents-and-tools/tool-use/computer-use-tool#handle-coordinate-scaling-for-higher-resolutions). On a long run, one request can hold more than 20 images, and the API then holds each one to a stricter limit. See [Manage screenshot history](https://platform.claude.com/docs/en/agents-and-tools/tool-use/computer-use-tool#manage-screenshot-history).
11631163
11641164### Input checks and results
11651165
1166Don't rely on the SDK to check a call's input. Have your driver check the fields it uses and refuse a call it can't run: raise `ToolError` (throw it in TypeScript). Claude reads the message and can send a corrected call.
1166Don’t rely on the SDK to check a call’s input. Have your driver check the fields it uses and refuse a call it can’t run: raise `ToolError` (throw it in TypeScript). Claude reads the message and can send a corrected call.
11671167
1168The SDK doesn't limit a `duration`, a `repeat` count, or a `scroll_amount`. Step 4 under [Run the computer toolset safely](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#run-the-computer-toolset-safely) covers them.
1168The SDK doesn’t limit a `duration`, a `repeat` count, or a `scroll_amount`. Step 4 under [Run the computer toolset safely](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#run-the-computer-toolset-safely) covers them.
11691169
11701170What a tool returns determines what Claude reads:
11711171
from line 1177
11771177
11781178### Run the computer toolset safely
11791179
1180What's on the screen steers Claude's next action. A page or a notification can attempt to make Claude type into the wrong window, or trigger an action with real effects.
1180What’s on the screen steers Claude’s next action. A page or a notification can attempt to make Claude type into the wrong window, or trigger an action with real effects.
11811181
11821182<Warning>
11831183 A driver that implements `type`, `key`, or `hold_key` needs a `confirm` callable. Without one, the constructor raises a configuration error, unless `configs` turns those tools off. The SDK itself asks no one: it runs every call that your `confirm` approves, and with no `confirm` it runs every call, including every click. Every computer tool you implement is on by default.
from line 1188
118811881. Isolate the desktop. Run it in a dedicated, minimal-privilege container or VM for each session, with no credentials and no host mounts. Install only the applications the task needs. Run the code that calls the API outside it.
118911892. Gate actions that have real effects with `confirm`. A purchase or a sent message is an ordinary `left_click`, `type`, or `key`, and `confirm` receives the tool and its input, not the screen. So choose which tools need approval based on the applications Claude can reach on the desktop.
119011903. Keep terminals, run dialogs, and launchers off the desktop unless the task needs one. When one has keyboard focus, `type`, `key`, and `hold_key` run whatever Claude types, and a click can start a program. If the task needs one, ask a person before keyboard input and clicks, and isolate the desktop so that a command can reach no further than the task needs.
11914. Refuse input your desktop shouldn't honor, such as a point outside the screenshot, a `wait` of several minutes, or a very large `repeat` or `scroll_amount`. Raise `ToolError` (throw it in TypeScript) instead of moving the value into range.
11925. Treat everything on the screen as untrusted, including window titles and clipboard text. Don't run it or pass it on unchecked.
11914. Refuse input your desktop shouldn’t honor, such as a point outside the screenshot, a `wait` of several minutes, or a very large `repeat` or `scroll_amount`. Raise `ToolError` (throw it in TypeScript) instead of moving the value into range.
11925. Treat everything on the screen as untrusted, including window titles and clipboard text. Don’t run it or pass it on unchecked.
11931193
11941194The SDK applies step 2 through the callable you pass. The other steps are up to your driver and your deployment. The precautions under [Security considerations for the computer use tool](https://platform.claude.com/docs/en/agents-and-tools/tool-use/computer-use-tool#security-considerations) apply as well.
11951195
1196The following `confirm` asks a person before any keyboard input, through your own `ask_user()` (typescript: `askUser()`) function, and approves every other call. `context.member` (typescript: `ctx.member`) is the tool's name. To have a person approve clicks too, set `ASK_FIRST` to `KEYBOARD | CLICKS` (typescript: `new Set([...KEYBOARD, ...CLICKS])`).
1196The following `confirm` asks a person before any keyboard input, through your own `ask_user()` (typescript: `askUser()`) function, and approves every other call. `context.member` (typescript: `ctx.member`) is the tool’s name. To have a person approve clicks too, set `ASK_FIRST` to `KEYBOARD | CLICKS` (typescript: `new Set([...KEYBOARD, ...CLICKS])`).
11971197
11981198<CodeGroup exclude="shell:cURL, shell:CLI, csharp, go, java, php, ruby">
11991199 ```python Python
from line 1254
12541254
12551255A refused call gets an error result, and the run continues. For a refused `type` call, Claude reads `The user did not grant permission to run 'type'. Do not retry it unless the user asks you to.`
12561256
1257This `confirm` approves every tool that isn't in `ASK_FIRST`, including any tool you add later. To fail closed, approve only the tools with no effect on the desktop (`screenshot`, `zoom`, `cursor_position`, and `wait`) and ask about every other tool.
1257This `confirm` approves every tool that isn’t in `ASK_FIRST`, including any tool you add later. To fail closed, approve only the tools with no effect on the desktop (`screenshot`, `zoom`, `cursor_position`, and `wait`) and ask about every other tool.
12581258
12591259### Use both toolsets in one request
12601260
1261Pass both instances in `tools`. Each call carries its `toolset_name`, `browser` or `computer`, and the tool runner sends the call to the matching instance. After a failed call, the tool runner skips only the turn's later calls to the same toolset, so a failed computer call doesn't skip the turn's browser calls.
1261Pass both instances in `tools`. Each call carries its `toolset_name`, `browser` or `computer`, and the tool runner sends the call to the matching instance. After a failed call, the tool runner skips only the turn’s later calls to the same toolset, so a failed computer call doesn’t skip the turn’s browser calls.
12621262
12631263<CodeGroup exclude="shell:cURL, shell:CLI, csharp, go, java, php, ruby">
12641264 ```python Python
from line 1310
13101310 ```
13111311</CodeGroup>
13121312
1313In a loop you write, answer each call with `tool_result` (typescript: `toolResult`) on the instance whose `toolset_name` (typescript: `toolsetName`) matches the call's `toolset_name`. In each turn, track failed calls for each toolset separately, and answer a skipped call with that toolset's own text. [Run without the tool runner](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#run-without-the-tool-runner) has the browser's text, and the Skipped calls bullet at the top of this section has the computer's.
1313In a loop you write, answer each call with `tool_result` (typescript: `toolResult`) on the instance whose `toolset_name` (typescript: `toolsetName`) matches the call’s `toolset_name`. In each turn, track failed calls for each toolset separately, and answer a skipped call with that toolset’s own text. [Run without the tool runner](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#run-without-the-tool-runner) has the browser’s text, and the Skipped calls bullet at the top of this section has the computer’s.
13141314
13151315## Reference
13161316
from line 1327
13271327
13281328The browser class takes every option in the table. The computer class takes `configs`, `confirm`, and `tool_configs` (typescript: `toolConfigs`).
13291329
1330You can't change an option after construction. The [Python browser toolset guide](https://github.com/anthropics/anthropic-sdk-python/blob/main/browser-toolset.md), the [TypeScript browser toolset guide](https://github.com/anthropics/anthropic-sdk-typescript/blob/main/browser-toolset.md), the [Python computer toolset guide](https://github.com/anthropics/anthropic-sdk-python/blob/main/computer-toolset.md), and the [TypeScript computer toolset guide](https://github.com/anthropics/anthropic-sdk-typescript/blob/main/computer-toolset.md) describe each option. The Python guides also cover the async classes, `BetaAsyncAbstractBrowserToolset20260801` and `BetaAsyncAbstractComputerToolset20260801`.
1330You can’t change an option after construction. The [Python browser toolset guide](https://github.com/anthropics/anthropic-sdk-python/blob/main/browser-toolset.md), the [TypeScript browser toolset guide](https://github.com/anthropics/anthropic-sdk-typescript/blob/main/browser-toolset.md), the [Python computer toolset guide](https://github.com/anthropics/anthropic-sdk-python/blob/main/computer-toolset.md), and the [TypeScript computer toolset guide](https://github.com/anthropics/anthropic-sdk-typescript/blob/main/computer-toolset.md) describe each option. The Python guides also cover the async classes, `BetaAsyncAbstractBrowserToolset20260801` and `BetaAsyncAbstractComputerToolset20260801`.
13311331
13321332## Limitations
13331333
1334* **The SDK doesn't include a browser, a desktop, a ready-made driver, or a URL policy:** You supply them. See [Partner integrations](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#partner-integrations), [Implement a driver](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#implement-a-driver), and [Write a URL policy](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#write-a-url-policy).
1335* **The URL policy sees only `navigate` calls:** It doesn't see the requests a page makes, or pages that open any other way, such as from a link Claude clicks or a redirect. See [Intercept requests in the driver](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#intercept-requests-in-the-driver).
1336* **An approval is based on the last state report:** The page can change after that report. The SDK doesn't check the page again before the call runs.
1337* **Calls on one toolset run one at a time:** You can't turn this off.
1338* **The SDK doesn't check that tab IDs are unique or how many tabs there are, and doesn't always check that one tab is active:** The API rejects a report that breaks those rules.
1339* **For a computer call, `confirm` receives the tool and its input, not the screen:** You can't tell from them what a click at a given point does.
1340* **The SDK doesn't resize a computer toolset's images:** The API rejects an image over the model's limits. See [Scale coordinates and size images](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#scale-coordinates-and-size-images).
1334* **The SDK doesn’t include a browser, a desktop, a ready-made driver, or a URL policy:** You supply them. See [Partner integrations](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#partner-integrations), [Implement a driver](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#implement-a-driver), and [Write a URL policy](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#write-a-url-policy).
1335* **The URL policy sees only `navigate` calls:** It doesn’t see the requests a page makes, or pages that open any other way, such as from a link Claude clicks or a redirect. See [Intercept requests in the driver](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#intercept-requests-in-the-driver).
1336* **An approval is based on the last state report:** The page can change after that report. The SDK doesn’t check the page again before the call runs.
1337* **Calls on one toolset run one at a time:** You can’t turn this off.
1338* **The SDK doesn’t check that tab IDs are unique or how many tabs there are, and doesn’t always check that one tab is active:** The API rejects a report that breaks those rules.
1339* **For a computer call, `confirm` receives the tool and its input, not the screen:** You can’t tell from them what a click at a given point does.
1340* **The SDK doesn’t resize a computer toolset’s images:** The API rejects an image over the model’s limits. See [Scale coordinates and size images](https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-sdk#scale-coordinates-and-size-images).
13411341
13421342## Next steps
13431343
13441344<CardGroup cols={2}>
13451345 <Card title="Browser use tool" icon="browser" href="https://platform.claude.com/docs/en/agents-and-tools/tool-use/browser-use-tool">
1346 The member tools, the `browser_state` block, and the tool's security considerations.
1346 The member tools, the `browser_state` block, and the tool’s security considerations.
13471347 </Card>
13481348
13491349 <Card title="Computer use tool" icon="computer" href="https://platform.claude.com/docs/en/agents-and-tools/tool-use/computer-use-tool">
1350 The 17 tools, coordinates and image limits, and the tool's security considerations.
1350 The 17 tools, coordinates and image limits, and the tool’s security considerations.
13511351 </Card>
13521352
13531353 <Card title="Tool runner (SDK)" icon="arrows-clockwise" href="https://platform.claude.com/docs/en/agents-and-tools/tool-use/tool-runner">
No line in this hunk matches that.