# Connect Temporal Cloud

Canonical URL: https://docs.fuse.init.inc/integrations/temporal/setup

Create a Temporal Cloud service-account API key and submit it to Init for Cloud Ops namespace management.



## Before you start [#before-you-start]

Temporal uses **customer bearer credentials**. Init binds one API key to **one Temporal Cloud account** discovered during Connect. There is no Init platform OAuth app and no generic HTTP proxy for Temporal hosts.

This integration covers **Temporal Cloud Ops** (control-plane HTTP) only—account discovery, regions, namespaces, and async operations. It does **not** run Workflows/Activities (those use gRPC namespace endpoints) and does not support self-hosted Temporal.

Cloud Ops is in **Public Preview**. Init pins `temporal-cloud-api-version: v0.18.0` on every request. Version bumps require an explicit contract review.

**Connection admin/user** creates a service-account API key in Temporal Cloud and submits the key to Init.

You need:

* Permission to create service accounts and API keys in the Temporal Cloud account.
* RBAC roles that cover the Init actions you will run (account/namespace read vs write).
* A disposable namespace naming prefix for mutation testing; never point write validation at production namespaces.

## Configure the provider [#configure-the-provider]

### Create a service-account API key (**Connection admin/user**) [#create-a-service-account-api-key-connection-adminuser]

1. In Temporal Cloud, create or select a **service account** for machine identity (prefer service accounts over personal user keys).
2. Assign least-privilege **RBAC roles** for that account—Temporal permissions are roles, not OAuth scopes. Grant account-level read for discovery; grant namespace write only when callers need create/update/delete.
3. Create an **API key** for the service account and copy it once. Store it securely; Temporal may not show the full key again.
4. Confirm the account can call Cloud Ops over HTTPS at `https://saas-api.tmprl.cloud`.

There is no custom API origin to configure. Init always calls `https://saas-api.tmprl.cloud` and always sends `temporal-cloud-api-version: v0.18.0`.

Namespace names must match Temporal rules (lowercase alphanumeric with hyphens; length 2–39). Prefer a dedicated test prefix for writes.

## Connect to Init [#connect-to-init]

**Connection admin/user** starts a Temporal Connect session and submits:

| Field     | Required | Notes                                               |
| --------- | -------- | --------------------------------------------------- |
| `api_key` | Yes      | Temporal Cloud API key (service-account preferred). |

Use `temporal_example_key_not_valid` only as an inert documentation placeholder. Never paste a live key into docs.

Init probes `GET /cloud/account`, stores the key in Vault, and persists only safe account id, API version, and fixed origin metadata outside Vault.

## Permissions [#permissions]

Temporal access is **RBAC**, not OAuth scopes. Every Init action has empty `requiredScopes`; the key’s roles decide what succeeds.

| Capability        | Typical Temporal access | Init actions                             |
| ----------------- | ----------------------- | ---------------------------------------- |
| Read account      | Account read            | `account.get`                            |
| List regions      | Account/region read     | `regions.list`                           |
| Read namespaces   | Namespace read          | `namespaces.list`, `namespaces.get`      |
| Read operations   | Operation read          | `operations.get`                         |
| Write namespaces  | Namespace write         | `namespaces.create`, `namespaces.update` |
| Delete namespaces | Namespace delete        | `namespaces.delete`                      |

`namespaces.create` enables **API-key auth** on the new namespace and sets lifecycle delete protection. Create/update/delete are not exposed over MCP.

Mutations are **asynchronous**: Init maps the Fuse idempotency key to Temporal’s `asyncOperationId` and returns the operation handle immediately. Callers must poll `operations.get` until fulfillment—Init does not poll internally.

`namespaces.update` requires the current `resource_version` and sends a **full preserved namespace spec** (not a partial patch). Stale versions fail with conflict semantics—re-read, then retry.

`namespaces.delete` requires confirmation `"DELETE"` plus the current `resource_version`. Deletion is permanent for that namespace; disable delete protection first when it is enabled.

Init does **not** offer a generic proxy to `saas-api.tmprl.cloud`. Callers use the typed actions only.

## Verify the connection [#verify-the-connection]

1. Complete Connect and confirm the connection is active.
2. Run Init’s connection test (`GET /cloud/account`) or a safe read such as `account.get` / `regions.list`.
3. Success looks like Temporal accepting the bearer key for the bound account without `401`/`403`, with the connection showing account metadata and API version `v0.18.0`.

Connection testing proves account **read**. Namespace writes require write RBAC and should be validated only against disposable namespaces under a controlled prefix.

## Rotate or revoke access [#rotate-or-revoke-access]

1. Create a new service-account API key with the same least-privilege roles (overlap rotation: keep the old key valid until Connect succeeds with the new one).
2. Reconnect in Init with the new `api_key`.
3. Revoke or delete the previous key in Temporal Cloud.

If a key is exposed, revoke it immediately, then reconnect.

## Troubleshooting [#troubleshooting]

| Symptom                        | What to check                                                                                                |
| ------------------------------ | ------------------------------------------------------------------------------------------------------------ |
| `401` Unauthorized             | Key revoked, mistyped, or not a Cloud Ops API key.                                                           |
| `403` Forbidden                | Service account RBAC lacks the role for that action.                                                         |
| Version / preview errors       | Init pins `v0.18.0`; Cloud Ops Public Preview changes may need a contract bump.                              |
| Namespace name rejected        | Name must be lowercase, 2–39 chars, matching Temporal naming rules.                                          |
| Update conflict / `409`        | `resource_version` is stale; re-read the namespace and retry with the new version and full preserved spec.   |
| Delete rejected                | Confirmation must be exactly `DELETE`; include current `resource_version`; disable delete protection if set. |
| Mutation returned before ready | Poll `operations.get` with the returned `async_operation_id`; Init does not wait for completion.             |
| Proxy / custom host errors     | Temporal has no generic proxy allowlist; use typed actions only.                                             |
| Workflow / gRPC confusion      | This pack is Cloud Ops HTTP only—workflow execution uses separate namespace endpoints.                       |

