Solari

Quickstart

Install the SDK, mint an API key, and drive a real browser in under a minute.

Requirements

  • Node 20+ for @solarisdk/browser (the sandbox and VM SDKs need Node 18+).
  • Python 3.9+ for solari-browser.
  • await using works in compiled TypeScript 5.2+ (Node 20+ for browsers); running the syntax uncompiled needs Node 24. Sandboxes and VMs support it too with @solarisdk/sandbox and @solarisdk/desktop 0.4.0 / 0.2.0 or later; on older versions, use try/finally and call kill().

Install

npm install @solarisdk/browser

That's it. The SDK ships its own browser client. No Playwright or Patchright install needed.

Get an API key

Sign in at console.getsolari.com and create a key from the API Keys tab. You'll see the key once, right after you create it, so copy it then.

Keep your key private
Anyone with your key can run sessions and read every profile in your account. If it leaks, rotate it from the console.
export SOLARI_API_KEY="slr_live_…"

Open a session

launch() gives you a fresh browser with the standard Playwright API. browser.close() ends the session and lets your script exit.

import { Solari } from "@solarisdk/browser"

const client = new Solari({
  apiKey: process.env.SOLARI_API_KEY!,
  baseUrl: "https://api.getsolari.com",
  // region: "us-west",   // default, see /regions for the full list
})

const browser = await client.launch()

const page = await browser.newPage()
await page.goto("https://example.com")
console.log(await page.title())

await browser.close()    // ends the session; the script can now exit

Python

pip install solari-browser
import asyncio, os
from solari_browser import Solari

async def main():
    client = Solari(api_key=os.environ["SOLARI_API_KEY"])
    try:
        browser = await client.launch()
        page = await browser.new_page()
        await page.goto("https://example.com")
        print(await page.title())
        await browser.close()    # ends the session
    finally:
        await client.close()     # releases the connection pool

asyncio.run(main())
Optional: client.close()
browser.close() is enough to let your script exit. If you want to release the client's connection pool the moment you're done, call await client.close() too. On @solarisdk/browser before 0.1.3 this call was required — without it the process would hang after printing.

Drive the browser

Everything Playwright exposes is available on the page: navigation, locators, evaluation, screenshots, waits.

const browser = await client.launch()
const page = await browser.newPage()

// Navigate and wait for the network to settle.
await page.goto("https://news.ycombinator.com", { waitUntil: "networkidle" })

// Click and type with auto-waiting locators.
await page.locator("a:has-text('login')").click()
await page.locator("input[name=acct]").fill("demo-user")
await page.locator("input[name=pw]").fill("hunter2")

// Pull data out via evaluate.
const headlines = await page.locator(".titleline > a").allInnerTexts()

// Screenshot the whole page as PNG bytes.
const png = await page.screenshot({ fullPage: true })

await browser.close()

Or let it close itself

In compiled TypeScript 5.2+ (or on Node 24 uncompiled), await using closes the browser for you when the variable goes out of scope, even if something throws.

{
  await using browser = await client.launch({ stealth: true })
  const page = await browser.newPage()
  await page.goto("https://example.com")
  // browser closes here, automatically
}

Full kit

Combine stealth, a sticky residential proxy, captcha solving, and recording for the typical "scrape a defended site" shape.

Paid plans only
Stealth, proxies, and captcha solving need a paid plan. On the Free plan, a session that asks for any of them fails with HTTP 402.
const browser = await client.launch({
  stealth: true,
  recording: true,
  captcha: true,
  proxy: { country: "us", session: "warmup-1", sessionDuration: 10 },
})

const page = await browser.newPage()
await page.goto("https://example.com")

const sessionId = browser.id
await browser.close()

// The replay is ready a few seconds after you close.
const { url } = await client.sessions.getReplayUrl(sessionId)
console.log("replay:", url)

Next