---
title: "Ably"
description: "Use Ably for MainSDK real-time updates - API key, main.yaml, channel access, local testing and swapping."
section: "integrations"
canonical: "https://mainsdk.dev/docs/integrations/ably"
updated: "2026-10-28"
---

# Ably

> Use Ably for MainSDK real-time updates - API key, main.yaml, channel access, local testing and swapping.

Canonical: https://mainsdk.dev/docs/integrations/ably · Updated: 2026-10-28

Ably is a hosted real-time messaging service. In a MainSDK app it is a driver behind [`realtime`](https://mainsdk.dev/docs/interfaces/realtime): your server calls `realtime.publish()`, and clients listening with `realtime.subscribe()` get the update. Pick it as an alternative to Pusher when your team already uses Ably.

> **Note:** `realtime` has no spec yet. The keys and calls on this page are provisional and may change when the spec lands.

## Interfaces it serves

### Realtime updates (`realtime`)

- Status: Building for 0.3 · ships as a beta API
- Driver: `ably` (Ably). later
- Docs: https://mainsdk.dev/docs/interfaces/realtime.md

```yaml
realtime:
  driver: ably
```

Swap to another provider: `broadcast`, `local`, `pusher`, `supabase-realtime`.

## Before you start

1. Create an Ably app, one per environment.
2. Create an API key for your server with only the capabilities it needs. Clients should get short-lived tokens, never the API key.

Store the API key in your secrets manager.

## Configure

```yaml title="main.yaml"
realtime:
  driver: ably
```

How the Ably driver takes its API key is not decided yet [TBD]; it will be a `secret:` reference such as `secret:ABLY_API_KEY` (suggested name).

## Use it

```ts title="app/orders/actions.ts"
import { realtime } from "mainsdk";

await realtime.publish(`order:${order.id}`, { status: "shipped" });
```

## Local development and testing

`createTestApp()` from `@mainsdk/testing` runs `realtime` on its in-memory fake, and `chaos.on("realtime", { outage: true })` simulates an outage.

## What MainSDK adds on top

- Channel access checked per user and tenant.
- New broadcasts can go out in stages and pause on error spikes.

See [Real-time updates](https://mainsdk.dev/docs/interfaces/realtime).

## Limits and notes

- `realtime` is listed for phase 1, with no spec yet.
- Keep personal data out of messages; send IDs and statuses.

## Swap to or from it

```yaml title="main.yaml"
realtime:
  driver: pusher   # was ably
```

Broadcast holds no state in the provider, so it swaps with no migration.

## FAQ

**Can clients publish through Ably?** Not through the catalog calls: clients subscribe and your server broadcasts.

## Next

- [Real-time updates](https://mainsdk.dev/docs/interfaces/realtime)
- [Pusher](https://mainsdk.dev/docs/integrations/pusher) and [Supabase](https://mainsdk.dev/docs/integrations/supabase)
