# Quickstart

**Just want your AI assistant to use a browser?** Add `https://cdpfleet.com/mcp` to Claude, ChatGPT, Cursor or Claude Code as a connector (MCP server) and sign in when it asks — no API key, no code. Step by step for each app: [MCP setup](https://cdpfleet.com/docs/mcp/setup).

## From code

The examples below run as they are: set your API key and nothing else. No proxy and no local browsers are needed.

1.  Create an API key in the [dashboard](https://cdpfleet.com/app) and export it:
    
    ```sh
    export CDPFLEET_API_KEY=cdpf_...
    ```
    
2.  Install the packages listed at the top of your language's example.
3.  Run it. It launches a headless Chromium on the fleet, opens example.com through the [proxy included with your plan](https://cdpfleet.com/docs/proxies#community-proxy) and prints `Example Domain`.

With the SDK With Playwright only

### With the SDK

The [cdpfleet SDK](https://cdpfleet.com/docs/sdk) (npm and PyPI `cdpfleet`, a Go module) launches with the right retries when the fleet is busy and closes the session for you; you bring your own Playwright. The C# and Java SDKs aren't published yet — use **With Playwright only**.

 

```node
// npm install cdpfleet playwright@1.60.0
// Browsers run on cdpfleet, so no `npx playwright install` is needed.
import { chromium } from 'playwright';
import { Cdpfleet } from 'cdpfleet';

const fleet = new Cdpfleet(); // reads CDPFLEET_API_KEY
const options = {
  headless: 'new',
};

const session = await fleet.launch('chromium', options);
const browser = await session.connect(chromium);
const page = await browser.newPage();
await page.goto('https://example.com');
console.log(await page.title());
await session.close(); // ends the session and stops billing
```

```python
# pip install cdpfleet playwright==1.60.0
# Browsers run on cdpfleet, so no `playwright install` is needed.
from cdpfleet import Cdpfleet
from playwright.sync_api import sync_playwright

fleet = Cdpfleet()  # reads CDPFLEET_API_KEY
options = {
    "headless": "new",
}

with sync_playwright() as p, fleet.launch("chromium", options) as session:
    browser = session.connect(p.chromium)
    page = browser.new_page()
    page.goto("https://example.com")
    print(page.title())
# leaving the block closes the session and stops billing
```

```go
// go get github.com/cdpfleet/cdpfleet/sdk/go github.com/playwright-community/playwright-go@v0.6000.0
//
// One-time driver setup (needs Node.js 18+): playwright-go can no longer download the
// 1.60.0 driver itself, so build it from npm and point PLAYWRIGHT_DRIVER_PATH at it:
//   mkdir -p ~/.cache/pw-driver-1.60.0 && cd ~/.cache/pw-driver-1.60.0 &&
//     curl -sL https://registry.npmjs.org/playwright-core/-/playwright-core-1.60.0.tgz | tar xz &&
//     ln -sf "$(command -v node)" node
//   export PLAYWRIGHT_DRIVER_PATH=~/.cache/pw-driver-1.60.0
package main

import (
	"encoding/json"
	"fmt"
	"log"

	cdpfleet "github.com/cdpfleet/cdpfleet/sdk/go"
	"github.com/playwright-community/playwright-go"
)

func main() {
	fleet, err := cdpfleet.New() // reads CDPFLEET_API_KEY
	if err != nil {
		log.Fatal(err)
	}
	var options cdpfleet.Options
	if err := json.Unmarshal([]byte(`{
	  "headless": "new"
	}`), &options); err != nil {
		log.Fatal(err)
	}

	pw, err := playwright.Run(&playwright.RunOptions{SkipInstallBrowsers: true})
	if err != nil {
		log.Fatal(err)
	}
	defer pw.Stop()

	session, err := fleet.Launch("chromium", options)
	if err != nil {
		log.Fatal(err)
	}
	defer session.Close() // ends the session and stops billing

	browser, err := session.Connect(pw.Chromium)
	if err != nil {
		log.Fatal(err)
	}
	page, err := browser.NewPage()
	if err != nil {
		log.Fatal(err)
	}
	if _, err := page.Goto("https://example.com"); err != nil {
		log.Fatal(err)
	}
	title, _ := page.Title()
	fmt.Println(title)
}
```

### With Playwright only

No SDK: one HTTP request launches the browser, then Playwright connects to the `wsUrl` it returns. Works in all five languages.

 

```node
// npm install playwright@1.60.0
// Browsers run on cdpfleet, so no `npx playwright install` is needed.
import { chromium } from 'playwright';

const KEY = process.env.CDPFLEET_API_KEY;

// 1. Launch the browser
const res = await fetch('https://starter.cdpfleet.com/chromium/session', {
  method: 'POST',
  headers: { 'x-api-key': KEY, 'content-type': 'application/json' },
  body: JSON.stringify({
    headless: 'new',
  }),
});
if (!res.ok) throw new Error(`launch failed: ${res.status} ${await res.text()}`);
const { wsUrl } = await res.json();

// 2. Connect and drive it
const browser = await chromium.connect(wsUrl, { headers: { 'x-api-key': KEY } });
const page = await browser.newPage();
await page.goto('https://example.com');
console.log(await page.title());
await browser.close(); // ends the session and stops billing
```

```python
# pip install playwright==1.60.0 requests
# Browsers run on cdpfleet, so no `playwright install` is needed.
import os
import requests
from playwright.sync_api import sync_playwright

KEY = os.environ["CDPFLEET_API_KEY"]

# 1. Launch the browser
res = requests.post(
    "https://starter.cdpfleet.com/chromium/session",
    headers={"x-api-key": KEY},
    json={
        "headless": "new",
    },
    timeout=60,
)
res.raise_for_status()
ws_url = res.json()["wsUrl"]

# 2. Connect and drive it
with sync_playwright() as p:
    browser = p.chromium.connect(ws_url, headers={"x-api-key": KEY})
    page = browser.new_page()
    page.goto("https://example.com")
    print(page.title())
    browser.close()  # ends the session and stops billing
```

```java
// Maven: com.microsoft.playwright:playwright:1.60.0  and  com.google.code.gson:gson:2.11.0
// Run with PLAYWRIGHT_SKIP_BROWSER_DOWNLOAD=1: browsers run on cdpfleet.
import com.google.gson.JsonParser;
import com.microsoft.playwright.*;
import java.net.URI;
import java.net.http.*;
import java.util.Map;

public class Example {
  public static void main(String[] args) throws Exception {
    String key = System.getenv("CDPFLEET_API_KEY");

    // 1. Launch the browser
    String body = """
        {
          "headless": "new"
        }
        """;
    HttpResponse<String> res = HttpClient.newHttpClient().send(
        HttpRequest.newBuilder(URI.create("https://starter.cdpfleet.com/chromium/session"))
            .header("x-api-key", key)
            .header("content-type", "application/json")
            .POST(HttpRequest.BodyPublishers.ofString(body))
            .build(),
        HttpResponse.BodyHandlers.ofString());
    if (res.statusCode() != 200) {
      throw new RuntimeException("launch failed: " + res.statusCode() + " " + res.body());
    }
    String wsUrl = JsonParser.parseString(res.body()).getAsJsonObject().get("wsUrl").getAsString();

    // 2. Connect and drive it
    try (Playwright playwright = Playwright.create()) {
      Browser browser = playwright.chromium().connect(wsUrl,
          new BrowserType.ConnectOptions().setHeaders(Map.of("x-api-key", key)));
      Page page = browser.newPage();
      page.navigate("https://example.com");
      System.out.println(page.title());
      browser.close(); // ends the session and stops billing
    }
  }
}
```

```csharp
// dotnet add package Microsoft.Playwright --version 1.60.0
// Browsers run on cdpfleet, so no `playwright install` is needed.
using System.Net.Http.Json;
using System.Text;
using System.Text.Json;
using Microsoft.Playwright;

var key = Environment.GetEnvironmentVariable("CDPFLEET_API_KEY")!;

// 1. Launch the browser
using var http = new HttpClient();
http.DefaultRequestHeaders.Add("x-api-key", key);
var body = """
    {
      "headless": "new"
    }
    """;
var res = await http.PostAsync("https://starter.cdpfleet.com/chromium/session",
    new StringContent(body, Encoding.UTF8, "application/json"));
if (!res.IsSuccessStatusCode)
    throw new Exception($"launch failed: {(int)res.StatusCode} {await res.Content.ReadAsStringAsync()}");
var wsUrl = (await res.Content.ReadFromJsonAsync<JsonElement>()).GetProperty("wsUrl").GetString()!;

// 2. Connect and drive it
using var playwright = await Playwright.CreateAsync();
var browser = await playwright.Chromium.ConnectAsync(wsUrl, new BrowserTypeConnectOptions
{
    Headers = new Dictionary<string, string> { ["x-api-key"] = key },
});
var page = await browser.NewPageAsync();
await page.GotoAsync("https://example.com");
Console.WriteLine(await page.TitleAsync());
await browser.CloseAsync(); // ends the session and stops billing
```

```go
// go get github.com/playwright-community/playwright-go@v0.6000.0
//
// One-time driver setup (needs Node.js 18+): playwright-go can no longer download the
// 1.60.0 driver itself, so build it from npm and point PLAYWRIGHT_DRIVER_PATH at it:
//   mkdir -p ~/.cache/pw-driver-1.60.0 && cd ~/.cache/pw-driver-1.60.0 &&
//     curl -sL https://registry.npmjs.org/playwright-core/-/playwright-core-1.60.0.tgz | tar xz &&
//     ln -sf "$(command -v node)" node
//   export PLAYWRIGHT_DRIVER_PATH=~/.cache/pw-driver-1.60.0
// Browsers run on cdpfleet, so no browsers are downloaded (SkipInstallBrowsers).
package main

import (
	"encoding/json"
	"fmt"
	"io"
	"log"
	"net/http"
	"os"
	"strings"

	"github.com/playwright-community/playwright-go"
)

func main() {
	key := os.Getenv("CDPFLEET_API_KEY")

	// 1. Launch the browser
	body := `{
	  "headless": "new"
	}`
	req, _ := http.NewRequest("POST", "https://starter.cdpfleet.com/chromium/session", strings.NewReader(body))
	req.Header.Set("x-api-key", key)
	req.Header.Set("content-type", "application/json")
	res, err := http.DefaultClient.Do(req)
	if err != nil {
		log.Fatal(err)
	}
	defer res.Body.Close()
	if res.StatusCode != http.StatusOK {
		msg, _ := io.ReadAll(res.Body)
		log.Fatalf("launch failed: %s %s", res.Status, msg)
	}
	var session struct {
		WsURL string `json:"wsUrl"`
	}
	if err := json.NewDecoder(res.Body).Decode(&session); err != nil {
		log.Fatal(err)
	}

	// 2. Connect and drive it (Install fetches only the Playwright driver, once)
	opts := &playwright.RunOptions{SkipInstallBrowsers: true}
	if err := playwright.Install(opts); err != nil {
		log.Fatal(err)
	}
	pw, err := playwright.Run(opts)
	if err != nil {
		log.Fatal(err)
	}
	defer pw.Stop()
	browser, err := pw.Chromium.Connect(session.WsURL, playwright.BrowserTypeConnectOptions{
		Headers: map[string]string{"x-api-key": key},
	})
	if err != nil {
		log.Fatal(err)
	}
	page, err := browser.NewPage()
	if err != nil {
		log.Fatal(err)
	}
	if _, err := page.Goto("https://example.com"); err != nil {
		log.Fatal(err)
	}
	title, _ := page.Title()
	fmt.Println(title)
	browser.Close() // ends the session and stops billing
}
```

## Use your own proxy (optional)

Without `proxy`, sessions use the [Community proxy](https://cdpfleet.com/docs/proxies#community-proxy), free on every plan: shared by everyone who uses it, so slower at peak times, and a launch can be refused with `503 community_capacity_full` when it's full. Our three test launches on 2026-11-04 each got a different US IP. For your own proxy, add it to the launch options — the same key in every language and in the SDK:

```json
{
  "headless": "new",
  "proxy": "http://user:pass@proxy.example.com:8080"
}
```

Formats (HTTP, SOCKS5), pools, per-host rules and countries: [Proxies](https://cdpfleet.com/docs/proxies).

Next: pick another [browser](https://cdpfleet.com/docs/browsers), build a custom configuration in the [code builder](https://cdpfleet.com/docs/builder), or browse the [examples and benchmarks](https://cdpfleet.com/docs/cases).

## What the launch returns

```json
{
  "sessionId": "46903d7c-87d2-4320-b85b-cf109c0ec984",
  "wsUrl": "wss://router01.cdpfleet.com/session/46903d7c-87d2-4320-b85b-cf109c0ec984",
  "browser": "chromium",
  "resource_class": "linux_headless",
  "weight": 1,
  "memory_mb": 4096,
  "expires_at": "2026-09-30T13:00:00.000Z"
}
```

-   `wsUrl` — connect to it within **60 seconds**, or the session is closed. It's single-use: once you disconnect, the session ends.
-   `weight` / `resource_class` — how many of your plan's threads this session uses (see [Sessions & billing](https://cdpfleet.com/docs/sessions)).
-   `memory_mb` — the session's memory limit; going over it ends the session with `session_memory_limit`.
-   `expires_at` — when the session will be ended at the latest (its overall timeout, capped by your plan).

---
Source: https://cdpfleet.com/docs/quickstart · Markdown: https://cdpfleet.com/docs/quickstart.md · All docs for AI tools: https://cdpfleet.com/llms.txt
