# Webhooks API

## Aurinko Webhooks API

Webhooks allow your apps to receive real-time updates from the Aurinko platform. By registering a webhook URL, you can get notified when specific events happen.

Aurinko retrieves data by either subscribing to provider resources or using a poller for periodic updates. For certain resources, such as [Google Pub/Sub](https://docs.aurinko.io/unified-apis/webhooks-api/configuring-pub-sub-for-gmail-api-webhooks), manual configuration is required to ensure the provider’s data is successfully delivered to Aurinko.

### Aurinko account setup

***

First, create your account in the [Aurinko portal](https://app.aurinko.io/), then follow the guide to [get Your Developer API Keys](https://docs.aurinko.io/getting-started/get-your-developer-api-keys).

### Setting up a Webhook

***

1. Prepare an endpoint URL on your server.
2. Ensure your endpoint can handle POST requests with [authentication](https://docs.aurinko.io/unified-apis/webhooks-api/authentication) and supports the initial [url verification step.](#notification-url-verification)
3. Provide your endpoint to our system through the [event subscription](https://apirefs.aurinko.io/#tag/Webhooks/operation/subscribe) process.

### Authentication

***

Webhooks are secured using a shared secret that is used to generate a signature. The signature is sent in the HTTP header of each request, allowing you to verify the authenticity. The signing secret can be found on your app's dashboard page.

For more details, see the documentation: [Authentication](https://app.gitbook.com/o/4jzD0cdc8TPZbg83hQxP/s/0ua36KLVlbUN5bA2bgiq/~/edit/~/changes/zleGiPK3UvcThb1dxgK7/unified-apis/webhooks-api/authentication).

### Notification URL Verification

***

When you register a new webhook subscription with Aurinko, the platform performs a Notification URL Verification to ensure that your server is ready to receive and process events. Validate this request as any other requests by [authentication](#authentication). See the documentation for more details: [Notification URL Verification](https://app.gitbook.com/o/4jzD0cdc8TPZbg83hQxP/s/0ua36KLVlbUN5bA2bgiq/~/edit/~/changes/zleGiPK3UvcThb1dxgK7/unified-apis/webhooks-api/notification-url-verification).

### API Resources

***

The Aurinko webhook events are associated with API resources (parts of the API) and subscriptions are created for those resources. Here is the list of available API resources:

* */email/messages* - events representing mailbox changes.
* */email/tracking* - events representing email tracking changes.
* */calendars/primary/events, /calendars/{calId}/events* - events representing calendar changes.
* */contacts* - events representing address book changes.
* */tasklists/default/tasks, /tasklists/{tlId}/tasks* - events representing todo item changes.
* */booking/{bookingId}* - events representing booking lifecycle changes.

### Subscribing

***

To create a new subscription POST a resource and a notification url to \
the [subscriptions endpoint](https://apirefs.aurinko.io/#tag/Webhooks/operation/subscribe):

#### Email messages

```bash
curl -H 'Authorization: Bearer <access token>'
    -X POST https://api.aurinko.io/v1/subscriptions
    -d '{
        "resource": "/email/messages",
        "notificationUrl": "https://myserver/pushEvents"
}'  
```

*Response:*

```json
{
    "id": "87665448354",
    "resource": "/email/messages", 
    "notificationUrl": "https://myserver/pushEvents" 
}  
```

#### Email tracking

```bash
curl -H 'Authorization: Bearer <access token>'
    -X POST https://api.aurinko.io/v1/subscriptions
    -d '{
        "resource": "/email/tracking",
        "notificationUrl": "https://myserver/pushEvents"
}'
```

{% hint style="info" %}
For more details on the email tracking fields (<mark style="color:red;">`opens`</mark>, <mark style="color:red;">`threadReplies`</mark>, <mark style="color:red;">`trackOpensAfterSendDelay`</mark>, <mark style="color:red;">`context`</mark>, <mark style="color:red;">`customDomainAlias`</mark>) and how to include them when sending messages, see the Email Tracking Options section in the [Email API documentation.](https://docs.aurinko.io/unified-apis/email-api#email-tracking-options)
{% endhint %}

#### Calendar events

```bash
curl -H 'Authorization: Bearer <access token>'
    -X POST https://api.aurinko.io/v1/subscriptions
    -d '{
        "resource": "/calendars/primary/events",
        "notificationUrl": "https://myserver/pushEvents"
}'
```

or for a specific calendar:

```bash
curl -H 'Authorization: Bearer <access token>'
    -X POST https://api.aurinko.io/v1/subscriptions
    -d '{
        "resource": "/calendars/{calId}/events",
        "notificationUrl": "https://myserver/pushEvents"
}'
```

#### Contacts

```bash
curl -H 'Authorization: Bearer <access token>'
    -X POST https://api.aurinko.io/v1/subscriptions
    -d '{
        "resource": "/contacts",
        "notificationUrl": "https://myserver/pushEvents"
}'
```

#### Tasks

```bash
curl -H 'Authorization: Bearer <access token>'
    -X POST https://api.aurinko.io/v1/subscriptions
    -d '{
        "resource": "/tasklists/default/tasks",
        "notificationUrl": "https://myserver/pushEvents"
}'
```

or for a specific task list:

```bash
curl -H 'Authorization: Bearer <access token>'
    -X POST https://api.aurinko.io/v1/subscriptions
    -d '{
        "resource": "/tasklists/{tlId}/tasks",
        "notificationUrl": "https://myserver/pushEvents"
}'
```

#### Booking

```bash
curl -H 'Authorization: Bearer <access token>'
    -X POST https://api.aurinko.io/v1/subscriptions
    -d '{
        "resource": "/booking/{bookingId}",
        "notificationUrl": "https://myserver/pushEvents"
}'
```

### Payloads

***

Each API resource may have its own payload format. Below is a sample payload that is common for <mark style="color:red;">`email/messages`</mark>, <mark style="color:red;">`/contacts`</mark>, <mark style="color:red;">`/calendars/{id}/events`</mark>, <mark style="color:red;">`/tasklists/{id}/tasks`</mark>:

```json
{
    "subscription" : 1217,
    "resource" : "/email/messages",
    "accountId" : 1532,
    "payloads" : [
        {
            "id" : "AQMkAGY0ZTQyM2ZlLTM5N2UtNGZkYy1hZmQ2LTJkNDdmNTlmMGZlNgBGAAADhXGu-
                   WVhvEKOWPBUZKnvPwcAAAAUsezTfrRCmmimIKi3ETUAAAIBDAAAARSx7NN\_tEKaaKY
                   gqLcRNQAGD3-S2QAAAA==",
            "changeType" : "created"
        }
        {
            "id" : "AQMkAGY0ZTQyM2ZlLTM5N2UtNGZkYy1hZmQ2LTJkNDdmNTlmMGZlNgBGAAADhXGu-
                   WVhvEKOWPBUZKnvPwcAAAAUsezTfrRCmmimIKi3ETUAAAIBDAAAARSx7NN\_tEKaaKY
                   gqLcRNQAGD3-S2QAAAA==",
            "changeType" : "updated"
        },
        {
            "id" : "AQMkAGY0ZTQyM2ZlLTM5N2UtNGZkYy1hZmQ2LTJkNDdmNTlmMGZlNgBGAAADhXGu-
                   WVhvEKOWPBUZKnvPwcAAAAUsezTfrRCmmimIKi3ETUAAAIBDAAAARSx7NN\_tEKaaKY
                   gqLcRNQAGD3-S2QAAAA==",
            "changeType" : "deleted"
        }
    ]
}
```

Booking have their own payload format. The <mark style="color:red;">`/booking/{bookingId}`</mark> webhook delivers a JSON payload only when a booking (meeting) is created.

```json
{
  "subscription" : 4880,
  "resource" : "/booking/935",
  "accountId" : 1535,
  "payloads" : [
    {
      "bookingId" : 935,
      "calendarId" : "primary",
      "eventId" : "AQMkAGEwZWM2OTY0LWQ4M2UtNGIwYi05M2RmLWJhMDc5OGUxYzQ2ZQBGAAADvqWN9e2g-0SLB0ron1CplQcA6AyjjUD5nUarse36ZjN3XQAAAgENAAAA6AyjjUD5nUarse36ZjN3XQAC5jFyywAAAA=="
    }
  ]
}
```

Next, an example of the <mark style="color:red;">`email/tracking`</mark> events (eventType can be open, reply, or replyBounce).

{% hint style="info" %}
For more details on the email tracking fields (<mark style="color:red;">`opens`</mark>, <mark style="color:red;">`threadReplies`</mark>, <mark style="color:red;">`trackOpensAfterSendDelay`</mark>, <mark style="color:red;">`context`</mark>, <mark style="color:red;">`customDomainAlias`</mark>) and how to include them when sending messages, see the Email Tracking Options section in the [Email API documentation](https://docs.aurinko.io/unified-apis/email-api#email-tracking-options).
{% endhint %}

```json
{
    "subscription": 1271,
    "resource": "/email/tracking",
    "accountId": 1626,
    "payloads": [
        {
            "id": 1670,
            "createdAt": "2023-09-29T09:13:44Z",
            "eventType": "reply",
            "threadId": "",
            "messageId": "",
            "internetMessageId": "<...@mail.gmail.com>",
            "trackingId": 1614,
            "context" : "",
            "trackingCode": "5c59753a-3e4f-4c2c-a2f7-1e5c4fc538d2"
        },
        {
            "id": 1687,
            "createdAt": "2023-09-29T10:59:20.236665Z",
            "eventType": "open",
            "location" : "",
            "userAgent": "Mozilla/4.0 (compatible; ms-office; MSOffice 16)",
            "remoteAddr": "176.116.84.4",
            "trackingId": 1617,
            "context" : "",
            "trackingCode": "fce4d887-1aea-4b2f-93fc-5e02147f9c3d"
        }
    ]
}

{
    "subscription" : 3223,
    "resource" : "/email/tracking",
    "accountId" : 1464,
    "payloads" : [
        {
            "id" : 5973,
            "createdAt" : "2024-10-23T17:15:57Z",
            "eventType" : "replyBounce",
            "threadId" : "",
            "messageId" : "",
            "internetMessageId" : "<...@mail.gmail.com>",
            "trackingId" : 3230,
            "context" : "",
            "trackingCode" : "bce0e37e-9f90-4171-9f76-926c77b2c9b1"
        }
    ]
}
```

\
When an email is first processed for tracking, an ‘Initial’ event is triggered. This event occurs only once when tracking begins, typically upon sending the email, and is not included in subsequent tracking updates:

<pre class="language-json"><code class="lang-json">{ 
    "subscription" : 3190, 
    "resource" : "/email/tracking", 
    "accountId" : 1535, 
    "payloads" : [ 
        { 
            "id" : 5822, 
<strong>            "createdAt" : "2024-10-17T13:35:04Z", 
</strong>            "eventType" : "initial", 
            "threadId" : "", 
            "messageId" : "", 
            "internetMessageId" : "&#x3C;...@mail.gmail.com>", 
            "trackingId" : 3159, 
            "context" : "", 
            "trackingCode" : "e2d9e1fb-e1b2-4a57-96d9-5bc0fe10b129" 
        } 
    ] 
}

</code></pre>

### Handling Webhooks

***

When you receive a webhook:

1. Validate the signature to ensure it's from the Aurinko platform.
2. Respond with a <mark style="color:red;">`200 OK`</mark> as quickly as possible.
3. Process the event data asynchronously.

### Retries

***

If your endpoint responds with any HTTP status other than <mark style="color:red;">`200 OK`</mark> or <mark style="color:red;">`422 Unprocessable`</mark>, Aurinko will attempt to resend the webhook 1, 2, 4, 8 ... etc seconds (the interval won't increase beyond 10mins). Responding with the 422 HTTP status results in removing the subscription.

### Lifecycle events

***

If for some reason your webhook subscription becomes problematic (i.e. because account credentials have expired), Aurinko will send a lifecycle event like this:

```json
{
    "subscription" : 1217,
    "resource" : "/email/messages",
    "accountId" : 1532,
    "lifecycleEvent": "error",
    "error": "Error message"
}
```

When the subscription comes back to life, Aurinko will send:

```json
{
    "subscription" : 1217,
    "resource" : "/email/messages",
    "accountId" : 1532,
    "lifecycleEvent": "active"
}
```

### Deleting a webhook

***

```bash
curl -H 'Authorization: Bearer <access token>'
    -X DELETE https:/api.aurinko.io/v1/subscriptions/{id}
```
