import type { Metadata } from "next"; import { CodeBlock } from "@/components/ui/code-block"; import { DocPage } from "@/components/docs/doc-page"; import { A, Code, H2, Li, P, Step, Steps, Strong, Ul } from "@/components/docs/prose"; import { Callout } from "@/components/docs/callout"; import { CodeTabs } from "@/components/docs/code-tabs"; import { ResponseExample } from "@/components/docs/response-example"; export const metadata: Metadata = { title: "Quickstart", description: "Create an account, generate an API key and make your first Fetcha request in cURL, JavaScript or Python.", }; const FIRST_REQUEST_CURL = `curl https://www.fetcha.co/v1/fetch -X POST -H "Authorization: Bearer $FETCHA_API_KEY" -H "Content-Type: application/json" -d '{"url": "https://example.com"}'`; const FIRST_REQUEST_JS = `const res = await fetch("https://www.fetcha.co/v1/fetch", { method: "POST", headers: { Authorization: \`Bearer \${process.env.FETCHA_API_KEY}\`, "Content-Type": "application/json", }, body: JSON.stringify({ url: "https://example.com" }), }); const data = await res.json(); if (!res.ok) throw new Error(\`\${data.error.code}: \${data.error.message}\`); console.log(data.status); // 200 console.log(data.metadata.network); // "residential" console.log(data.content.slice(0, 200));`; const FIRST_REQUEST_PY = `import os import requests res = requests.post( "https://www.fetcha.co/v1/fetch", headers={ "Authorization": f"Bearer {os.environ['FETCHA_API_KEY']}", "Content-Type": "application/json", }, json={"url": "https://example.com"}, ) data = res.json() if res.status_code >= 400: raise RuntimeError(f"{data['error']['code']}: {data['error']['message']}") print(data["status"]) # 200 print(data["metadata"]["network"]) # "residential" print(data["content"][:200])`; const RESPONSE = { request_id: "req_k3j9d0f2a8b1c7e4", success: true, status: 200, url: "https://example.com", final_url: "https://example.com/", content: "\n\n
\n
Sign up at fetcha.co/signup with your email address and a password. A personal organization (Your name's workspace) and a first project named{" "}
Default are created automatically; you can rename them later in the dashboard.
Open the verification link we send you. Until the email is verified, every API call returns 403 EMAIL_NOT_VERIFIED. The dashboard Playground works before verification so
you can explore, but real API keys do not.
In the dashboard, open your project, go to API keys and create a key. Choose live mode (keys start with fch_live_) and keep the default scopes{" "}
fetch:execute, sessions:write and usage:read.
Post a URL to /v1/fetch. This exact one-liner is the smallest valid request: no country, no network, default html format, 30-second timeout.
The same request from application code:
A fetch returns HTTP 200 whenever Fetcha reached the target, even if the target itself answered with an error. Look at success and status{" "}
to know how the origin responded, and at metadata to see how the request was routed.
success is true when the origin answered with a 2xx or 3xx status and the page did not look like a block. A blocked target returns{" "}
success: false with the origin's status (for example 403) and metadata.attempts greater than one.
content holds the body as a string for html, json and raw formats. Ask for {`"format": "text"`} to receive a readable{" "}
text field instead, or {`"format": "json"`} to get a parsed json field.
metadata.network is the concrete network class that served the request (residential today). metadata.country echoes the country you targeted, or{" "}
null.
request_id is what you quote to support. It also appears in the X-Fetcha-Request-ID response header.
The dashboard Playground runs the same pipeline as the API against your current project, without needing a key in your terminal. Use it to try
countries, formats and sessions, inspect timing, and copy the generated code. Requests made there are counted in your usage and appear in the request log with source{" "}
playground.
{`"country": "CA"`}: see Geolocation.