API Quickstart
Turn any PDF or scanned image into structured JSON in under 5 minutes. This guide gets you from zero to a working integration.
01 Getting Started
Three steps to your first parsed document:
Go to shapeforge-4vqx.polsia.app/#pricing and pick a plan. API key delivered instantly after checkout — no waiting, no manual review.
Your dashboard shows two keys: a sk_live_ key for real documents and a sk_test_ key for sandbox testing. Start with the test key — it's free and unlimited.
Send a file or URL to POST /api/v1/parse. Get back structured JSON with field extraction, confidence scores, and tables. See the example below →
02 Authentication
All API requests require a Bearer token in the Authorization header.
Authorization: Bearer sk_test_your_key_here
| Key prefix | Type | Behavior |
|---|---|---|
sk_test_ |
Sandbox | Returns deterministic mock responses. No documents parsed, zero inference cost. Unlimited calls. |
sk_live_ |
Live | Processes real documents using AI. Counts against your monthly quota. Requires a paid plan. |
sk_test_ keys. Switch to sk_live_ when you're ready to process real documents. Your integration code doesn't need to change — same endpoint, same request format.
03 First API Call
The single endpoint: POST /api/v1/parse. Accepts a file upload or a document URL.
Upload a file
curl -X POST https://shapeforge-4vqx.polsia.app/api/v1/parse \ -H 'Authorization: Bearer sk_test_your_key_here' \ -F 'file=@invoice.pdf'
Parse from URL
curl -X POST https://shapeforge-4vqx.polsia.app/api/v1/parse \ -H 'Authorization: Bearer sk_test_your_key_here' \ -H 'Content-Type: application/json' \ -d '{"url": "https://example.com/invoice.pdf"}'
| Parameter | Type | Description |
|---|---|---|
file | multipart/form-data | PDF, JPG, PNG, or TIFF. Max 50 MB. Use this or url, not both. |
url | string (JSON body) | Publicly accessible document URL. ShapeForge fetches it server-side and follows redirects. |
04 Code Samples
Full integration examples in your language. Replace sk_test_your_key_here with your actual key from the dashboard.
# File upload curl -X POST https://shapeforge-4vqx.polsia.app/api/v1/parse \ -H 'Authorization: Bearer sk_test_your_key_here' \ -F 'file=@/path/to/invoice.pdf' \ | python3 -m json.tool # URL-based parse curl -X POST https://shapeforge-4vqx.polsia.app/api/v1/parse \ -H 'Authorization: Bearer sk_test_your_key_here' \ -H 'Content-Type: application/json' \ -d '{"url": "https://example.com/receipt.pdf"}' \ | python3 -m json.tool
# pip install requests import requests API_KEY = "sk_test_your_key_here" BASE_URL = "https://shapeforge-4vqx.polsia.app" def parse_file(file_path): with open(file_path, "rb") as f: response = requests.post( f"{BASE_URL}/api/v1/parse", headers={"Authorization": f"Bearer {API_KEY}"}, files={"file": f} ) response.raise_for_status() return response.json() def parse_url(doc_url): response = requests.post( f"{BASE_URL}/api/v1/parse", headers={"Authorization": f"Bearer {API_KEY}"}, json={"url": doc_url} ) response.raise_for_status() return response.json() # Usage result = parse_file("invoice.pdf") print(result["document_type"]) # "invoice" print(result["extracted_fields"]) # {"total_amount": {"value": "$1,200.00", "confidence": 0.97}}
// Node.js 18+ (native fetch + FormData) import { readFileSync } from 'fs'; import { FormData, Blob } from 'node:buffer'; const API_KEY = 'sk_test_your_key_here'; const BASE_URL = 'https://shapeforge-4vqx.polsia.app'; // File upload async function parseFile(filePath) { const form = new FormData(); form.append('file', new Blob([readFileSync(filePath)]), filePath); const res = await fetch(`${BASE_URL}/api/v1/parse`, { method: 'POST', headers: { Authorization: `Bearer ${API_KEY}` }, body: form }); if (!res.ok) throw new Error(`API error ${res.status}: ${await res.text()}`); return res.json(); } // URL-based parse async function parseUrl(docUrl) { const res = await fetch(`${BASE_URL}/api/v1/parse`, { method: 'POST', headers: { Authorization: `Bearer ${API_KEY}`, 'Content-Type': 'application/json' }, body: JSON.stringify({ url: docUrl }) }); if (!res.ok) throw new Error(`API error ${res.status}: ${await res.text()}`); return res.json(); } // Usage const result = await parseFile('invoice.pdf'); console.log(result.document_type); // "invoice" console.log(result.extracted_fields); // { total_amount: { value: "$1,200.00", confidence: 0.97 } }
05 Response Format
All responses are application/json. Here's a full annotated example from a parsed invoice:
{
"document_type": "invoice", // invoice | receipt | contract | form | report
"extracted_fields": {
"invoice_number": { "value": "INV-2024-0042", "confidence": 0.99 },
"vendor_name": { "value": "Acme Corp", "confidence": 0.97 },
"issue_date": { "value": "2024-11-15", "confidence": 0.96 },
"due_date": { "value": "2024-12-15", "confidence": 0.95 },
"subtotal": { "value": "$1,000.00", "confidence": 0.98 },
"tax": { "value": "$200.00", "confidence": 0.97 },
"total_amount": { "value": "$1,200.00", "confidence": 0.99 }
}, // confidence: 0–1.0, higher = more certain
"tables": [
{
"name": "line_items",
"headers": ["Description", "Qty", "Unit Price", "Amount"],
"rows": [
["Widget A", "5", "$100.00", "$500.00"],
["Widget B", "5", "$100.00", "$500.00"]
]
}
],
"raw_text": "INVOICE\nInvoice #: INV-2024-0042\n...",
"metadata": {
"page_count": 1,
"file_name": "invoice.pdf",
"processed_at": "2024-11-20T14:32:00Z"
},
"sandbox": true, // false when using sk_live_ keys
"upgrade_url": "https://shapeforge-4vqx.polsia.app/#pricing"
}
Field reference
06 Error Codes
ShapeForge uses standard HTTP status codes. Error responses include an error field with a human-readable message.
| Status | Code | Meaning |
|---|---|---|
| 200 | OK | Document parsed successfully. |
| 400 | Bad Request | Missing file/url, unsupported format (only PDF, JPG, PNG, TIFF), or file exceeds 50 MB. |
| 401 | Unauthorized | Missing or invalid Authorization header. Check your key and Bearer format. |
| 402 | Payment Required | Monthly quota exceeded. Response includes upgrade_url to upgrade your plan. |
| 429 | Too Many Requests | Rate limit hit. Back off and retry after a short delay. |
| 500 | Server Error | Something went wrong on our end. Retry once — if it persists, contact support. |
{
"error": "Monthly quota exceeded",
"upgrade_url": "https://shapeforge-4vqx.polsia.app/#pricing"
}
07 Sandbox vs Live
ShapeForge provides two environments so you can integrate without incurring costs or processing real documents during development.
| Feature | Sandbox (sk_test_) | Live (sk_live_) |
|---|---|---|
| Cost | Free | Counts against quota |
| Document processing | Returns mock fixtures | Real AI parsing |
| Response | Deterministic (same every time) | Varies by document |
| Rate limit | Unlimited | Tier-based (see below) |
| Response header | X-ShapeForge-Mode: sandbox | X-ShapeForge-Mode: live |
sandbox field in response | true | false |
sk_test_. Never commit either key to source control. Use environment variables: SHAPEFORGE_API_KEY=sk_test_...
08 Rate Limits
Sandbox keys are unlimited. Live keys have monthly document quotas that reset on the 1st of each month.
| Plan | Monthly documents | Price | Best for |
|---|---|---|---|
| Starter | 500 / month | $29/mo | Small apps, early-stage products |
| Growth | 5,000 / month | $99/mo | Production workloads, growing teams |
| Enterprise | Custom | Talk to us | High volume, SLA, dedicated support |
When you exceed your quota, the API returns 402 Payment Required with an upgrade_url in the response body. Your current usage is always visible in the dashboard.
09 Go Live
Ready to process real documents? Two steps:
Go to Pricing and pick the plan that fits your volume. API key activated instantly.
Replace sk_test_ with your sk_live_ key from the dashboard. Same endpoint, same request format — nothing else changes.
Ready to ship?
Get your live API key and start processing real documents in minutes.