Browse API documentation
Apply for API access

POST /v1/diacritize

Add Persian reading marks without replacing the source.

The diacritization endpoint returns the submitted Persian text, its marked reading form, and explicit operations that point back to Unicode code-point positions in the original string.

POSThttps://api.vowelmarks.com/v1/diacritize

Updated September 15, 2026 · API version 1

Request

Send text containing at least one Persian-script letter. include_ezafe defaults to true. Set it to false when your interface should omit marks introduced specifically for Ezafe while retaining other reading marks.

FieldTypeRequiredDescription
textstringYesPersian text containing at least one Persian-script letter; maximum 6,000 Unicode code points. The complete serialized JSON body must be at most 32 KiB (32,768 bytes).
include_ezafebooleanNoInclude contextual Ezafe operations. Defaults to true.
curl https://api.vowelmarks.com/v1/diacritize \
  -H "Authorization: Bearer $VOWELMARKS_API_KEY" \
  -H "Content-Type: application/json" \
  -H "Idempotency-Key: lesson-42-diacritize" \
  --data '{"text":"کتاب جدید","include_ezafe":true}'

Response

original is the exact parsed JSON string you submitted. marked is produced by adding Arabic-script combining marks to that source. operations lets a renderer apply the same marks without trusting rewritten text.

{
  "request_id": "95b…",
  "engine_version": "vowelmarks-api-v1.2026-08-10",
  "original": "کتاب جدید",
  "marked": "کِتابِ جَدید",
  "operations": [
    { "source_index": 0, "mark": "ِ", "type": "reading" },
    { "source_index": 3, "mark": "ِ", "type": "ezafe" }
  ],
  "usage": {
    "meter": "text", "input_code_points": 9,
    "multiplier": 1, "units": 9,
    "additional_units": 0, "cache_hit": false
  }
}

Index operations correctly

source_index is a Unicode code-point index, not a JavaScript UTF-16 code-unit offset and not a UTF-8 byte offset. Convert with Array.from(text) in JavaScript. ZWNJ, spaces, punctuation, and existing combining marks each retain their own source positions and count toward usage.

const characters = Array.from(result.original);
for (const operation of result.operations) {
  const sourceCharacter = characters[operation.source_index];
  // Attach operation.mark after sourceCharacter.
}

Source-preservation guarantee

A valid operation can add only documented Arabic-script combining marks to an Arabic-script source letter. If engine output changes source letters, punctuation, spacing, ZWNJ, numbers, or embedded English, VowelMarks rejects the generation and charges no usage.

  • Do not normalize original before applying operations.
  • Do not calculate indexes with JavaScript string.length.
  • Treat type as a stable public category, currently reading or ezafe.
  • Do not infer confidence from operation presence; v1 does not publish calibrated confidence scores.