Overview
Skyvern supports proxy and geolocation configuration to help you:- Access geo-restricted content
- Test from different locations
- Comply with regional requirements
- Avoid rate limiting and blocking
- Simulate users from specific regions
Proxy Locations
Skyvern provides residential proxies in multiple countries and regions:Available Proxy Locations
from skyvern.schemas.runs import ProxyLocation
class ProxyLocation(StrEnum):
# United States
RESIDENTIAL = "RESIDENTIAL" # US (general)
US_CA = "US-CA" # California
US_NY = "US-NY" # New York
US_TX = "US-TX" # Texas
US_FL = "US-FL" # Florida
US_WA = "US-WA" # Washington
# Europe
RESIDENTIAL_GB = "RESIDENTIAL_GB" # United Kingdom
RESIDENTIAL_DE = "RESIDENTIAL_DE" # Germany
RESIDENTIAL_FR = "RESIDENTIAL_FR" # France
RESIDENTIAL_ES = "RESIDENTIAL_ES" # Spain
RESIDENTIAL_IE = "RESIDENTIAL_IE" # Ireland
RESIDENTIAL_IT = "RESIDENTIAL_IT" # Italy
RESIDENTIAL_NL = "RESIDENTIAL_NL" # Netherlands
# Asia Pacific
RESIDENTIAL_JP = "RESIDENTIAL_JP" # Japan
RESIDENTIAL_IN = "RESIDENTIAL_IN" # India
RESIDENTIAL_AU = "RESIDENTIAL_AU" # Australia
RESIDENTIAL_NZ = "RESIDENTIAL_NZ" # New Zealand
RESIDENTIAL_KR = "RESIDENTIAL_KR" # South Korea
RESIDENTIAL_PH = "RESIDENTIAL_PH" # Philippines
# Americas (Other)
RESIDENTIAL_CA = "RESIDENTIAL_CA" # Canada
RESIDENTIAL_MX = "RESIDENTIAL_MX" # Mexico
RESIDENTIAL_BR = "RESIDENTIAL_BR" # Brazil
RESIDENTIAL_AR = "RESIDENTIAL_AR" # Argentina
# Other
RESIDENTIAL_TR = "RESIDENTIAL_TR" # Turkey
RESIDENTIAL_ZA = "RESIDENTIAL_ZA" # South Africa
RESIDENTIAL_ISP = "RESIDENTIAL_ISP" # ISP proxies
NONE = "NONE" # No proxy
Using Proxy Locations
In Task Runs
from skyvern import Skyvern
from skyvern.schemas.runs import ProxyLocation
skyvern = Skyvern(api_key="your-api-key")
# Run task from UK
task = await skyvern.run_task(
prompt="Check product availability",
url="https://shop.example.co.uk",
proxy_location=ProxyLocation.RESIDENTIAL_GB
)
# Run task from Japan
task = await skyvern.run_task(
prompt="Extract pricing information",
url="https://example.jp",
proxy_location=ProxyLocation.RESIDENTIAL_JP
)
In Workflow Runs
workflow_run = await skyvern.run_workflow(
workflow_id="wpid_price_comparison",
parameters={"product_id": "ABC123"},
proxy_location=ProxyLocation.RESIDENTIAL_DE # Germany proxy
)
Via API
curl -X POST https://api.skyvern.com/api/v1/tasks \
-H "x-api-key: your-api-key" \
-H "Content-Type: application/json" \
-d '{
"prompt": "Extract product information",
"url": "https://example.com",
"proxy_location": "RESIDENTIAL_FR"
}'
Granular Geolocation Targeting
For more precise targeting, use theGeoTarget object:
GeoTarget Structure
from skyvern.schemas.runs import GeoTarget
class GeoTarget(BaseModel):
country: str # ISO 3166-1 alpha-2 (e.g., "US", "GB")
subdivision: str | None # ISO 3166-2 (e.g., "CA" for California)
city: str | None # GeoNames English name
City-Level Targeting
# Target New York City specifically
task = await skyvern.run_task(
prompt="Check local store availability",
url="https://example.com/stores",
proxy_location=GeoTarget(
country="US",
subdivision="NY",
city="New York"
)
)
# Target London, UK
task = await skyvern.run_task(
prompt="Check UK-specific content",
url="https://example.co.uk",
proxy_location=GeoTarget(
country="GB",
city="London"
)
)
# Target California (state-level)
task = await skyvern.run_task(
prompt="Test California-specific features",
url="https://example.com",
proxy_location=GeoTarget(
country="US",
subdivision="CA"
)
)
Using Dict Format
# You can also use dict format
task = await skyvern.run_task(
prompt="Check regional pricing",
url="https://example.com",
proxy_location={
"country": "US",
"subdivision": "CA",
"city": "San Francisco"
}
)
Via API
curl -X POST https://api.skyvern.com/api/v1/tasks \
-H "x-api-key: your-api-key" \
-H "Content-Type: application/json" \
-d '{
"prompt": "Extract product information",
"url": "https://example.com",
"proxy_location": {
"country": "US",
"subdivision": "CA",
"city": "Los Angeles"
}
}'
Supported Countries
SUPPORTED_GEO_COUNTRIES = {
"US", # United States
"AR", # Argentina
"AU", # Australia
"BR", # Brazil
"CA", # Canada
"DE", # Germany
"ES", # Spain
"FR", # France
"GB", # United Kingdom
"IE", # Ireland
"IN", # India
"IT", # Italy
"JP", # Japan
"MX", # Mexico
"NL", # Netherlands
"NZ", # New Zealand
"PH", # Philippines
"KR", # South Korea
"TR", # Turkey
"ZA", # South Africa
}
Timezone Configuration
Proxies automatically set the browser timezone to match the proxy location:from skyvern.schemas.runs import get_tzinfo_from_proxy
# Timezone is automatically configured based on proxy
task = await skyvern.run_task(
prompt="Check time-sensitive content",
url="https://example.com",
proxy_location=ProxyLocation.RESIDENTIAL_JP # Uses Asia/Tokyo timezone
)
Timezone Mappings
# Examples of automatic timezone mapping:
ProxyLocation.US_CA → "America/Los_Angeles"
ProxyLocation.US_NY → "America/New_York"
ProxyLocation.RESIDENTIAL_GB → "Europe/London"
ProxyLocation.RESIDENTIAL_JP → "Asia/Tokyo"
ProxyLocation.RESIDENTIAL_AU → "Australia/Sydney"
ProxyLocation.RESIDENTIAL_IN → "Asia/Kolkata"
Use Cases
1. Multi-Region Testing
# Test product availability in different regions
regions = [
("US", ProxyLocation.RESIDENTIAL),
("UK", ProxyLocation.RESIDENTIAL_GB),
("Japan", ProxyLocation.RESIDENTIAL_JP),
("Australia", ProxyLocation.RESIDENTIAL_AU),
]
results = {}
for region_name, proxy in regions:
task = await skyvern.run_task(
prompt="Check product availability and pricing",
url="https://shop.example.com/product/ABC123",
proxy_location=proxy,
data_extraction_schema={
"available": "boolean",
"price": "number",
"currency": "string"
}
)
results[region_name] = task.output
print("Regional availability:")
for region, data in results.items():
print(f"{region}: ${data['price']} {data['currency']} - {'Available' if data['available'] else 'Out of stock'}")
2. Geo-Restricted Content
# Access content only available in specific regions
task = await skyvern.run_task(
prompt="Extract UK-specific offers",
url="https://example.co.uk/offers",
proxy_location=ProxyLocation.RESIDENTIAL_GB
)
print(f"UK Offers: {task.output}")
3. Rate Limiting Avoidance
import asyncio
from itertools import cycle
# Rotate through different proxies
proxies = cycle([
ProxyLocation.US_CA,
ProxyLocation.US_NY,
ProxyLocation.US_TX,
ProxyLocation.US_FL,
])
for i in range(100):
task = await skyvern.run_task(
prompt=f"Scrape page {i}",
url=f"https://example.com/page/{i}",
proxy_location=next(proxies) # Rotate proxies
)
await asyncio.sleep(1) # Rate limiting
4. Compliance Testing
# Test GDPR compliance from EU locations
eu_locations = [
ProxyLocation.RESIDENTIAL_DE,
ProxyLocation.RESIDENTIAL_FR,
ProxyLocation.RESIDENTIAL_IT,
ProxyLocation.RESIDENTIAL_ES,
]
for location in eu_locations:
task = await skyvern.run_task(
prompt="Check cookie consent and data privacy notices",
url="https://example.com",
proxy_location=location,
data_extraction_schema={
"cookie_consent_shown": "boolean",
"gdpr_compliant": "boolean",
"privacy_policy_link": "string"
}
)
print(f"{location}: GDPR compliant = {task.output['gdpr_compliant']}")
5. State-Specific Content
# Check state-specific regulations or content
task = await skyvern.run_task(
prompt="Extract California-specific privacy information",
url="https://example.com/privacy",
proxy_location=GeoTarget(
country="US",
subdivision="CA"
)
)
Browser Sessions with Proxy
Persistent Proxy Configuration
# Browser sessions maintain proxy configuration
workflow_run = await skyvern.run_workflow(
workflow_id="wpid_123",
proxy_location=ProxyLocation.RESIDENTIAL_GB,
browser_session_id="pbs_existing" # Will use GB proxy
)
# Session metadata includes proxy info
session = await skyvern.get_browser_session("pbs_123")
print(f"Proxy: {session.proxy_location}")
print(f"IP Address: {session.ip_address}")
Creating Sessions with Specific Proxies
# Launch browser with specific proxy
browser = await skyvern.launch_cloud_browser(
proxy_location=ProxyLocation.RESIDENTIAL_JP
)
page = await browser.get_working_page()
# All navigation uses Japan proxy
await page.goto("https://example.jp")
await page.click(prompt="Click login")
session_id = browser.browser_session_id
print(f"Session {session_id} using Japan proxy")
Configuration Options
Environment Variables
For self-hosted deployments:# Proxy configuration
PROXY_SERVER="http://proxy.example.com:8080"
PROXY_USERNAME="your-username"
PROXY_PASSWORD="your-password"
# Residential proxy zones (Skyvern Cloud)
RESIDENTIAL_PROXY_URL="http://proxy.provider.com"
RESIDENTIAL_PROXY_USERNAME="username"
RESIDENTIAL_PROXY_PASSWORD="password"
Custom Proxy Configuration
from skyvern import Skyvern
# Use custom proxy (self-hosted)
skyvern = Skyvern(
api_key="your-api-key",
proxy_server="http://your-proxy.com:8080",
proxy_username="username",
proxy_password="password"
)
Best Practices
1. Choose Appropriate Proxy
# Use geographically close proxies for better performance
if target_site.endswith(".co.uk"):
proxy = ProxyLocation.RESIDENTIAL_GB
elif target_site.endswith(".jp"):
proxy = ProxyLocation.RESIDENTIAL_JP
else:
proxy = ProxyLocation.RESIDENTIAL # Default US
task = await skyvern.run_task(
prompt="Extract data",
url=target_site,
proxy_location=proxy
)
2. Handle Proxy Failures
from skyvern.exceptions import ProxyError
try:
task = await skyvern.run_task(
prompt="Extract data",
url="https://example.com",
proxy_location=ProxyLocation.RESIDENTIAL_GB
)
except ProxyError:
# Retry with different proxy
task = await skyvern.run_task(
prompt="Extract data",
url="https://example.com",
proxy_location=ProxyLocation.RESIDENTIAL # Fallback to US
)
3. Monitor Proxy Performance
import time
proxy_performance = {}
for proxy in [ProxyLocation.RESIDENTIAL_GB, ProxyLocation.RESIDENTIAL_DE]:
start = time.time()
task = await skyvern.run_task(
prompt="Quick load test",
url="https://example.com",
proxy_location=proxy
)
duration = time.time() - start
proxy_performance[proxy] = duration
print("Proxy performance:")
for proxy, duration in proxy_performance.items():
print(f"{proxy}: {duration:.2f}s")
4. Respect Geo-Restrictions
# Only use proxies for legitimate purposes
# Respect websites' terms of service
# Don't circumvent security measures
# Good: Testing your own multi-region deployment
task = await skyvern.run_task(
prompt="Test EU version of our site",
url="https://your-app.eu",
proxy_location=ProxyLocation.RESIDENTIAL_DE
)
# Be cautious with third-party sites
# Ensure you have permission to access from different regions
Troubleshooting
Proxy Connection Failed
# Check proxy availability
try:
task = await skyvern.run_task(
prompt="Test task",
url="https://example.com",
proxy_location=ProxyLocation.RESIDENTIAL_JP
)
except Exception as e:
if "proxy" in str(e).lower():
print("Proxy connection failed, trying alternative")
# Try different proxy or no proxy
task = await skyvern.run_task(
prompt="Test task",
url="https://example.com",
proxy_location=ProxyLocation.NONE
)
IP Address Verification
# Verify proxy is working
task = await skyvern.run_task(
prompt="Extract IP address from page",
url="https://api.ipify.org?format=json",
proxy_location=ProxyLocation.RESIDENTIAL_GB,
data_extraction_schema={"ip": "string"}
)
print(f"Public IP: {task.output['ip']}")
# Should be a UK IP address
Geo-Blocked Content
# If content is still blocked, try more specific location
task = await skyvern.run_task(
prompt="Access region-locked content",
url="https://example.com",
proxy_location=GeoTarget(
country="GB",
city="London" # Try specific city
)
)
Related Documentation
- Browser Sessions - Managing browser instances
- Tasks - Running tasks
- Workflows - Building workflows
- Authentication - Authentication and security