Sonic OCR API Documentation
Complete reference for authenticating, dispatching documents, and integrating the Sonic OCR API.
Production Base URL: https://ocr.ashuchoudhury.in
Model Identifier: sonic-ocr-1
Authentication
Authenticate every request by passing your API key in the standard Authorization header:
Authorization: Bearer YOUR_API_KEY
API keys can be restricted to specific server IP addresses from your dashboard for production security.
POST /v1/ocr
Extracts text from an image (JPEG, PNG or WebP, up to 15 MB).
Method 1: Multipart File Upload (Recommended)
curl -X POST https://ocr.ashuchoudhury.in/v1/ocr \ -H "Authorization: Bearer YOUR_API_KEY" \ -F "[email protected]"
Method 2: Base64 JSON
curl -X POST https://ocr.ashuchoudhury.in/v1/ocr \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{"image": "data:image/jpeg;base64,/9j/4AAQSkZJRg..."}'
Response (200 OK)
{
"id": "ocr_8fK29m1a7b4c9e01df23",
"object": "ocr.result",
"created": 1793548900,
"model": "sonic-ocr-1",
"text": "GOVERNMENT OF ASSAM\nDEPARTMENT OF HEALTH SERVICES\nBIRTH CERTIFICATE\nName: Ashraful Golam Choudhury\nRegistration No: 0392238",
"processing_ms": 1820
}
Python Integration
import requests
response = requests.post(
"https://ocr.ashuchoudhury.in/v1/ocr",
headers={"Authorization": "Bearer YOUR_API_KEY"},
files={"file": ("document.jpg", open("document.jpg", "rb"), "image/jpeg")},
timeout=60,
)
response.raise_for_status()
print(response.json()["text"])
Node.js / TypeScript Integration
import fs from "fs";
const fileBuffer = fs.readFileSync("document.jpg");
const formData = new FormData();
formData.append("file", new Blob([fileBuffer], { type: "image/jpeg" }), "document.jpg");
const res = await fetch("https://ocr.ashuchoudhury.in/v1/ocr", {
method: "POST",
headers: { Authorization: "Bearer YOUR_API_KEY" },
body: formData,
});
const data = await res.json();
console.log(data.text);
PHP Integration
$curl = curl_init();
curl_setopt_array($curl, [
CURLOPT_URL => 'https://ocr.ashuchoudhury.in/v1/ocr',
CURLOPT_RETURNTRANSFER => true,
CURLOPT_POST => true,
CURLOPT_HTTPHEADER => ['Authorization: Bearer YOUR_API_KEY'],
CURLOPT_POSTFIELDS => ['file' => new CURLFile('document.jpg', 'image/jpeg', 'document.jpg')],
CURLOPT_TIMEOUT => 60
]);
$response = json_decode(curl_exec($curl), true);
curl_close($curl);
echo $response['text'];
GET /v1/usage
Returns live quota and consumption details for your account.
{
"used_today": 12,
"daily_limit": 10000,
"used_this_month": 340,
"monthly_limit": 300000,
"rate_limit_per_minute": 60,
"plan_expires_on": "2027-12-31",
"status": "active"
}
Rate Limits & Headers
Every response returns live rate limit and quota headers:
X-RateLimit-Limit: 60 X-RateLimit-Remaining: 59 X-Quota-Limit: 10000 X-Quota-Remaining: 9850 X-Monthly-Quota-Remaining: 298500
Note: For Unlimited / VIP accounts, quota headers return unlimited.
HTTP Status Codes
| Status | error.type | Meaning |
|---|---|---|
| 200 | — | Success. Extracted text returned in text. |
| 400 | invalid_request | Missing file field or malformed request body. |
| 401 | authentication_error | Missing or invalid Bearer API key. |
| 403 | permission_error / plan_expired / ip_not_allowed | Account not active, plan expired, or client IP not whitelisted. |
| 413 | payload_too_large | Image exceeds 15 MB limit. |
| 415 | unsupported_media_type | Only JPEG, PNG and WebP images are accepted. |
| 429 | rate_limit_exceeded / quota_exceeded | Per-minute RPM or daily/monthly quota reached. See Retry-After. |
| 503 | engine_busy / maintenance | Temporary engine overload or maintenance. Retry with backoff. |