payout.completed

Airbnb paid the host. Sent once per payout, the first time Repull sees it, for payouts dated in the last 14 days. data.payout and data.lines are exactly what GET /v1/channels/airbnb/transactions?payout_id= returns for it, with the same transactionIds, so you can deduplicate across webhooks and reads. The lines' signed amounts sum to data.payout.payout.paidOutAmount. Payouts are found by the automatic refresh (about daily per account) or a POST /v1/channels/airbnb/transactions.

Payload

Every delivery uses the same outer envelope (event, eventId, apiVersion, timestamp, data). Dedupe on eventId — it stays stable across retries and replays, while the X-Repull-Delivery-Id header changes on every attempt.

{
  "event": "payout.completed",
  "eventId": "3f1c9a2e-8b7d-4c6a-9e0f-1a2b3c4d5e6f",
  "apiVersion": "2026-04",
  "timestamp": "2026-05-01T12:34:56.000Z",
  "data": {
    "channel": "airbnb",
    "accountId": "10000001",
    "accountName": "Seaside Stays",
    "payout": {
      "transactionId": "M-O5P2WERXKFVYH",
      "accountId": "10000001",
      "accountName": "Seaside Stays",
      "status": "COMPLETED",
      "type": "Payout",
      "isPayout": true,
      "date": "2026-09-24",
      "currency": "USD",
      "amount": 318.48,
      "grossAmount": null,
      "fees": {
        "hostServiceFee": null,
        "cleaningFee": null
      },
      "payout": {
        "payoutId": "M-O5P2WERXKFVYH",
        "payoutIdSynthetic": false,
        "payoutDate": "2026-09-24",
        "lineIndex": null,
        "paidOutAmount": 318.48
      },
      "confirmationCode": null,
      "reservationId": null,
      "listingId": null,
      "listingName": null,
      "onInactiveListing": false,
      "guestName": null,
      "nights": null,
      "reservationStartDate": null,
      "description": "Account Holder, Checking 0000 (USD)",
      "reference": null,
      "unavailableFields": [
        "taxes",
        "guest_paid_total",
        "original_transaction_id",
        "currency_conversion",
        "management_fee"
      ],
      "syncedAt": "2026-09-25T06:37:12.000Z"
    },
    "lines": [
      {
        "transactionId": "M-O5P2WERXKFVYH:resolution_adjustment:HMMBM4BWTY:1",
        "accountId": "10000001",
        "accountName": "Seaside Stays",
        "status": "COMPLETED",
        "type": "Resolution Adjustment",
        "isPayout": false,
        "date": "2026-09-23",
        "currency": "USD",
        "amount": -250,
        "grossAmount": null,
        "fees": {
          "hostServiceFee": null,
          "cleaningFee": null
        },
        "payout": {
          "payoutId": "M-O5P2WERXKFVYH",
          "payoutIdSynthetic": false,
          "payoutDate": "2026-09-24",
          "lineIndex": 1,
          "paidOutAmount": null
        },
        "confirmationCode": "HMMBM4BWTY",
        "reservationId": "235812",
        "listingId": "1234567890123456789",
        "listingName": "Harbor Loft",
        "onInactiveListing": false,
        "guestName": "Alex Guest",
        "nights": 4,
        "reservationStartDate": "2026-09-02",
        "description": "Resolution adjustment for resolution 17888008062543",
        "reference": "17888008062543",
        "unavailableFields": [
          "taxes",
          "guest_paid_total",
          "original_transaction_id",
          "currency_conversion",
          "management_fee"
        ],
        "syncedAt": "2026-09-25T06:37:12.000Z"
      },
      {
        "transactionId": "M-O5P2WERXKFVYH:reservation:HMB2E9SR9P:1",
        "accountId": "10000001",
        "accountName": "Seaside Stays",
        "status": "COMPLETED",
        "type": "Reservation",
        "isPayout": false,
        "date": "2026-09-24",
        "currency": "USD",
        "amount": 568.48,
        "grossAmount": 672.75,
        "fees": {
          "hostServiceFee": -104.27,
          "cleaningFee": 120
        },
        "payout": {
          "payoutId": "M-O5P2WERXKFVYH",
          "payoutIdSynthetic": false,
          "payoutDate": "2026-09-24",
          "lineIndex": 2,
          "paidOutAmount": null
        },
        "confirmationCode": "HMB2E9SR9P",
        "reservationId": "235907",
        "listingId": "1234567890123456789",
        "listingName": "Harbor Loft",
        "onInactiveListing": false,
        "guestName": "Sam Guest",
        "nights": 3,
        "reservationStartDate": "2026-09-21",
        "description": "Sep 21 – 24, 2026 HMB2E9SR9P",
        "reference": null,
        "unavailableFields": [
          "taxes",
          "guest_paid_total",
          "original_transaction_id",
          "currency_conversion",
          "management_fee"
        ],
        "syncedAt": "2026-09-25T06:37:12.000Z"
      }
    ]
  }
}

Verifying signatures

Every delivery includes a timestamped X-Repull-Signature header of the form t=<unix_ts>,v1=<hex>, where v1 is HMAC-SHA256(signing_secret, `${t}.${raw_body}`). Verify it before processing — see Verify Signatures for full Node.js and Python examples.

Use the raw body

Sign the raw request body exactly as received, not a re-stringified JSON object. Re-serialisation can reorder keys or change whitespace and break the signature.

Tip: Acknowledge with a 2xx status within 10 seconds. Failed deliveries are retried up to 5 times with exponential backoff.Webhook reliability →

AI