Pricing
Pay per call. No subscription, no minimum, no commitment. Per-page ops
bill the page count (min one page); CSV, archive, data, and the utils
hash/hmac/base64 ops bill per MB of input (min 1 MiB) — the
data/sql engine at a higher tier; image ops bill per
megapixel (min one); QR, barcode, metadata, UUIDs, JWT decode/verify,
and the generate ops are flat per-call; the pipeline bills the sum of its steps. Calls debit your Relaystation
balance — one balance funds cputools and every other Relaystation product.
These are the launch defaults. The live 402 challenge is always authoritative — an unauthenticated POST to any op
returns the exact price for that call before you pay.
PDF /v1/pdf/<op>
| Tool | What it does | Price |
|---|---|---|
| merge | Combine PDFs into one | $0.0010 / page |
| split | Split by ranges or burst to single pages | $0.0010 / page |
| rotate | Rotate pages | $0.0010 / page |
| pages | Delete, reorder, or insert pages | $0.0010 / page |
| watermark | Stamp text on pages | $0.0010 / page |
| form | Fill or flatten PDF forms | $0.0010 / page |
| extract-text | Pull text + structure out of a PDF | $0.0020 / page |
| metadata | Read or set document metadata | $0.0010 flat |
| encrypt | Password-protect a PDF (256-bit AES) | $0.0010 / page |
| decrypt | Remove a PDF password | $0.0010 / page |
| compress | Recompress to shrink a PDF | $0.0010 / page |
| repair | Repair a damaged PDF (diagnose + rewrite) | $0.0010 / page |
| render | Rasterize pages to PNG/JPEG ≤ 40 pages, ≤ 300 DPI | $0.0010 / page |
| ocr | Extract text from a scanned PDF (Tesseract) ≤ 5 pages (synchronous) | $0.0030 / page |
| ocr-searchable | Make a scanned PDF searchable (invisible OCR text layer) ≤ 5 pages (synchronous) | $0.0040 / page |
| from-html | Render HTML → PDF (headless Chromium, sandboxed) static HTML, inline assets; no network/JS | $0.0030 flat |
| from-office | Convert an Office file → PDF (LibreOffice) docx/xlsx/pptx/odt/ods/odp/rtf/txt/csv, ≤ 30 MB | $0.0050 flat |
| images | Extract embedded images → PNGs ≤ 200 images | $0.0010 / page |
| diff | Text-compare two PDFs (unified diff) | $0.0010 / page |
| bookmarks | Read the outline / bookmark tree | $0.0010 flat |
| attachments | List / extract embedded file attachments | $0.0010 flat |
| verify-signatures | Verify digital signatures (structural + digest; no CA store) | $0.0010 flat |
Office /v1/office/<op>
| Tool | What it does | Price |
|---|---|---|
| rescue | Best-effort convert an exotic/legacy office file → PDF (LibreOffice) pages/numbers/key/vsd/vsdx/pub/cdr/fodt/doc/xls/ppt/wpd, ≤ 30 MB | $0.0080 flat |
CSV /v1/csv/<op>
| Tool | What it does | Price |
|---|---|---|
| convert | Convert between csv / tsv / json / ndjson | $0.0002 / MB |
| dedupe | Drop duplicate rows (order-preserving) | $0.0002 / MB |
| select | Keep, drop, or reorder columns | $0.0002 / MB |
Image /v1/image/<op>
| Tool | What it does | Price |
|---|---|---|
| resize | Resize / fit an image (animated GIF/WebP preserved with animated:true) | $0.0003 / MP |
| convert | Convert image format (png/jpeg/webp/avif/…; animated frames preserved with animated:true) | $0.0003 / MP |
| compress | Re-encode at lower quality | $0.0003 / MP |
| rotate | Rotate / flip an image | $0.0003 / MP |
| metadata | Read dimensions / format / EXIF presence | $0.0005 flat |
| crop | Crop a region | $0.0003 / MP |
| blur | Gaussian blur | $0.0003 / MP |
| sharpen | Sharpen | $0.0003 / MP |
| grayscale | Convert to grayscale | $0.0003 / MP |
| exif-strip | Strip EXIF/metadata (auto-orient first) | $0.0003 / MP |
| dominant-color | Get the dominant color | $0.0002 flat |
| composite | Overlay / watermark one image onto another | $0.0003 / MP |
| contact-sheet | Tile images into a thumbnail-grid PNG | $0.0003 / MP |
| ocr | Extract text from an image (Tesseract, 10 languages) | $0.0030 flat |
| from-html | Render HTML → image (headless Chromium screenshot, sandboxed) | $0.0030 flat |
| adjust | Adjust brightness / saturation / hue / lightness / negate / tint | $0.0003 / MP |
| trim | Auto-crop uniform borders | $0.0003 / MP |
| extend | Pad / extend on any side | $0.0003 / MP |
Codes /v1/{qr,barcode,codes/<op>}
| Tool | What it does | Price |
|---|---|---|
| qr | Generate a QR code (PNG/SVG) data ≤ 4096 chars | $0.0002 flat |
| barcode | Generate a 1D barcode (Code128/EAN/UPC/…) data ≤ 4096 chars | $0.0002 flat |
| qr-decode | Read a QR code from an uploaded image | $0.0002 flat |
| color-convert | Convert a color between hex / rgb / hsl | $0.0002 flat |
Utils /v1/utils/<op>
| Tool | What it does | Price |
|---|---|---|
| hash | Hash bytes (sha256/sha512/sha1/md5) | $0.0002 / MB |
| hmac | Keyed HMAC (sha256/sha512/sha1/md5); key never logged | $0.0002 / MB |
| base64 | Base64 encode / decode a string | $0.0002 / MB |
| uuid | Generate v4 UUIDs count ≤ 1000 | $0.0001 flat |
| jwt-decode | Decode a JWT header + payload (no verify) | $0.0001 flat |
| jwt-verify | Verify a JWT signature, alg-pinned; key never logged | $0.0001 flat |
Generate /v1/generate/<op>
| Tool | What it does | Price |
|---|---|---|
| og-image | Render a social-card PNG (satori → sharp) one OG template | $0.0005 flat |
| mock-data | Generate fake rows from a field→type schema (json/csv/ndjson) rows ≤ 1000, fields ≤ 50 | $0.0002 flat |
| invoice | Render an invoice PDF from structured data (pdf-lib) ≤ 100 line items | $0.0002 flat |
| chart | Render a bar / line / pie chart PNG (SVG → sharp) ≤ 50 data points | $0.0002 flat |
| qr-logo | QR code with a logo composited in the center (ECC H) | $0.0002 flat |
| favicon | Favicon set (PNGs) from an image or initials text ≤ 8 sizes | $0.0002 flat |
| placeholder | Placeholder image (dimensions/label text; png or svg) | $0.0002 flat |
| identicon | Deterministic GitHub-style identicon PNG from a seed | $0.0002 flat |
Archive /v1/archive/<op>
| Tool | What it does | Price |
|---|---|---|
| zip | Zip 1+ files into one archive | $0.0002 / MB |
| unzip | Extract a zip to a manifest of entries ≤ 128 MiB uncompressed, ≤ 10000 entries, ratio ≤ 1000:1; encrypted rejected | $0.0002 / MB |
| gzip | Gzip compress / decompress a file (transparent gzip handling for CSV inputs) | $0.0002 / MB |
Data /v1/data/<op>
| Tool | What it does | Price |
|---|---|---|
| filter | Keep rows matching a structured predicate (no formula eval) | $0.0002 / MB |
| sort | Sort rows by one or more columns | $0.0002 / MB |
| groupby | Group rows and aggregate (count/sum/avg/min/max) | $0.0002 / MB |
| join | Join two tables (inner/left/right/outer) | $0.0002 / MB |
| union | Concatenate tables (ordered key-union schema) | $0.0002 / MB |
| profile | Column stats: type, nulls, cardinality, min/max/mean | $0.0002 / MB |
| cast | Coerce column types (string/integer/number/boolean/date) | $0.0002 / MB |
| pivot | Reshape long↔wide (pivot / unpivot) | $0.0002 / MB |
| schema-infer | Infer a JSON Schema or SQL DDL from the data | $0.0002 / MB |
| validate | Check rows against a structured schema | $0.0002 / MB |
| diff | Row-level changeset between two tables | $0.0002 / MB |
| from-xlsx | Parse an Excel file → table (csv/json) | $0.0002 / MB |
| to-xlsx | Write a table → Excel (.xlsx), formula-injection-safe (multi-sheet + styling) | $0.0002 / MB |
| derive | Add computed columns (structured, no formula eval) | $0.0002 / MB |
| fillna | Fill empty cells (value / ffill / bfill / mean / median / mode) | $0.0002 / MB |
| dropna | Drop rows with empty cells | $0.0002 / MB |
| rename | Rename columns | $0.0002 / MB |
| slice | Row slicing / sampling (offset/limit/head/tail/sample) | $0.0002 / MB |
| explode | Unnest an array/list cell into multiple rows | $0.0002 / MB |
| sample | Sample rows (n or fraction; random/head/systematic; reproducible seed) | $0.0002 / MB |
| sql | Query your file with full SQL (sandboxed DuckDB, read-only; parquet in & out) no files/network/extensions; ≤ 25 s; ≤ 128 MiB out | $0.0005 / MB |
Text /v1/text/<op>
| Tool | What it does | Price |
|---|---|---|
| case | Recase text (upper/lower/title/camel/snake/kebab) | $0.0002 / MB |
| slugify | URL-slugify text (strip diacritics, hyphenate) | $0.0002 / MB |
| diff | Unified diff of two strings | $0.0002 / MB |
| apply-patch | Apply a unified diff to a source string (422 on context mismatch) | $0.0002 / MB |
| merge3 | Three-way merge of two changes against a common base (conflict markers on overlap) | $0.0002 / MB |
| count | Count characters / words / lines + reading time | $0.0002 / MB |
| regex-extract | Extract regex matches (ReDoS-guarded; patterns + input bounded) | $0.0002 / MB |
| template | Render a logic-less mustache-subset template (no eval) | $0.0002 / MB |
| markdown-to-html | Markdown → HTML, always whitelist-sanitized | $0.0002 / MB |
| html-to-text | Convert HTML → plain text | $0.0002 / MB |
| sanitize-html | Sanitize HTML against a safe whitelist | $0.0002 / MB |
Pipeline /v1/pipeline
The pipeline runtime composes a chain of
transforms in one call and bills the sum of its steps —
each step at its normal per-op rate — plus a $0 orchestration fee. A
three-step pipeline on a 5 MB file is Σ (step rate ×
5 MiB). An unauthenticated POST returns the exact
summed price as a 402 quote, and a failed step refunds the
whole run.
Limits
- Inputs: inline base64 up to 4 MB, or up to
50 MB by storage reference (mint a presigned upload via
POST /v1/cputools/upload-url). - OCR is synchronous and capped at 5 pages per call —
larger asynchronous OCR jobs are coming. render is
capped at 40 pages and 300 DPI. QR/barcode data
is capped at 4096 characters. uuid is capped at 1000
per call; mock-data at 1000 rows / 50 fields. Over a
cap returns a
422before any charge. - archive/unzip is zip-bomb-guarded — and the rejection
is a feature: a tiny archive that would expand past
128 MiB, an archive over 10000 entries, or a per-entry
compression ratio above 1000:1 is rejected with a
422before any charge, and the expansion is also halted in-flight if the actual output crosses the cap. Encrypted/password-protected zips are rejected; a nested.zipentry comes back as bytes (one level — never recursively extracted). jwt-verify is algorithm-pinned (noalg:nonedowngrade) and never logs your key. - data/sql runs read-only on a sandboxed DuckDB — no
filesystem, network, or extension access, so your query sees only your
file — and is memory-, time- (≤ 25 s), and output-capped
(≤ 128 MiB; a larger result returns
413). data join / union / groupby outputs are byte-capped (the cartesian-blowup guard). pipeline is capped at 10 steps and 128 MiB threaded between steps, and is atomic — a failed step refunds the whole run.
Worked examples
| Job | Math | Total |
|---|---|---|
| 10-page merge | 10 × $0.001 | $0.010 |
| 30-page extract-text | 30 × $0.002 | $0.060 |
| 3-page OCR | 3 × $0.003 | $0.009 |
| 5-page render to PNG | 5 × $0.001 | $0.005 |
| 2 MB csv convert | 2 × $0.0002 | $0.0004 |
| 4-megapixel image resize | 4 × $0.0003 | $0.0012 |
| 3 MB sha256 hash | 3 × $0.0002 | $0.0006 |
| unzip a 5 MB archive | 5 × $0.0002 (compressed input) | $0.0010 |
| 2 MB data groupby | 2 × $0.0002 | $0.0004 |
| 5 MB data/sql query | 5 × $0.0005 (DuckDB worker) | $0.0025 |
| 3-step pipeline on 5 MB | Σ (step rate × 5 MiB) + $0 fee | sum of the steps |
| QR / metadata / UUID / og-image | flat | $0.0002 / $0.001 / $0.0001 / $0.0005 |
One call, one payment
The lodestone is a single HTTPS call carrying the files and an x402 payment authorization — no account, no signup step.
curl -X POST https://api.relaystation.ai/v1/pdf/merge \
-H 'X-Payment: <base64 EIP-3009 auth>' \
-H 'Idempotency-Key: merge-invoices-20260605' \
-H 'Content-Type: application/json' \
-d '{"files":[{"inline":"<base64 pdf>"},{"inline":"<base64 pdf>"}]}' Top up your balance
Pay per call with a per-call x402 payment, or top up with a card via Stripe. One Relaystation balance funds cputools and every other Relaystation product. We absorb the payment-rail fees (Stripe processing, x402 gas) — they never appear in your balance. Sign in to top up via Stripe, or send an x402 payment on any call.