opção

browser-to-api

browserbase/skills browserbase/skills

Gerar uma especificação OpenAPI 3.1 a partir de uma captura de rastreamento do navegador, analisando o tráfego HTTP observado, criando modelos de URLs e inferindo esquemas JSON a partir de amostras de solicitações e respostas.

...Expandir tudo
0
Tempo atualizado 30 de Setembro de 2026

Do navegador à API

Descoberta de API orientada por replays. Analisa uma captura de rastreamento do navegador, emparelha seus eventos de solicitação/resposta do CDP, cria modelos para as URLs observadas, infere esquemas JSON a partir de amostras e gera um documento OpenAPI 3.1, além de um relatório de cobertura legível por humanos.

Esta habilidade não captura tráfego. Trata-se de um processamento pós-teste puramente offline, realizado sobre os buckets cdp/network/*.jsonl do rastreamento do navegador. As duas habilidades se combinam:

browser-trace    →  .o11y//cdp/network/{requests,responses}.jsonl
browser-to-api  →  .o11y//api-spec/index.html + openapi.yaml + client.mjs

Quando usar

  • O usuário deseja um documento OpenAPI para uma API de site de terceiros ou não documentada.
  • O usuário tem um rastreamento de navegador executado e deseja extrair endpoints e esquemas a partir dele.
  • O usuário está desenvolvendo um cliente/SDK para um site que não publica uma especificação.
  • O usuário deseja um relatório de cobertura mostrando quais fluxos ampliariam a especificação.

Se o usuário quiser capturar o tráfego, encaminhe-o primeiro para o rastreamento do navegador.

Fluxo de trabalho em duas etapas

1. Capture com o browser-trace (e, opcionalmente, os corpos das mensagens ativando a opção “browse network”)

# Exemplo local para um alvo Chrome existente que pode ser depurado
TARGET=9222

node ../browser-trace/scripts/start-capture.mjs "$TARGET" my-site
browse open about:blank --cdp "$TARGET"
browse network on                                    # capturar corpos de solicitação/resposta
browse open https://example.com
# ...gerar os fluxos que você deseja capturar...

# Faça um snapshot do diretório de corpos ANTES de desativar a captura (o diretório temporário é compartilhado
# por sessão; portanto, execuções subsequentes de `browse network on` misturariam seus corpos
# com o que quer que uma captura futura grave, caso você pule esta etapa).
cp -r "$(browse network path | jq -r .path)" .o11y/my-site/cdp/network/bodies/
browse network off

node ../browser-trace/scripts/stop-capture.mjs my-site
node ../browser-trace/scripts/bisect-cdp.mjs my-site

browse network on é opcional, mas altamente recomendado — sem ele, a especificação não possui esquemas de corpo de resposta (o firehose do CDP usado pelo browse cdp não incorpora corpos). Com ele, tanto os corpos de solicitação (já capturados pelo CDP) quanto os corpos de resposta são unidos ao rastreamento pelo requestId do CDP.

2. Gerar a especificação

node scripts/discover.mjs --run .o11y/my-site
# → .o11y/my-site/api-spec/index.html          ← abra este arquivo
#   .o11y/my-site/api-spec/client.mjs
#   .o11y/my-site/api-spec/openapi.yaml
#   .o11y/my-site/api-spec/openapi.json
#   .o11y/my-site/api-spec/report.md
#   .o11y/my-site/api-spec/confidence.json
#   .o11y/my-site/api-spec/samples/*.json
#   .o11y/my-site/api-spec/intermediate/*.jsonl

O discover.mjs detecta automaticamente /cdp/network/bodies/. Para usar uma captura de corpo proveniente de outro local (por exemplo, se não foi feito um snapshot e você deseja o diretório de rede em tempo real ), passe explicitamente a opção --bodies .

3. Abra o relatório em HTML

Após a conclusão do discover.mjs, sempre abra o relatório HTML gerado:

abra .o11y/my-site/api-spec/index.html

O relatório é um arquivo HTML independente (não requer servidor) que mostra cada operação descoberta como um cartão expansível com variáveis, uso do cliente, exemplos de solicitação/resposta e um trecho gerado do client.mjs na parte inferior. Esse é o principal resultado — sempre o abra para o usuário.

Opções da CLI

Opção Obrigatório Significado
--run sim Caminho para o diretório de execução do rastreamento do navegador
--out não Diretório de saída; padrão /api-spec/
--bodies não navegar pelo diretório de capturade rede para incluir no rastreamento (detectado automaticamente em /api-spec/ quando presente)
--include não Incluir apenas URLs que correspondam à expressão regular (repetível)
--excluir não Excluir URLs que correspondam à expressão regular (repetível; além dos padrões)
--origins não Lista de origens permitidas separadas por vírgulas (por exemplo, api.example.com,example.com)
--format não Formato de saída. Padrão: ambos
--title não Informações da OpenAPI .título. Padrão derivado da origem principal
--redact não Nomes de cabeçalhos extras / chaves JSON a serem suprimidos (separados por vírgulas)
--min-samples não Número mínimo de amostras por endpoint a serem incluídas. Padrão: 1
--stage não Executar apenas um estágio: carregar, filtrar, normalizar, inferir, emitir

Layout de saída

/api-spec/
├── index.html                relatório visual — abra este arquivo (autônomo, sem servidor)
├── client.mjs                cliente fetch zero-dep com funções tipadas por operação
├── openapi.yaml              especificação legível por máquina
├── openapi.json              espelho
├── report.md                 resumo em Markdown + exemplos de curl
├── confidence.json           confiança por endpoint + sinalizadores de normalização
├── samples/                  exemplos de solicitação/resposta com dados ocultados
│   └── __.json
└── intermediate/             subprodutos do pipeline (jsonl emparelhado/filtrado/por endpoint)

O que você obtém com o “browse cdp” e o “browse network”

Duas fontes de captura complementares:

Fonte Fornece Limitação
browse cdp (usado pelo browser-trace) método desolicitação/URL/cabeçalhos/dados de POST, status da resposta/cabeçalhos/tipo MIME, cronograma completo do evento Não incorpora o corpo da resposta. O corpo deve ser obtido com Network.getResponseBody, o que o firehose não faz.
navegar pela rede (comando separado) corpos de solicitação E corpos de resposta no disco, indexados pelo requestId do CDP A pasta de captura é compartilhada por sessão de navegação; um snapshot feito antes de executar outro “browse network on” a sobrescreve.

O discover.mjs extrairá os corpos de um diretório de navegação de rede se você passar --bodies (ou armazená-los em /cdp/network/bodies/, que é detectado automaticamente). A correspondência é feita pelo requestId — a navegação de rede grava isso em cada request.json como id, e nós fazemos a junção diretamente.

O que muda quando os corpos estão presentes:

  • ✅ Modelagem de caminhos, esquemas de parâmetros de consulta, códigos de status, tipos de conteúdo — permanecem os mesmos em ambos os casos.
  • ✅ Esquemas do corpo da solicitação — o `postData` do CDP é suficiente; o diretório de corpos é um recurso opcional para casosque não utilizam `postData`.
  • ✅ Esquemas do corpo da resposta — totalmente inferidos a partir de amostras reais. Sem corpos, você obtém esqueletos do tipo { description, content: }.

O relatório sinaliza todos os endpoints que não possuem amostra de corpo de resposta.

Filtragem automática de ruído

A etapa de normalização classifica e descarta automaticamente o ruído da infraestrutura:

  • Rastreamento/análise — caminhos contendo /track, /pixel, /beacon, /impression, /pageview, /dag/v*
  • Defesa contra bots — Akamai (/akam/), cargas úteis de impressão digital (sensor_data), caminhos multifragmentados ofuscados
  • Estrutura de sessão — /session, /authenticate/start, consentimento de cookies, endpoints de experimentos A/B
  • Renderizações de páginas HTML — solicitações GET que retornam text/html (a página renderizada, não a API)

Isso normalmente elimina 60 a 80% do tráfego capturado. O sinalizador --include pode corrigir um falso positivo.

Decomposição de pontos de extremidade GraphQL / multiplexados

Quando um único endpoint (como /dapi/fe/gql) é chamado com diferentes valores de operationName, a skill automaticamente o divide em operações lógicas separadas. Cada uma recebe seu próprio:

  • Entrada de caminho OpenAPI (por exemplo, /dapi/fe/gql [Autocompletar])
  • Esquema de solicitação/resposta inferido apenas a partir das amostras dessa operação
  • Exemplo de Curl e tabela de variáveis no relatório

A detecção funciona em campos do corpo (operationName, method, action) e parâmetros de consulta (opname, op). Isso abrange GraphQL (APQ e inline), JSON-RPC e padrões de despacho semelhantes.

Limitações

  • A cobertura é limitada ao fluxo capturado. Endpoints não executados no rastreamento não aparecerão. A habilidade não pode garantir a completude.
  • Os esquemas são indutivos, não contratuais. Um campo pode ser opcional no servidor, mesmo que todas as amostras o contenham.
  • A autenticação é observada, não especificada. A habilidade registra cabeçalhos de autenticação em uma extensão x-observed-auth, mas não afirma um esquema de segurança.
  • A modelagem de caminhos é heurística. Padrões numéricos, UUID, hexadecimais e slugs são detectados por segmento. URLs ambíguas são sinalizadas no arquivo confidence.json.
  • A supressão de dados é feita da melhor maneira possível. As supressões padrão abrangem credenciais comuns, mas segredos específicos do aplicativo podem passar despercebidos; use --redact para cabeçalhos/chaves personalizados conhecidos.

Melhores práticas

  1. Direcione os fluxos que você deseja documentar. Quanto mais rico for o rastreamento do navegador, mais rica será a especificação.
  2. Use --origins para sites com tráfego intenso. Uma página de marketing acessa dezenas de servidores de análise; restrinja à origem da API que lhe interessa.
  3. Inspecione o arquivo report.md primeiro. Ele contém exemplos prontos para o `curl` e amostras de respostas para cada operação descoberta.
  4. Aumente --min-samples para 2+ quando quiser apenas endpoints com formato confiável no documento final — descarte os casos menos frequentes.
  5. Combine com a opção “browse network on” quando os esquemas do corpo da resposta forem importantes. O CDP Firehose, por si só, contém corpos de solicitação, mas não corpos de resposta.

Para detalhes internos do pipeline e a referência do formato de arquivo, consulte o arquivo REFERENCE.md.

Ver no GitHub
---
name: browser-to-api
description: Generate an OpenAPI 3.1 specification from a browser-trace capture by analyzing observed HTTP traffic, templating URLs, and inferring JSON schemas from request/response samples.
license: MIT
---

# Browser to API

Replay-driven API discovery. Consume a `browser-trace` capture, pair its CDP request / response events, templatize observed URLs, infer JSON schemas from samples, and emit an **OpenAPI 3.1** document plus a human-readable coverage report.

This skill **does not capture traffic**. It is purely offline post-processing on top of `browser-trace`'s `cdp/network/*.jsonl` buckets. The two skills compose:

```
browser-trace    →  .o11y/<run>/cdp/network/{requests,responses}.jsonl
browser-to-api   →  .o11y/<run>/api-spec/index.html + openapi.yaml + client.mjs
```

## When to use

- The user wants an OpenAPI document for a third-party or undocumented website API.
- The user has a `browser-trace` run and wants endpoints + schemas extracted from it.
- The user is building a client/SDK against a site that doesn't publish a spec.
- The user wants a coverage report showing which flows would broaden the spec.

If the user wants to **capture** traffic, send them to `browser-trace` first.

## Two-step workflow

### 1. Capture with `browser-trace` (and optionally bodies via `browse network on`)

```bash
# Local example against an existing debuggable Chrome target
TARGET=9222

node ../browser-trace/scripts/start-capture.mjs "$TARGET" my-site
browse open about:blank --cdp "$TARGET"
browse network on                                    # capture request/response bodies
browse open https://example.com
# ...drive whatever flows you want covered...

# Snapshot the bodies dir BEFORE turning capture off (the temp dir is shared
# per-session, so subsequent `browse network on` runs would mix your bodies
# with whatever a future capture writes if you skip this step).
cp -r "$(browse network path | jq -r .path)" .o11y/my-site/cdp/network/bodies/
browse network off

node ../browser-trace/scripts/stop-capture.mjs my-site
node ../browser-trace/scripts/bisect-cdp.mjs my-site
```

`browse network on` is **optional but strongly recommended** — without it, the spec has no response-body schemas (the CDP firehose used by `browse cdp` does not embed bodies). With it, both request bodies (already captured by CDP) *and* response bodies are joined into the trace by CDP `requestId`.

### 2. Generate the spec

```bash
node scripts/discover.mjs --run .o11y/my-site
# → .o11y/my-site/api-spec/index.html          ← open this
#   .o11y/my-site/api-spec/client.mjs
#   .o11y/my-site/api-spec/openapi.yaml
#   .o11y/my-site/api-spec/openapi.json
#   .o11y/my-site/api-spec/report.md
#   .o11y/my-site/api-spec/confidence.json
#   .o11y/my-site/api-spec/samples/*.json
#   .o11y/my-site/api-spec/intermediate/*.jsonl
```

`discover.mjs` auto-detects `<run>/cdp/network/bodies/`. To use a body capture from elsewhere (e.g. didn't snapshot, want the live `browse network` dir), pass `--bodies <path>` explicitly.

### 3. Open the HTML report

After `discover.mjs` finishes, **always open the generated HTML report**:

```bash
open .o11y/my-site/api-spec/index.html
```

The report is a self-contained HTML file (no server needed) that shows each discovered operation as an expandable card with variables, client usage, request/response examples, and a generated `client.mjs` snippet at the bottom. This is the primary deliverable — always open it for the user.

## CLI flags

| Flag | Required | Meaning |
|---|---|---|
| `--run <path>` | yes | Path to a `browser-trace` run directory |
| `--out <path>` | no | Output dir; default `<run>/api-spec/` |
| `--bodies <path>` | no | `browse network` capture dir to join into the trace (auto-detected from `<run>/cdp/network/bodies/` when present) |
| `--include <regex>` | no | Only include URLs matching regex (repeatable) |
| `--exclude <regex>` | no | Exclude URLs matching regex (repeatable; in addition to defaults) |
| `--origins <list>` | no | Comma-separated origin allow-list (e.g. `api.example.com,example.com`) |
| `--format <yaml\|json\|both>` | no | Output format. Default `both` |
| `--title <string>` | no | OpenAPI `info.title`. Default derived from primary origin |
| `--redact <list>` | no | Extra header names / JSON keys to redact (comma-separated) |
| `--min-samples <n>` | no | Minimum samples per endpoint to include. Default `1` |
| `--stage <name>` | no | Run only one stage: `load`, `filter`, `normalize`, `infer`, `emit` |


## Output layout

```
<run>/api-spec/
├── index.html                visual report — open this (self-contained, no server)
├── client.mjs                zero-dep fetch client with typed functions per operation
├── openapi.yaml              machine-readable spec
├── openapi.json              mirror
├── report.md                 markdown summary + curl examples
├── confidence.json           per-endpoint confidence + normalization flags
├── samples/                  redacted request/response examples
│   └── <method>__<path-hash>.json
└── intermediate/             pipeline byproducts (paired/filtered/endpoints jsonl)
```

## What you get from `browse cdp` and `browse network`

Two complementary capture sources:

| Source | Provides | Limitation |
|---|---|---|
| `browse cdp` (used by `browser-trace`) | request method/URL/headers/`postData`, response status/headers/mimeType, full event timing | **Does not embed response bodies.** Bodies must be pulled with `Network.getResponseBody`, which the firehose doesn't do. |
| `browse network on` (separate command) | request bodies AND response bodies on disk, keyed by CDP `requestId` | Capture dir is shared per `browse` session; snapshot before another `browse network on` overwrites it. |

`discover.mjs` will pull bodies from a `browse network` dir if you pass `--bodies <path>` (or stash them under `<run>/cdp/network/bodies/`, which is auto-detected). The matching is by `requestId` — `browse network` writes that into each `request.json` as `id`, and we join directly.

What changes when bodies are present:

- ✅ Path templating, query-param schemas, status codes, content-types — same either way.
- ✅ Request-body schemas — `postData` from CDP is enough; bodies dir is a nice-to-have for non-`postData` cases.
- ✅ **Response-body schemas** — fully inferred from real samples. Without bodies you get `{ description, content: <mimeType> }` skeletons.

The report flags every endpoint that has no response-body sample.

## Automatic noise filtering

The normalize stage automatically classifies and drops infrastructure noise:

- **Tracking / analytics** — paths containing `/track`, `/pixel`, `/beacon`, `/impression`, `/pageview`, `/dag/v*`
- **Bot defense** — Akamai (`/akam/`), fingerprint payloads (`sensor_data`), obfuscated multi-segment paths
- **Session plumbing** — `/session`, `/authenticate/start`, cookie consent, A/B experiment endpoints
- **HTML page renders** — `GET` requests returning `text/html` (the rendered page, not the API)

This typically drops 60-80% of captured traffic. The `--include` flag can rescue a false positive.

## GraphQL / multiplexed endpoint decomposition

When a single endpoint (like `/dapi/fe/gql`) is called with different `operationName` values, the skill automatically splits it into separate logical operations. Each gets its own:
- OpenAPI path entry (e.g. `/dapi/fe/gql [Autocomplete]`)
- Request/response schema inferred from only that operation's samples
- Curl example and variables table in the report

Detection works on body fields (`operationName`, `method`, `action`) and query params (`opname`, `op`). This covers GraphQL (APQ and inline), JSON-RPC, and similar dispatch patterns.

## Limitations

- **Coverage is bounded by the captured flow.** Endpoints not exercised in the trace will not appear. The skill cannot prove completeness.
- **Schemas are inductive, not contractual.** A field might be optional on the server even if every sample contained it.
- **Auth is observed, not specified.** The skill records auth-shaped headers in an `x-observed-auth` extension but won't claim a security scheme.
- **Path templating is heuristic.** Numeric / UUID / hex / slug patterns are detected per segment. Ambiguous URLs are flagged in `confidence.json`.
- **Redaction is best-effort.** Default redactions cover common credentials, but app-specific secrets may slip through; use `--redact` for known custom headers/keys.

## Best practices

1. **Drive the flows you want documented.** The richer the browser-trace, the richer the spec.
2. **Use `--origins` for noisy sites.** A marketing page hits dozens of analytics hosts; restrict to the API origin you care about.
3. **Inspect `report.md` first.** It has curl-ready examples and response samples for every discovered operation.
4. **Bump `--min-samples` to 2+** when you want only confidently-shaped endpoints in the final doc — drop the long tail.
5. **Pair with `browse network on`** when response-body schemas matter. The CDP firehose alone has request bodies but not response bodies.

For pipeline internals and the file format reference, see [REFERENCE.md](REFERENCE.md).

Instalar browser-to-api

Baixe e descompacte os arquivos de habilidades no diretório .claude/skills/.

Baixar ZIP

Clone o repositório e copie os arquivos da habilidade para o seu projeto.

git clone https://github.com/browserbase/skills/tree/main/skills/browser-to-api # Copy SKILL.md to your .claude/skills/ directory

Copiar Copiar
Configuração rápida: Copie a pasta da habilidade para .claude/skills/ O Claude detectará e utilizará automaticamente a habilidade
Repositório browserbase/skills

Habilidades relacionadas

agentwallet
Tempo atualizado 7 de Julho de 2026
brightdata-cli
Tempo atualizado 29 de Junho de 2026
humanize
Tempo atualizado 7 de Julho de 2026
korean-stock-search
Tempo atualizado 8 de Julho de 2026
OR