Skip to content

API docs

Everything the website does, your scripts can do: upload a file, ask for a format, wait, download. Five requests, plain JSON over HTTPS.

1. Get a key

Create one on the API keys page. It starts with bck_, is shown once, and acts as your account with your plan's limits. Send it on every request:

Authorization: Bearer bck_…

Keep it secret, like a password. Revoke it on the same page and it stops working at once.

2. Create the file

Say what you are about to upload. kind is image or video, and size_bytes is the file's exact size. The answer holds the file's id and an upload_url, valid for an hour.

export BISACOMPRESS_KEY=bck_…

FILE=$(curl -s https://bisacompress-api.manabisa.com/api/v1/files \
  -H "Authorization: Bearer $BISACOMPRESS_KEY" \
  -H "Content-Type: application/json" \
  -d '{"name":"photo.jpg","kind":"image","size_bytes":'"$(wc -c < photo.jpg)"'}')
# {"file":{"id":"0192…","status":"uploading",…},"upload_url":"https://…"}

FILE_ID=$(echo "$FILE" | jq -r .file.id)
UPLOAD_URL=$(echo "$FILE" | jq -r .upload_url)

3. Upload the bytes

PUT the file to upload_url as it is. This goes straight to storage, so it needs no Authorization header.

curl -s -X PUT --upload-file photo.jpg "$UPLOAD_URL"

4. Start a job

Choose the output format and a preset: small, balanced (the default), or high.

KindFormats
imagewebp, jpeg, avif
videomp4 (H.264), webm (VP9)
JOB_ID=$(curl -s https://bisacompress-api.manabisa.com/api/v1/jobs \
  -H "Authorization: Bearer $BISACOMPRESS_KEY" \
  -H "Content-Type: application/json" \
  -d '{"file_id":"'"$FILE_ID"'","format":"webp","preset":"balanced"}' | jq -r .id)
# the job: {"id":"0192…","status":"queued","progress":0,…}

5. Wait, then download

Ask for the job every second or two. status goes queued → processing (with progress 0–100) → done or failed. When it is done the answer carries a download_url, valid for an hour.

while :; do
  JOB=$(curl -s https://bisacompress-api.manabisa.com/api/v1/jobs/$JOB_ID -H "Authorization: Bearer $BISACOMPRESS_KEY")
  STATUS=$(echo "$JOB" | jq -r .job.status)
  [ "$STATUS" = done ] && break
  [ "$STATUS" = failed ] && { echo "$JOB" | jq -r .job.error; exit 1; }
  sleep 2
done
curl -s -o photo.webp "$(echo "$JOB" | jq -r .download_url)"

Everything else

  • GET /usage: your plan, storage, and how many jobs you have left today.
  • GET /files and GET /jobs: your 100 newest, newest first.
  • DELETE /files/{id}: deletes a file and its result, and gives back the storage. Results are kept until you do.
  • GET /plans: every plan's limits and prices; no key needed.

Limits

PlanPer fileStorageJobs at a timeJobs per 24 h
Free50 MB2 GB325
Pro2 GB100 GB502,000
Max5 GB1 TB100,00010,000

Every key and session also shares a limit of 120 requests a minute. GET /usage always has your current numbers.

Errors

Every error is JSON, {"error":"…"}, with one of these statuses:

400Something in the request is wrong: a missing field, an unknown format, or a format for the other kind.
401The key is missing, revoked, or expired.
402Your plan does not include cloud compression.
403Your storage is full, the file is not yours, or the route needs a signed-in session (API keys cannot manage keys).
404No such file or job on your account.
409The file still has a job in progress, so it cannot be deleted yet.
413The file is larger than your plan allows.
429Too many jobs in progress, the daily job limit, or too many requests. Wait and retry.

Questions: support@manabisa.com.