ResumeJSON

Quickstart

One endpoint, three ways to send a CV. You will have JSON back in about 2.2 seconds.

Authentication

Subscribe on RapidAPI and send your key on every request. RapidAPI handles the metering and the billing; this service checks that the call actually came through it.

To try the parser without a key, use the free browser tool — same endpoint, same model, smaller limits.

x-rapidapi-key: YOUR_KEY
x-rapidapi-host: resumejson-resume-cv-parser-api.p.rapidapi.com

RapidAPI shows the exact x-rapidapi-host for your subscription in the code snippet on the listing. Copy it from there — it is the authoritative value.

A request that reaches the origin without RapidAPI's proxy secret gets 403 not_via_rapidapi. A key that is sent through RapidAPI but is not on an active subscription never reaches us at all: the gateway answers 403 itself, with {"message": "…"} and no error.code.

Three ways to send a resume

1. JSON, when you already have the text

curl -X POST 'https://resumejson-resume-cv-parser-api.p.rapidapi.com/v1/parse' \
  -H 'x-rapidapi-key: YOUR_KEY' \
  -H 'x-rapidapi-host: resumejson-resume-cv-parser-api.p.rapidapi.com' \
  -H 'content-type: application/json' \
  -d '{"text":"Sarah Okonkwo\nStaff Engineer ..."}'

2. Multipart, straight from an upload form

curl -X POST 'https://resumejson-resume-cv-parser-api.p.rapidapi.com/v1/parse' \
  -H 'x-rapidapi-key: YOUR_KEY' \
  -H 'x-rapidapi-host: resumejson-resume-cv-parser-api.p.rapidapi.com' \
  -F 'file=@cv.pdf'

3. Raw bytes, when you are streaming a file through

curl -X POST 'https://resumejson-resume-cv-parser-api.p.rapidapi.com/v1/parse' \
  -H 'x-rapidapi-key: YOUR_KEY' \
  -H 'x-rapidapi-host: resumejson-resume-cv-parser-api.p.rapidapi.com' \
  -H 'content-type: application/pdf' \
  --data-binary @cv.pdf

PDF, DOCX and image types are recognised from the file's own bytes, so an upload labelled application/octet-stream still works. A JPEG, PNG or WebP of the page goes through the same three routes.

Getting the resume back in another language

By default a CV comes back in its own language: an Indonesian CV returns Indonesian job titles. Add output_language and the text values are written in the language you name instead.

curl -X POST 'https://resumejson-resume-cv-parser-api.p.rapidapi.com/v1/parse?output_language=French' \
  -H 'x-rapidapi-key: YOUR_KEY' \
  -H 'x-rapidapi-host: resumejson-resume-cv-parser-api.p.rapidapi.com' \
  -F 'file=@cv.pdf'

Any language the model can write is accepted — there is no fixed list. Send a name (French, Bahasa Indonesia, 日本語) or a code (fr, pt-BR, zh-Hans); a code is expanded for you, and meta.outputLanguage comes back with what was understood, so fr answers "French".

A JSON or multipart body can carry the same value as an output_language field instead. The query string works for all three ways of sending a CV, including raw bytes, which is why it is the one documented here. If you send both, the query string wins.

TranslatedLeft exactly as written
Job titles, the headline, highlights, skills, degrees, fields of study, locations, and the languages spoken with their proficiency wording.Names of people, companies and schools. Emails, phone numbers, URLs. Dates, which are normalised rather than translated.

Translating is not inventing: a field the CV does not state is still null. A value that is not a language — too long, or carrying anything a language name does not — comes back as 400 unsupported_language before the document is read.

Limits

LimitValueWhat happens past it
Upload size20 MB413 too_large
Extracted text60,000 characters413 too_large
Upstream model budget25 s per attempt, 2 retries503 upstream_unavailable with Retry-After
Monthly requestsYour plan's quota, in the table below429 from the RapidAPI gateway, naming the MONTHLY quota. Final until the window resets.
Burst rateSet by the RapidAPI gateway; it sends no header counting it429 {"message": "Too many requests"}. Back off a few seconds and retry; it does not touch the monthly quota.
Resumes per requestOneThere is no bulk or batch endpoint. Send one CV per call and run your own concurrency.
DeliverySynchronousThe parse returns on the same request. There are no webhooks, no callbacks and no job ids to poll.
HandwritingNot supportedThe parser is built for printed pages. A handwritten CV is not refused — it goes to the vision path and comes back looking like any other parse — but its accuracy has never been measured, so it is not promised.

Every response through RapidAPI carries your position against that quota: x-ratelimit-requests-limit, x-ratelimit-requests-remaining, and x-ratelimit-requests-reset in seconds. The window runs from the day you subscribed, not the calendar month. Read x-ratelimit-requests-remaining to warn before the refusal rather than after it.

What it costs

The same rungs the listing meters, on the page you are reading. Billing and metering are RapidAPI's; these are the numbers it charges.

PlanPriceIncludedBilling
Basic$0100 parses a monthA hard cap, so it can never bill you.
Pro$0Pay per use — $0.05 a parseNo monthly fee. You are billed only for the parses you make.
Ultra$291,000 parses a monthOverage beyond the quota rather than a blocked integration. $0.045 a parse past it.
Mega$995,000 parses a monthOverage beyond the quota rather than a blocked integration. $0.018 a parse past it.

Basic is a hard cap and cannot bill you. The paid plans allow overage past the quota rather than blocking a working integration at it; every per-parse overage is in the table above. Subscribe on RapidAPI.

Every error, and what to do about it

Retry the transient one. The rest describe something about the request that a retry will not change.

Every row here still costs you a request. RapidAPI meters at its gateway, on the call rather than on the answer: measured 2026-09-16, a 400 decremented x-ratelimit-requests-remaining by exactly the same one as a 200. That includes the 500s, which are our fault and not yours. What costs nothing is a call the gateway turns away itself — the quota 429 below, and a request to a path the listing does not declare; those come back with no x-ratelimit-* headers at all.

StatusCodeMeaningRetry?
400bad_requestThe request itself could not be read — malformed multipart, or JSON that is not an object.No
400empty_inputNo text field, no file part, or an empty body.No
400unsupported_languageoutput_language was not a language. Send a name like French or a code like fr.No
403not_via_rapidapiThe call did not come through RapidAPI.No
403noneYour subscription is not active — lapsed, cancelled, or never started. RapidAPI sends this, not the parser, so the body is {"message": "…"} with no error.code: branch on the presence of the code, not on the status. Check the subscription on the listing.No — renew or resubscribe
405method_not_allowed/v1/parse is POST only.No
413too_largePast the upload or character limit. The body carries limit.No
415unsupported_typeNot a PDF, DOCX, text or supported image. The body carries supported.No
422unreadable_fileThe file could not be opened: an encrypted or corrupt PDF, or a DOCX that is not a readable zip.No
422not_a_resumeNothing in the document reads as a CV.No
429noneYour plan's monthly request quota is spent: the message names the MONTHLY quota. RapidAPI sends this, not the parser, so the body is {"message": "…"} with no error.code: branch on the message.No — wait for x-ratelimit-requests-reset, or upgrade
429noneToo many requests in a short burst: the body is {"message": "Too many requests"}, also from RapidAPI. It clears on its own.Yes, after a back-off of a few seconds
404not_foundNo endpoint at that path. The parse endpoint is /v1/parse.No
500internalOur fault, and unexpected. The body carries request_id, the same value as the x-request-id header. It counts against your quota like any other call.No — quote the id
500gate_misconfiguredOur fault: the deployment is missing a secret, so it refuses rather than serving paid parses ungated. It counts against your quota like any other call.No — tell support
502upstream_invalidThe model answered with something unusable.Once
503upstream_unavailableThe model is down or rate-limited.Yes, after Retry-After

Stuck on an error the table does not explain? Write to support@tiraisoft.com with the x-request-id, the status and the error.code, or ask on the RapidAPI listing.

Every response to /v1/parse carries an x-request-id header, and a 500 repeats it in the body as request_id. It identifies that one call. Quote it about a parse that came back wrong as well as one that failed — it saves you reproducing anything.

{
  "error": {
    "code": "too_large",
    "message": "That document is 91,204 characters; the limit is 60,000. Send the resume alone, not a bundle.",
    "limit": 60000
  }
}

Reading the response

Two keys: resume is the document, meta is what happened. Every field of resume is documented in the field reference.

meta fieldWhat it tells you
sourcetext, pdf, docx or image — what the bytes actually were. A scanned PDF is pdf, like any other PDF.
readtext if the document had a text layer, vision if the model had to read the pages as images.
charactersHow much text was parsed, or null when read is vision and there was no text layer to count.
outputLanguageThe language you asked for, resolved — send fr and this reads French. null when you asked for none and the CV came back in its own language.
durationMsServer-side time, also sent as the X-Parse-Ms header.