---
title: Manage Events subscriptions
description: >-
  Declare Events subscriptions in shopify.app.toml with a topic, actions,
  handle, uri, and optional fields.
source_url:
  html: 'https://shopify.dev/docs/apps/build/events/subscribe'
  md: 'https://shopify.dev/docs/apps/build/events/subscribe.md'
---

# Manage Events subscriptions

**Developer preview:**

Events is in developer preview on the [`unstable`](https://shopify.dev/docs/api/usage/versioning#making-requests-to-an-api-version) API version, available today for a [subset of topics](https://shopify.dev/docs/api/events). Use it for early testing ahead of a stable release and broader topic coverage. For topics not yet supported, use webhooks alongside Events in the same `shopify.app.toml`. As Events expands topic coverage, it will become the primary subscription mechanism.

An Events subscription tells Shopify which resources your app wants to track, which changes on those resources matter, and where to send the delivery.

This page covers subscription configuration and the concepts that determine what qualifies a delivery. To narrow which changes trigger a delivery or shape what each delivery returns, see [Filter Events deliveries](https://shopify.dev/docs/apps/build/events/delivery-filtering) and [Events delivery structure](https://shopify.dev/docs/apps/build/events/delivery-structure).

![Illustration of Events pipeline and how configuration gates deliveries.](https://shopify.dev/assets/assets/images/apps/webhooks-events/events-gates-0S8k7jvM.png)

***

## Requirements

You need Shopify CLI 3.92 or higher to configure Events in `shopify.app.toml`. Run `shopify version` to check your version, and [upgrade Shopify CLI](https://shopify.dev/docs/api/shopify-cli#upgrade-shopify-cli) if needed.

Each topic you subscribe to has a [required access scope](https://shopify.dev/docs/apps/build/authentication-authorization/app-installation/manage-access-scopes). See the [Events reference](https://shopify.dev/docs/api/events) for a full list of supported topics and their required scopes.

***

## Versioning

The `api_version` field in `[events]` controls the GraphQL Admin API version used to validate and run subscription `query` operations:

## shopify.app.toml

```toml
[events]
api_version = "unstable"
```

**Note:**

Events is available only on the [`unstable`](https://shopify.dev/docs/api/usage/versioning#making-requests-to-an-api-version) API version. Use it for early testing ahead of a stable release and broader topic coverage. For all production use cases continue to use [webhooks](https://shopify.dev/docs/apps/build/webhooks).

***

## Subscription fields

Each Events subscription is defined by an `[[events.subscription]]` entry in your `shopify.app.toml` file. Every subscription requires the following fields:

| Field | Purpose |
| - | - |
| `handle` | Unique ID for this subscription (alphanumeric, `_`, `-`, max 50 characters). Included in the delivery payload and headers. |
| `topic` | Capitalized resource name (for example `Product`). See [Topic boundaries](#topic-boundaries). |
| `actions` | One or more of `create`, `update`, `delete`. See [Actions](#actions). |
| `uri` | Delivery destination. HTTPS URL, AWS EventBridge ARN, or Google Pub/Sub URI. |

Additional optional fields are available for [filtering deliveries](https://shopify.dev/docs/apps/build/events/delivery-filtering) and [defining their response structure](https://shopify.dev/docs/apps/build/events/delivery-structure):

| Field | Purpose |
| - | - |
| `triggers` | Field paths that narrow `update` deliveries. If omitted, every change to the topic fires. See [Delivery filtering](https://shopify.dev/docs/apps/build/events/delivery-filtering). |
| `query` | GraphQL operation whose result appears in `data`. See [Delivery structure](https://shopify.dev/docs/apps/build/events/delivery-structure). |
| `query_filter` | Expression evaluated on the query result after `query` runs. See [Delivery filtering](https://shopify.dev/docs/apps/build/events/delivery-filtering). |

***

## Topics

A `topic` names the GraphQL Admin resource your subscription listens to. For example, Events subscriptions on the [`Product`](https://shopify.dev/docs/api/events/unstable/product) topic listen for changes to [`Product`](https://shopify.dev/docs/api/admin-graphql/latest/objects/Product) GraphQL Admin objects.

Some objects don't have their own topic because they only exist as part of another resource. For example, `ProductVariant` doesn't have a separate Events topic. Shopify surfaces `ProductVariant` changes on the `Product` topic. If you need to listen to changes to `ProductVariant`, you would subscribe to `Product`, not a standalone `ProductVariant` topic.

Use the [Events reference](https://shopify.dev/docs/api/events) for the current list of topics and validation behavior when you deploy.

***

## Actions

`actions` lists which lifecycle transitions on the subscribed `topic` can produce a delivery.

* `create` and `delete` apply to the topic entity itself. There's no field-path narrowing for those actions at the subscription level. Shopify matches these actions at the resource create/delete boundary for that `topic`.

* `update` covers changes on the topic entity and, where the model routes them there, on owned children (for example `ProductVariant` fields under `Product`). Optional `triggers` restricts which field paths can qualify an `update`. That mechanism applies only to `update`. See [Delivery filtering](https://shopify.dev/docs/apps/build/events/delivery-filtering).

You can list any combination of `create`, `update`, and `delete`. A subscription that includes `update` alongside `create` or `delete` still uses `triggers` only when deciding which `update` changes qualify.

***

## Example

The following subscription listens for any create, update, or delete on the `Product` topic and delivers to a single endpoint. It uses no `triggers`, `query`, or `query_filter`, so every qualifying change fires a delivery with the base payload.

## Product subscription

##### shopify.app.toml

```toml
[events]
api_version = "unstable"

[[events.subscription]]
handle = "product-updates"

topic = "Product"
actions = ["create", "update", "delete"]

uri = "https://your-app.example.com/events/product"
```

##### {} Response

```json
{
  "topic": "Product",
  "action": "update",
  "handle": "product-updates",
  "fields_changed": [
    "product[id: 'gid://shopify/Product/123'].variants[id: 'gid://shopify/ProductVariant/456'].price"
  ],
  "query_variables": {
    "productId": "gid://shopify/Product/123",
    "variantsId": "gid://shopify/ProductVariant/456"
  }
}
```

***

## Next steps

* [Delivery filtering](https://shopify.dev/docs/apps/build/events/delivery-filtering): Narrow `update` deliveries with `triggers` and gate sends with `query_filter`.
* [Delivery structure](https://shopify.dev/docs/apps/build/events/delivery-structure): Shape `data` with `query` and understand what each delivery contains.

***
