Burrowbox Blog
← All posts

Let an AI agent browse from another country, and check where it really is

· The Burrowbox team · 7 min read

#How to make an AI agent browse from another country

Give the agent's machine a VPN location: {"vpn": {"type": "proxy", "country": "de"}}. The machine's browser and apps then go online from an IP in that country, and the machine keeps the same exit IP for as long as the network allows. Before the agent trusts a price or a page, check the exit with GET /api/machines/{id}/vpn, or from the agent's side with the network_info tool. To compare markets, change the country on the running machine with PUT /api/machines/{id}/vpn. It takes effect at once, with no restart (VPN locations).

That covers the usual reasons to send an agent abroad: checking localized prices, seeing which products or articles a region gets, and testing your own site the way customers in each market see it.

#What the country changes, and what it doesn't

Google's guidance on locale-adaptive pages describes sites that return different content based on the visitor's perceived country or preferred language. Those are two different signals: the country usually comes from the IP address, the language from the Accept-Language header. A VPN location changes the IP. The language is a separate setting: browsers set Accept-Language from their own interface language, and it usually lists the same locales as navigator.languages (MDN). So a store can show German prices and still show the page in English.

On Burrowbox, all of the machine's traffic goes through the location: the built-in browser, curl, apt, pip, and any app that honors the system proxy settings. Apps that ignore the system proxy, which is rare, connect directly.

The browser is persistent, so cookies survive restarts and country switches. If a site saved a region choice in a cookie on an earlier run, it may keep that choice after you switch. Ask the agent to report the currency and region the page shows along with the number.

#Step 1: Pick a location

GET /api/vpn/locations needs no authentication. It lists the two types, a set of common countries and the current prices.

curl https://burrowbox.dev/api/vpn/locations

Any two-letter country code works, not only the listed ones. A city (lowercase, no spaces, like newyork) is optional and best effort. It only works on networks where types[].cityTargeting is true. Elsewhere the API rejects it with 400.

#Step 2: Give the machine a location

Set it when you create the machine:

curl -X POST https://burrowbox.dev/api/machines \
  -H "Authorization: Bearer $BURROWBOX_KEY" -H "Content-Type: application/json" \
  -d '{"name": "price-check", "vpn": {"type": "proxy", "country": "de"}}'

Or on an existing machine:

curl -X PUT https://burrowbox.dev/api/machines/$MACHINE_ID/vpn \
  -H "Authorization: Bearer $BURROWBOX_KEY" -H "Content-Type: application/json" \
  -d '{"vpn": {"type": "proxy", "country": "de"}}'

type defaults to proxy, and {"vpn": null} turns the location off. Claiming a machine from a warm pool takes the same vpn field. Burrowbox runs the network, so there's no proxy account or credential on your side. Machines created before the VPN launched have to be recreated to use it.

#Step 3: Check the exit before the agent reads a price

Ask the API where the machine is actually browsing from:

curl https://burrowbox.dev/api/machines/$MACHINE_ID/vpn \
  -H "Authorization: Bearer $BURROWBOX_KEY"
{ "vpn": { "type": "proxy", "country": "de" }, "egress": { "ok": true, "ip": "91.108.196.68", "country": "DE", "city": "Berlin", "org": "AS209372 WS Telecom Inc" } }

vpn is what you asked for, and egress is what sites see, so a mismatch between the two means the page shouldn't be trusted yet.

The agent can run the same check itself. Connect it over MCP to the machine's endpoint (POST /api/machines/{id}/mcp) with the machine's mcpToken and give it the network_info tool, which returns the public IP, country and network, and whether a VPN location is set (machine MCP tools). A line in the system prompt is enough:

"Before reporting a price, call network_info and include the country it returns. Read navigator.languages with browser_evaluate and report it too. Report the currency the page displays."

With the location and the language in every report, whoever reads the results can tell which signal a site responded to.

#Step 4: Switch countries while it runs

Partial changes keep the other fields, so {"vpn": {"country": "fr"}} changes only the country. The change applies live on a running machine, and the response includes "applied": true once it has taken effect. This Node script walks through four markets, checks each exit before it trusts the page, and hands each market to your agent:

// compare.mjs (Node 18+). runAgent is your agent, connected to the machine's MCP endpoint.
import { runAgent } from "./agent.mjs";

const BB = "https://burrowbox.dev";
const id = process.env.MACHINE_ID;
const headers = { Authorization: `Bearer ${process.env.BURROWBOX_KEY}`, "Content-Type": "application/json" };

for (const country of ["de", "fr", "gb", "us"]) {
  const set = await fetch(`${BB}/api/machines/${id}/vpn`, {
    method: "PUT", headers, body: JSON.stringify({ vpn: { country } }),
  }).then((r) => r.json());
  if (!set.applied) { console.log(country, "not applied; is the machine running?"); continue; }

  const { egress } = await fetch(`${BB}/api/machines/${id}/vpn`, { headers }).then((r) => r.json());
  if (!egress?.ok || egress.country.toLowerCase() !== country) {
    console.log(country, "exit doesn't match, skipping", egress);
    continue;
  }

  const answer = await runAgent(
    `Open https://shop.example.com/product/123 and report the price, currency and stock status. ` +
    `Use browser_snapshot to read the page. You are browsing from ${egress.country}.`
  );
  console.log(country, egress.ip, answer);
}

The machine doesn't restart between countries, so the agent keeps its tabs and any login it already has. The network session is pinned per machine, so the exit IP stays the same for as long as the network allows. That matters for sites that tie a session to an IP. If you need several countries at the same moment rather than one after another, use one machine per country.

To run the comparison every morning without your own scheduler, see the Comet post, which wakes a signed-in browser on a schedule.

Changing the country is a platform action. Your server does it with the API key, or an agent you trust with the platform MCP calls machine_set_vpn. The agent working on the machine only reads its location, with network_info.

#Which VPN type to use

There are two types. proxy browses from a real IP in the country, and HTTPS passes through untouched, end to end between the machine and the site. unlock works differently: the provider (Bright Data) opens HTTPS traffic and re-encrypts it with its own certificate, which the machine trusts while unlock is on. The provider can read the machine's web traffic, including pages the agent is signed in to. Switching to or from unlock also restarts the browser once (tabs reopen). For checking prices and content, proxy is enough, and HTTPS stays end to end.

#What it costs

The VPN is an add-on to the machine's normal rate (Billing). With proxy, it's +$0.03 an hour while the machine runs with the location on, plus $10 per GB of traffic. A small machine costs $0.11 an hour while running. Live prices are in GET /api/vpn/locations under types[].pricing. Stop the machine between runs and it costs $0.001 an hour, with its browser state kept (Machines).

If you're still choosing where agents should run, the cloud browser vs sandbox vs cloud computer guide compares the options, and the AgentCore Browser post shows a pinned country on a machine driven by Strands Agents.

#FAQ

#Can the agent change its own country?

Not with its machine token. The machine MCP has network_info, which reads the location. Setting it is done by your server with PUT /api/machines/{id}/vpn, or through the platform MCP tool machine_set_vpn, which uses your API key.

#Does changing the country restart the machine?

No. A country or type change on a running machine takes effect at once. The only restart is the browser's, once, when you switch to or from unlock.

#Will the site show the local language?

Not necessarily. The VPN location changes the IP address. The language comes from the browser's Accept-Language header, which follows the browser's own language. Have the agent check navigator.languages with browser_evaluate and report what it found.

#Can I pick a city?

Sometimes. city is best effort and only works where types[].cityTargeting is true in GET /api/vpn/locations. Elsewhere the API returns 400. Changing the country clears the city.

#Key takeaways

  • Set {"vpn": {"type": "proxy", "country": "…"}} on the machine, at creation or later with PUT /api/machines/{id}/vpn.
  • Check egress.country (or the agent's network_info) before you trust a page.
  • Switch countries live with {"vpn": {"country": "fr"}}. There's no restart, and the IP stays stable per machine.
  • The IP is one locale signal. Accept-Language is another, and the VPN doesn't change it.
  • Use proxy for this. unlock lets the provider read HTTPS traffic.

Create an account to try it.

#Sources