WebSnap API

Screenshot & PDF halaman web — preset device, custom size, PNG/JPG/PDF, auto cleanup disk.
Base URL: origin yang sama dengan UI (contoh http://127.0.0.1:8899). Tanpa autentikasi — jangan diekspos publik tanpa proteksi. Tiga jalur capture: job antrean (file tersimpan), preview sinkron (dikembalikan langsung), dan stream query (kompatibel webss).

Quick start

# 1) PNG full-page, desktop 1280×900
curl -s -X POST localhost:8899/api/preview -H 'Content-Type: application/json' \
  -d '{"url":"example.com","mode":"desktop","format":"png","fullPage":true}' -o shot.png

# 2) PDF lewat job antrean (file tersimpan di disk)
curl -s -X POST localhost:8899/api/jobs -H 'Content-Type: application/json' \
  -d '{"url":"example.com","mode":"desktop","format":"pdf","fullPage":true}' | jq .job.id

# 3) PDF lewat preview sinkron (langsung dikirim)
curl -s -X POST localhost:8899/api/preview -H 'Content-Type: application/json' \
  -d '{"url":"example.com","mode":"desktop","format":"pdf"}' -o page.pdf

# 4) Custom size + JPG lewat query stream
curl -s "localhost:8899/api/screenshot?url=https%3A%2F%2Fexample.com&resX=1440&resY=900&format=jpg&scale=1" -o shot.jpg

Endpoint

MethodPathRespons
POST/api/jobs
Menjalankan capture di belakang antrean. File disimpan di disk; progres bisa dipantau lewat GET /api/jobs/{id}.
JSON `{ job }` (201)
POST/api/preview
Menjalankan capture dan mengembalikan file langsung di respons (tanpa menyimpan permanen untuk PNG/JPG). PDF juga didukung dan dikirim sebagai application/pdf.
Binary PNG/JPG/PDF + header `X-Snapshot-*`
GET/api/screenshot
Semua parameter lewat query string. `url` wajib di-encode dengan encodeURIComponent.
Binary PNG/JPG/PDF
GET/api/jobs
Semua job (terbaru dulu) + status antrean.
JSON `{ jobs, queue, runningJobs, activeCaptures }`
GET/api/jobs/{id}
Status, progres, log, statistik, hasil file.
JSON `{ job }`
POST/api/jobs/{id}/cancel
Job queued langsung dibatalkan; job running berhenti di checkpoint berikutnya.
JSON `{ job }`
DELETE/api/jobs/{id}
Hapus job dari memori sekaligus file hasilnya.
JSON `{ ok: true }`
POST/api/cleanup
Hapus semua file job & preview tanpa menunggu TTL.
JSON `{ ok, removed, storage }`
GET/api/devices
Daftar preset, batas nilai, dan konfigurasi cleanup.
JSON `{ devices, limits, cleanup }`
GET/healthz
Antrean, slot capture aktif, statistik browser bersama, storage, dan konfigurasi cleanup.
JSON status
GET/f/{name}
Menyajikan file hasil (png/jpg/pdf) untuk ditampilkan di browser.
File
GET/d/{name}
Menyajikan file hasil dengan header attachment.
File (attachment)
GET/openapi.json
Dokumen OpenAPI 3.1 seluruh endpoint — bisa diimpor ke Postman/Insomnia.
JSON
GET/docs
Dokumentasi interaktif (halaman ini).
HTML

Parameter

Request body — POST /api/jobs & POST /api/preview

ParameterTipeDefaultKeterangan
url wajibstring—URL target. Tanpa skema otomatis diberi https://. Hanya http/https yang diterima.
modestringdesktopProfil device: desktop, mobile, laptop, desktop4k, iphone, android, tablet, atau custom untuk memakai width/height sendiri.
widthinteger—Lebar viewport saat mode: custom. Rentang 100–3840px.
heightinteger—Tinggi viewport saat mode: custom. Rentang 100–5000px.
scaleFactorinteger1 (custom) / bawaan presetDevice pixel ratio 1–4. Ukuran file PNG/JPG = width×scaleFactor.
isMobilebooleanotomatis (width ≤ 768)Menandai viewport sebagai mobile (touch + userAgent mobile). Hanya relevan untuk mode: custom.
themestringnoneEmulasi prefers-color-scheme: none, light, dark.
formatstringpng (screenshot endpoint: jpg)Format output: png, jpg, atau pdf. PDF tersedia di semua endpoint.
qualityinteger90Kualitas kompresi JPG 40–100. Diabaikan untuk PNG/PDF.
fullPagebooleantrue (screenshot endpoint: false)Ambil seluruh halaman (auto-scroll dulu) atau hanya viewport.
delayinteger1500Jeda tambahan setelah halaman siap, 0–60000 ms. Alias: waitTime.
retryinteger3Jumlah percobaan navigasi 1–5 (strategi: networkidle2 → domcontentloaded → load).
outputstringsnapshotPrefiks nama file (disanitasi). Query di /api/screenshot memakai nama name.

Query string — GET /api/screenshot

ParameterTipeDefaultKeterangan
url wajibstring—URL target. Tanpa skema otomatis diberi https://. Hanya http/https yang diterima.
modestringdesktopProfil device: desktop, mobile, laptop, desktop4k, iphone, android, tablet, atau custom untuk memakai width/height sendiri.
themestringnoneEmulasi prefers-color-scheme: none, light, dark.
formatstringpng (screenshot endpoint: jpg)Format output: png, jpg, atau pdf. PDF tersedia di semua endpoint.
fullPagebooleantrue (screenshot endpoint: false)Ambil seluruh halaman (auto-scroll dulu) atau hanya viewport.
waitTimeinteger—Alias delay (kompatibel webss).
outputstringsnapshotPrefiks nama file (disanitasi). Query di /api/screenshot memakai nama name.
viewportstringdesktopPreset kompatibel webss: desktop = 1280×900, mobile = 390×844.
resXinteger—Lebar output kompatibel webss (100–3840). Dipakai bersama resY, default skala 1x.
resYinteger—Tinggi output kompatibel webss (100–5000).
scaleinteger1Device pixel ratio saat memakai resX/resY. Set 1 agar ukuran file persis resX×resY.
namestringpreviewAlias output untuk /api/screenshot.

Profil device

KeyLabelViewport
desktopDesktop1280×900 @1x
mobileMobile390×844 @3x · touch
laptopLaptop1920×1080 @1x
desktop4kDesktop 4K3840×2160 @1x
iphoneiPhone 15 Pro Max430×932 @3x · touch
androidAndroid Pixel 8412×915 @3x · touch
tabletiPad Pro1024×1366 @2x · touch
customCustom sizepakai width × height (100–3840 × 100–5000)

Contoh

POST /api/jobs
curl -s -X POST localhost:8899/api/jobs -H 'Content-Type: application/json' \
  -d '{"url":"https://news.ycombinator.com","mode":"desktop","format":"pdf","fullPage":true}'
POST /api/preview
curl -s -X POST localhost:8899/api/preview -H 'Content-Type: application/json' \
  -d '{"url":"example.com","mode":"custom","width":1440,"height":900,"format":"jpg"}' -o shot.jpg
GET /api/screenshot
curl -s "localhost:8899/api/screenshot?url=https%3A%2F%2Fexample.com&resX=390&resY=844&format=jpg" -o shot.jpg

Header respons

HeaderIsi
X-Snapshot-SizeUkuran file hasil dalam byte
X-Snapshot-ElapsedDurasi capture dalam ms
X-Snapshot-ViewportViewport CSS yang dipakai (widthxheight)
X-Snapshot-BlockedJumlah request iklan/tracker yang diblokir
X-Snapshot-Clipped1 bila halaman dipotong karena terlalu tinggi
X-Snapshot-Browserreused / launched — apakah browser bersama dipakai ulang
X-Snapshot-Request-IdID permintaan, cocok dengan log server

Kode error

KodeArti
400Parameter tidak valid (URL kosong, ukuran di luar rentang, format salah)
404Job atau file tidak ditemukan
409Job sudah selesai/dibatalkan sehingga tidak bisa dibatalkan lagi
413PDF hasil lebih besar dari MAX_SYNC_PDF_BYTES pada jalur sinkron — pakai POST /api/jobs
500Capture gagal (navigasi error, halaman menolak, renderer crash, render melebihi batas keras)
503Antrean penunggu sinkron penuh (MAX_SYNC_WAITERS); respons berisi header Retry-After
504Permintaan sinkron melebihi PREVIEW_TIMEOUT_MS

Catatan operasional

Variabel lingkungan

VariabelDefaultFungsi
PORT8899Port HTTP service
HOST0.0.0.0Interface bind
SNAPSHOT_DIR./snapshotsFolder output job (dan subfolder preview/)
MAX_CONCURRENT_CAPTURES1Jumlah capture bersamaan (job + preview berbagi slot). Alias lama: CONCURRENCY
MAX_JOBS40Job yang disimpan di memori/disk sebelum yang terlama dihapus
MAX_SYNC_WAITERS20Panjang antrean penunggu permintaan sinkron sebelum 503
PREVIEW_TIMEOUT_MS55000Batas durasi capture sinkron
MAX_SYNC_HEIGHT4000Tinggi maksimum (CSS px) untuk PNG/JPG pada jalur sinkron; 0 = tanpa batas
MAX_SYNC_PDF_BYTES41943040Ukuran maksimum PDF pada jalur sinkron (byte)
MAX_FULLPAGE_HEIGHT32000Tinggi maksimum hasil full-page (CSS px). Lebih tinggi dari ini akan dipotong; 0 = tanpa batas
JOB_TIMEOUT_MS240000Watchdog job antrean — job yang lewat batas dihentikan
RENDER_TIMEOUT_MS120000Batas keras tahap render PDF/screenshot pada job
BROWSER_IDLE_MS90000Tutup Chromium bersama setelah idle selama ini
CHROME_PATHautoPath Chromium (kosong = deteksi otomatis / bundled)
FILE_TTL_MINUTES360TTL file job; 0 = nonaktif
PREVIEW_TTL_MINUTES360TTL file preview; 0 = nonaktif
MAX_STORAGE_MB1500Kuota total folder snapshot; kelebihan dihapus dari yang terlama
CLEANUP_INTERVAL_MINUTES15Interval putaran auto cleanup
PREVIEW_KEEP60Jumlah file preview terbaru yang dipertahankan sebelum TTL habis