# Webhooks

### Get notified about workflow updates

A webhook is a HTTP request used to provide push notifications. TransactionLink sends webhooks to your server to notify programmatically about the completion of the workflow or the change of the workflow status if it is asynchronous.

Our webhooks will notify you of:

* **Workflow completion**\
  When the process is completed, we send the information that the workflow is completed for a given user, with the necessary identifiers and the workflow's reference name. After receiving the notification, the data obtained in the process will be available to download via our API.
* **Workflow awaiting**\
  The user interaction with widget is finished but some tasks have been being processed in background.\
  When all tasks has been processed there is send workflow completed webhook.
  * **Workflow status updates**\
    This is especially useful for asynchronous, long-running workflows, which do not respond with an upfront authorization and don't require user input in our widget.

### Configuring webhooks

To receive webhooks, set up a dedicated endpoint on your server and then configure the Webhook URL in the "Settings" page of our dashboard. TransactionLink sends **POST** requests with a raw JSON payload to your designated endpoint.

<figure><img src="https://files.readme.io/7af96f9-Screenshot_2022-03-29_at_23.15.08.png" alt=""><figcaption></figcaption></figure>

{% hint style="info" %}

#### Test it with ngrok

If you don't have a service accessible from a public network to receive data, we can recommend using [**ngrok**](https://ngrok.com/), which is a reverse proxy fronting web service. Ngrok is the fastest way to put your app on the internet.
{% endhint %}

{% hint style="info" %}

#### Webhook retries and connection errors

Unsuccessful or lack of response within ten seconds attempts to notify the client server will be retried up to five times with a five-second interval. Any response outside the **2xx**, will result in failure
{% endhint %}

### Security

All outgoing webhooks are signed by TransactionLink. The message signature is included in the **JWS-SIGNATURE** header in **detached format**. Verification requires understanding of **JSON Web Tokens(JWTs)** and **JSON Web Signatures**.

### Verification

#### Extract the JWT header

After getting the signature from the webhook, you need to extract the **JOSE header**. It's the part before the first dot. Decode it from **base64Url** format, and you should get a JSON object like the below.

```json
{
  "alg": "RS256",
  "kid": "070725bf-7dac-4712-b61a-420ba3701263",
  "typ": "JWT"
}
```

Extract the value corresponding to the **kid (key ID)** field. This will be used to retrieve the public key corresponding to the private key that was used to sign this request. The **alg** field specifies the algorithm used for signing. By default it's **SHA256 with RSA (RS256)**

#### Get the public key

Having the kid value ready, you can get the public key by making an API call to TransactionLink API as described [here](https://docs.transactionlink.io/docs/transactionlink-api/api-reference/authentication#get-public-key). By default, the key is returned in PEM format.\
\
**Key rotation**\
The key pair used for signing is rotated every 24 hours. After expiration public keys can still be obtained from the API for the next 24 hours. To lower the number of HTTP calls the keys can be cached locally for the next day after the first retrieval.

#### Validate the signature

To validate the signature you should use a preferred **JWT library**. The signature is returned in **detached format**. In order to validate it, the **compact format** must be composed.

First, the payload in correct format is required. When creating the signature, TransactionLink omits all whitespace in the payload. Remove all whitespace from the payload you received in the webhook and encode it in **base64Url**. Put the encoded payload into the detached signature (between two dots) to get the compact format.

Having all three required parts you can pass them to a preferred **JWS validator** and check if the signature is valid.

### Getting webhook outputs

You will receive the notifications on your configured webhook endpoint about the workflow.\
This notification is necessary to retrieve the result of your workflow.

```json
{
  "partyId" : "33e35574-6a97-4e93-94ee-2f28ab3c97c7",
  "caseId" : "33e35574-6a97-4e93-94ee-2f28ab3c97c7",
  "workflowId" : "cd1c4384-bb5b-4483-8974-d8b3ef935843",
  "workflowName" : "70953b16-704a-43a7-b9d0-6cb7d63e491c",
  "workflowDefinitionId" : "a16bc61f-b7ab-4a1d-8301-71740fe6b3a2",
  "workflowStatus" : "COMPLETED",
  "workspaceId" : "aebf8333-5b3e-4840-92dc-f4c8c2c56051"
}
```


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.transactionlink.io/docs/v1/webhooks.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
