Webhooks allow your application Backend to be notified with an HTTP call when certain events happen. They can be divided into 2 main groups:

  • Application specific webhooks: are specific to one application, for example when a user is activated in that application.
  • Global webhooks: are specific to user accounts and they affect all the applications in the cluster, for example when a user account is deleted.

HTTP specification

When a webhook is triggered, an HTTP call is made to the URL specified in the Control Panel as shown in the following example:

Example request:

POST example_path HTTP/1.1
Host: example_domain
Content-Type: application/json
x-kwsapi-signature: secure-signature-here
x-kwsapi-webhook-uid: name-of-webhook-here


The custom headers have the following meaning:

  • x-kwsapi-signature: is a custom header that is sent in order to verify that the request is sent by KWS. The algorithm to calculate the expected signature value is explained below.
  • x-kwsapi-webhook-uid: is a custom header with the name of the triggered webhook.

and the body (in the example {“foo”: “bar”} ) will contain a JSON object with a set of fields that will depend on the triggered webhook. More details for the data sent in each call are given in the next subsections.


Note that the new fields might be added to the body in the future. So when parsing the JSON response, extra fields, that are not yet defined should be accepted, and ignored if not needed.

Signature algorithm

The signature will be the HMAC in hex format (lowercase), where the secret key is provided in the Control Panel (as explained later) and the message to be encoded will be the stringified version of the following JSON object:

    "secretKey": "example_key",
    "url": "https://api.example.com/example_path"
    "data": {"foo": "bar"},


  • secretKey is the secret key also used in the encoding.
  • url is the URL of the handler, as specified in the Control Panel.
  • data is the body in the request.

In other words, in order to calculate the kwsapi signature and check that it matches with the one provided in the headers, the following steps have to be taken:

  1. Create a JSON object with the secretKey, url and data fields as explained above.
  2. Create the stringified version of that JSON object.
  3. Calculate the HMAC code using the secret key and the the string message calculated in the previous step. Set the output to hex format all in lowercase.

As an example, this would be the code to calcualte the signature in Node.js

function generateSecureKey(secretKey, url, data) {
    const dataToSign = JSON.stringify({

    return crypto.createHmac('sha256', secretKey).update(dataToSign).digest('hex');


The JSON string should keep the fields in the order defined here. For the data field, it should be in the same order as received in the request. It should also be in the minified version, without extra white spaces or line feeds.

Application specific webhooks

  • child-activated: triggered when a user is activated in the app. It will contain the following data in the body:
    • userId (integer): the id of the user.
    • language (string): the user’s language (ISO Code).
    • signUpCountry (string): country from which the user signed up (ISO Code).
    • username (string): the display name of the user in the app.
    • dateOfBirth (string): the date of birth of the user.
  • user-permission-changed: triggered when the state of a permission in the app changes for a given user. It will contain the following data in the body:
    • userId (integer):
    • permissions (object): an object with keys as permission names and booleans as values indicating the new state of the permission.

Global webhooks

  • parent-registered: triggered when the parent has registered in the parent portal.
    • parentId (integer): the id of the parent.
    • createdAt (string): date of creation of the parent account.
    • email (string): email address of the parent.
    • language (string): the parent’s language (ISO Code).
  • child-linked-to-parent: triggered when the parent of a child acknowledges a child account.
    • userId (integer): the id of the user.
    • parentId (integer): the id of the parent.
  • user-account-deleted: triggered when a user account has been deleted.
    • userId (integer): the id of the user.
  • parent-account-deleted: triggered when a parent account has been deleted.
    • parentId (integer): the id of the parent.

Setting up webhooks in the Control Panel

As explained in a previous section, there are two kind of webhooks: app specific and global. Both can be set up in the Control Panel, but they can be found in different parts of the Control Panel.

Application specific webhooks

App specific webhooks found in the webhooks tab after selecting an application in “My Apps” section:


Clicking on the “Create Webhook” will show the view to create a new webhook:


Global webhooks

Global webhooks can be found found in the “KWS Modules” section:


Clicking on the “Global webhooks” button will show the list of webhooks:


And clicking on the “Create Webhook” will show the view to create a new webhook: