> ## Documentation Index
> Fetch the complete documentation index at: https://docs.kugelaudio.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Dictionaries

> Per-project pronunciation and replacement lists

Custom dictionaries are per-project pronunciation and replacement lists.
Each entry maps a written word to the text or IPA the TTS pipeline should
pronounce instead. Use them for brand names, product names, acronyms, and
domain vocabulary that should sound consistent across requests.

Changes are available to synthesis after the dictionary mutation finishes.
Generation must send the dictionary's `project_id`; omission loads no project
dictionary. The current Python TTS request/session builders do not expose that
field, so use the [raw generation API](/api-reference/tts/generate) (or the
JavaScript one-shot client) for dictionary-backed synthesis.

For the full HTTP contract, field limits, master-key `project_id` rules,
and error codes, see the [Dictionaries API reference](/api-reference/endpoints/dictionaries).

## Create a Dictionary

```python theme={null}
from kugelaudio import KugelAudio

client = KugelAudio(api_key="YOUR_API_KEY")

dictionary = client.dictionaries.create(
    name="Brand names",
    description="Product and company names",
    language="en",
)

print(dictionary.id)
```

## Manage Dictionaries

```python theme={null}
# List every dictionary in the project
dictionaries = client.dictionaries.list()

# Fetch one
dictionary = client.dictionaries.get(dictionary.id)

# Update name / description / language / is_active (only provided fields change)
dictionary = client.dictionaries.update(
    dictionary.id,
    description="Updated description",
    is_active=False,
)

# Delete a dictionary (cascades to its entries)
client.dictionaries.delete(dictionary.id)
```

<Note>
  Every dictionary and entry method accepts a keyword-only `project_id`. It is
  required **only** for master-key callers acting on a specific project; with a
  normal project-scoped API key, omit it.
</Note>

## Add and Manage Entries

Use `replacement` for normal spelling-based fixes. Use `ipa` when you need
an exact phonetic pronunciation; IPA takes precedence over `replacement`.

```python theme={null}
created_entry = client.dictionaries.entries.add(
    dictionary.id,
    word="Postgres",
    replacement="post-gres",
)

page = client.dictionaries.entries.list(
    dictionary.id,
    search="post",
    limit=50,
)

for entry in page.entries:
    print(f"{entry.word} → {entry.replacement}")

client.dictionaries.entries.update(
    dictionary.id,
    page.entries[0].id,
    replacement="postgres",
)

client.dictionaries.entries.delete(dictionary.id, page.entries[0].id)
```

## Atomic Bulk Sync

`replace_all` upserts every entry in one transaction and deletes entries
currently in the dictionary whose `word` is not in the payload. Use it to
sync from a CMS, PIM, or internal glossary.

<Warning>
  `replace_all` is intentionally destructive for omitted words. Only call it
  with the complete desired contents of that dictionary.
</Warning>

```python theme={null}
result = client.dictionaries.entries.replace_all(
    dictionary.id,
    entries=[
        {"word": "Postgres", "replacement": "post-gres"},
        {"word": "Kubernetes", "replacement": "koo-ber-net-eez"},
    ],
)

print(f"upserted={result.upserted} deleted={result.deleted}")
```

## Generation Limitation

`dictionary_ids` alone is not enough: the API requires `project_id` for both
the default active dictionaries and an explicit selection. Because the Python
generation builders cannot send `project_id`, use the [raw generation
API](/api-reference/tts/generate) for dictionary-backed synthesis.

## Next steps

* [Types & Errors](/sdks/python/types) — `Dictionary`, `DictionaryEntry`, and result models
* [Text Normalization](/sdks/python/normalization) — how normalization interacts with dictionaries
