Skip to main content

Create a trigger inbox for an app

This tutorial covers the Trigger Inbox API connected to an app using the user’s app connection. It follows the same queue model as Trigger Inbox onboarding, adding connection setup before inbox creation.

Before you begin

  • An access token set as $TOKEN. Token exchange covers how to get one.
  • Your action_key and trigger input field values. Using triggers covers how to find these.
  • A connected app account for the user. Connection flow covers setup. You will retrieve app_key and connection_id in Step 1.

Step 1: Find your app key and connection ID

Creating an inbox for an app needs two values from the Powered by Zapier API, both authenticated with the same $TOKEN as the Trigger Inbox API:
  • app_key: the app’s key, from GET /v2/apps. Accepts the versionless key (e.g. SlackCLIAPI), a slug (e.g. slack), or @latest suffix (e.g. SlackCLIAPI@latest). All resolve to the latest version automatically.
  • connection_id: the ID of the user’s connected account, from GET /v2/authentications.

1. Find the app key

List apps and read the key field. The query parameter narrows the list by app title, but returns partial matches, you may get more than one result. Match the title field to identify the correct app.
curl -s "https://api.zapier.com/v2/apps?query=Slack" \
  -H "Authorization: Bearer $TOKEN" | python3 -m json.tool
Each app has a versionless key and a UUID id:
{
  "data": [
    {
      "id": "81f613aa-c98a-4383-a5fc-195e68647217",
      "key": "SlackCLIAPI",
      "type": "app",
      "title": "Slack"
    }
  ]
}
Use the key (for example, SlackCLIAPI) as your app_key. Replace APP_ID in the next step with the id value from the response.

2. Find the connection ID

List the user’s authentications for your app. Replace APP_ID in the request with the app id from Step 1. Each authentication represents a connected app account, with a UUID id and an app field holding the app’s UUID.
curl -s "https://api.zapier.com/v2/authentications?app=$APP_ID" \
  -H "Authorization: Bearer $TOKEN" | python3 -m json.tool
{
  "data": [
    {
      "type": "authentication",
      "id": "019487c8-6b2a-7c1e-9f3d-2a1b0c4d5e6f",
      "app": "81f613aa-c98a-4383-a5fc-195e68647217",
      "is_expired": false,
      "title": "Slack some.user@example.com"
    }
  ]
}
Match the authentication whose app equals the app id from the previous step, then use its id as your connection_id.
The authentications endpoint requires the app’s UUID (id), not the app_key string. Use the id from Step 1 here, and app_key in the subscription request in Step 2.
Carry these two values into Step 2:
Inbox subscription fieldSourceExample
app_keyGET /v2/appskeySlackCLIAPI
connection_idGET /v2/authenticationsid019487c8-6b2a-7c1e-9f3d-2a1b0c4d5e6f

Step 2: Create the inbox

Replace YOUR_APP_KEY, YOUR_ACTION_KEY, YOUR_CONNECTION_ID, and YOUR_INPUT_KEY/YOUR_INPUT_VALUE with the values from Step 1 and your prerequisites.
curl -s -X POST "https://api.zapier.com/trigger-inbox/api/v1/inboxes" \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "name": "my-slack-inbox",
    "subscription": {
      "app_key": "YOUR_APP_KEY",
      "action_key": "YOUR_ACTION_KEY",
      "connection_id": "YOUR_CONNECTION_ID",
      "inputs": {
        "YOUR_INPUT_KEY": "YOUR_INPUT_VALUE"
      }
    }
  }' | python3 -m json.tool

export INBOX_ID="<id from response>"

Step 3: Wait for active

Poll until the status is active. Initialization typically takes a few seconds. Go to inbox states for an overview of all status transitions.
DELAY=5
while true; do
  STATUS=$(curl -s "https://api.zapier.com/trigger-inbox/api/v1/inboxes/$INBOX_ID" \
    -H "Authorization: Bearer $TOKEN" \
    | python3 -c "import sys,json; print(json.load(sys.stdin)['status'])")
  echo "Status: $STATUS"
  [ "$STATUS" = "active" ] && break
  if [ "$STATUS" = "initialization_failure" ]; then
    echo "Inbox setup failed. Check paused_reason, delete this inbox, and try again."
    exit 1
  fi
  sleep $DELAY
  DELAY=$(( DELAY < 60 ? DELAY * 2 : 60 ))
done

Step 4: Send an event from the connected app

Perform an action in the connected app to produce a trigger event. For example, if you subscribed to Slack new messages, post a message to the monitored channel. The event will appear in the inbox within a few seconds to a few minutes, depending on the trigger type.

Step 5: Lease messages

curl -s -X POST "https://api.zapier.com/trigger-inbox/api/v1/inboxes/$INBOX_ID/messages/lease" \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"lease_seconds": 300, "lease_limit": 10}' | python3 -m json.tool

export LEASE_ID="<lease_id from response>"
Each message in results[] contains the trigger payload in payload. If possible_duplicate_data is true, deduplication was not possible and your processing logic must be idempotent.

Step 6: Acknowledge messages

curl -s -X POST "https://api.zapier.com/trigger-inbox/api/v1/inboxes/$INBOX_ID/messages/ack" \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d "{\"lease_id\": \"$LEASE_ID\"}" | python3 -m json.tool
If processing fails before you acknowledge, let the lease expire. Messages return to the queue automatically and become available to lease again.

Complete script

Complete the Before you begin steps first, then set your variables and run the script:
#!/usr/bin/env bash
# Trigger Inbox — app script
# Prerequisites: TOKEN, APP_KEY, ACTION_KEY, CONNECTION_ID, and INPUTS set
# Usage: export TOKEN="..." APP_KEY="..." ACTION_KEY="..." CONNECTION_ID="..." && bash real-app.sh

set -euo pipefail

BASE_URL="https://api.zapier.com/trigger-inbox/api/v1"

# Replace these with your values from the Discover available triggers page
APP_KEY="${APP_KEY}"
ACTION_KEY="${ACTION_KEY}"
CONNECTION_ID="${CONNECTION_ID}"
# Replace with the required inputs for your trigger (key/value pairs)
INPUTS='{"YOUR_INPUT_KEY": "YOUR_INPUT_VALUE"}'

# 1. Create the inbox
echo "Creating inbox..."
INBOX_ID=$(curl -s -X POST "$BASE_URL/inboxes" \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d "{
    \"name\": \"real-app-inbox-$(date +%s)\",
    \"subscription\": {
      \"app_key\": \"$APP_KEY\",
      \"action_key\": \"$ACTION_KEY\",
      \"connection_id\": \"$CONNECTION_ID\",
      \"inputs\": $INPUTS
    }
  }" | python3 -c "import sys,json; print(json.load(sys.stdin)['id'])")
echo "Inbox ID: $INBOX_ID"

# 2. Wait for active
echo "Waiting for inbox to become active..."
DELAY=5
while true; do
  STATUS=$(curl -s "$BASE_URL/inboxes/$INBOX_ID" \
    -H "Authorization: Bearer $TOKEN" \
    | python3 -c "import sys,json; print(json.load(sys.stdin)['status'])")
  echo "  Status: $STATUS"
  [ "$STATUS" = "active" ] && break
  if [ "$STATUS" = "initialization_failure" ]; then
    echo "Inbox setup failed. Check paused_reason, delete this inbox, and try again."
    exit 1
  fi
  sleep $DELAY
  DELAY=$(( DELAY < 60 ? DELAY * 2 : 60 ))
done

# 3. Send an event from the connected app, then press Enter to continue
echo ""
echo "Inbox is active. Send an event from your connected app, then press Enter."
read -r

# 4. Lease messages
echo "Leasing messages..."
DELAY=5
while true; do
  LEASE_RESPONSE=$(curl -s -X POST "$BASE_URL/inboxes/$INBOX_ID/messages/lease" \
    -H "Authorization: Bearer $TOKEN" \
    -H "Content-Type: application/json" \
    -d '{"lease_seconds": 300, "lease_limit": 10}')

  LEASE_ID=$(echo "$LEASE_RESPONSE" \
    | python3 -c "import sys,json; print(json.load(sys.stdin).get('lease_id') or '')" 2>/dev/null)

  if [ -n "$LEASE_ID" ]; then
    echo "Messages leased:"
    echo "$LEASE_RESPONSE" | python3 -m json.tool
    break
  fi

  echo "  No messages yet, retrying in ${DELAY}s..."
  sleep $DELAY
  DELAY=$(( DELAY < 60 ? DELAY * 2 : 60 ))
done

# 5. Acknowledge
echo "Acknowledging messages..."
curl -s -X POST "$BASE_URL/inboxes/$INBOX_ID/messages/ack" \
  -H "Authorization: Bearer $TOKEN" \
  -H "Content-Type: application/json" \
  -d "{\"lease_id\": \"$LEASE_ID\"}" | python3 -m json.tool

echo ""
echo "Done."

Next steps