CDN Deployment
The CDN is Comvi’s production read path. When you publish a project, translations become JSON files at predictable URLs on Cloudflare’s global edge — this is where your apps should fetch them in production.
URL format
Section titled “URL format”Every published bundle is one JSON file per (language, namespace) pair. The default namespace is served at the project root; all other namespaces sit under a folder named after the namespace:
https://cdn.comvi.io/<distribution-token>/<language>.json # default namespacehttps://cdn.comvi.io/<distribution-token>/<namespace>/<language>.json # any other namespaceExamples for a project with token abc123:
https://cdn.comvi.io/abc123/en.json # default namespace, Englishhttps://cdn.comvi.io/abc123/checkout/fr.json # checkout namespace, Frenchhttps://cdn.comvi.io/abc123/emails/pt-BR.json # emails namespace, Brazilian PortugueseThe distribution token is project-scoped. Find it under Settings → Content Deploy in the dashboard.
Bundle shape
Section titled “Bundle shape”Each file is a flat JSON map from key to value:
{ "greeting": "Hello, {name}!", "nav.home": "Home", "nav.settings": "Settings"}Responses are served compact (no pretty-printing), gzip/brotli compressed, with Content-Type: application/json. Any i18n library that can load a JSON resource from a URL can consume them — see Consume Translations.
The publish pipeline
Section titled “The publish pipeline”Clicking Publish (or writing the API equivalent) triggers a worker job that:
- Builds a manifest — one file per selected
(language, namespace), filtered by your configured status filter - Uploads the files to object storage (Cloudflare R2), in parallel with retries
- Deletes stale files that were in the previous snapshot but are not in this one
- Invalidates the Cloudflare edge cache for every affected URL
- Updates the deployment record and notifies connected dashboard clients
The whole thing is typically done in a few seconds. You do not need to manage cache headers, URLs, or versions — the platform owns the full lifecycle.
sequenceDiagram participant U as User participant P as Platform API participant S as R2 Storage participant C as CDN Edge participant D as Dashboard U->>P: Click Publish Note over P: Build per-namespace per-language bundles P->>S: Upload bundles P->>C: Invalidate cache keys P->>D: Send deploy status update P-->>U: Publish complete
Manual vs auto-deploy
Section titled “Manual vs auto-deploy”Comvi publishes in two modes, both writing to the same CDN:
| Mode | Trigger | Delay |
|---|---|---|
| Manual | You click Publish | Runs immediately |
| Auto (if enabled) | Any translation edit, import, or status change | Debounced: 30 s after the last edit, capped at 5 min total |
Auto-deploy batches a burst of edits into one publish. Every new edit pushes the scheduled deploy forward by 30 seconds, up to a hard ceiling of 5 minutes from the first edit in the burst. This means a single typo fix doesn’t redeploy the world, but a long edit session also can’t starve the deploy forever.
Manual publish always wins: if you click Publish while an auto-deploy is pending, the auto-deploy is cancelled and the immediate job runs instead.
CDN settings
Section titled “CDN settings”Under Settings → Content Deploy you control what is deployed:
| Setting | Effect |
|---|---|
| Enabled | Master switch. If off, publish is a no-op (the dashboard still accepts the click). |
| Languages | Subset of project languages to include. Default: all. |
| Namespaces | Subset of namespaces to include. Default: all. |
| Status filter | Which translation statuses to include. Default: all statuses if nothing is selected. Select only Translated to keep drafts out of production. |
| Format | Default json. Other formats (e.g. i18next-v4 compatible shape) available for compatibility with third-party loaders. |
The status filter is the most important setting in practice. See Translation Lifecycle for what each status means.
Monitoring deployments
Section titled “Monitoring deployments”Each publish records a result you can see in the dashboard and via the REST API:
- Status —
success,partial(some files failed but below 5%), orfailed(aborted) - Files uploaded / failed
- Duration
- Warnings — e.g. ICU messages that couldn’t be converted to a legacy format
The last deploy timestamp and result are persisted on the project, so you can tell exactly what is currently on the edge without re-running anything.
Cache invalidation
Section titled “Cache invalidation”Publish invalidates every file it touches. On the next request to any affected URL, users get the fresh bundle. For typical bundle sizes and edge traffic, propagation is a few seconds globally.
If you are debugging a stale read:
- Confirm the CDN setting is Enabled
- Confirm the language and namespace you are fetching are in the CDN settings’ allow-list
- Confirm the value’s status matches the status filter. If no statuses are selected, all statuses are included.
- Bypass your own client cache (the SDK, the browser, and any intermediate CDN in front of your own site will all cache)
Rolling back
Section titled “Rolling back”There is no first-class “rollback to previous snapshot” button today. Because publish rebuilds the manifest from the current database state, the way to roll back is:
- Revert the offending translation values in the dashboard (use the editor’s history to find the previous value)
- Click Publish
This gives you a fully auditable rollback — every change still shows up in history. If you need versioned snapshots for a specific compliance reason, file a request.
Limits
Section titled “Limits”- 5% failure threshold — a deployment with more than 5% of files failing is aborted; the previous snapshot remains live
- Debounce ceiling — auto-deploy waits at most 5 minutes from the first edit in a burst before it runs, regardless of continued edits
- One in-flight deploy per project — a new manual publish is ignored while another is already running
Troubleshooting
Section titled “Troubleshooting”My app reads stale translations
Section titled “My app reads stale translations”Start from the top of the Cache invalidation checklist. The most common cause is the status filter excluding a value that is still Not reviewed.
Publish says “partial” — what now?
Section titled “Publish says “partial” — what now?”A partial deployment means under 5% of files failed, so the publish went through. Open the deploy result in the dashboard to see which files, and why. Typical causes are transient R2 errors — a re-publish usually clears them.
Publish says “failed” — what now?
Section titled “Publish says “failed” — what now?”Above 5% of files failed, and the deploy was aborted. The previous snapshot is still live. Open the deploy result to see error messages. If errors are uniform (e.g. network issues) just retry. If they are format conversion errors (e.g. ICU → i18next-v4), fix the source values and re-publish.
Is there authentication on the CDN URL?
Section titled “Is there authentication on the CDN URL?”Public project CDN URLs are unauthenticated — the token in the URL is the access identifier. Treat tokens as secrets only if your translations themselves are sensitive. For genuinely private content, contact us.