Skip to main content

Webhooks

Caution

The content of this page has not been updated to Strapi v5 yet.

Webhook is a construct used by an application to notify other applications that an event occurred. More precisely, webhook is a user-defined HTTP callback. Using a webhook is a good way to tell third party providers to start some processing (CI, build, deployment ...).

The way a webhook works is by delivering information to a receiving application through HTTP requests (typically POST requests).

User content-type webhooks

To prevent from unintentionally sending any user's information to other applications, Webhooks will not work for the User content-type. If you need to notify other applications about changes in the Users collection, you can do so by creating Lifecycle hooks using the ./src/index.js example.

Available configurations

You can set webhook configurations inside the file ./config/server.

  • webhooks
    • defaultHeaders: You can set default headers to use for your webhook requests. This option is overwritten by the headers set in the webhook itself.

Example configuration

./config/server.js
module.exports = {
webhooks: {
defaultHeaders: {
"Custom-Header": "my-custom-header",
},
},
};

Securing your webhooks

Most of the time, webhooks make requests to public URLs, therefore it is possible that someone may find that URL and send it wrong information.

To prevent this from happening you can send a header with an authentication token. Using the Admin panel you would have to do it for every webhook. Another way is to define defaultHeaders to add to every webhook requests.

You can configure these global headers by updating the file at ./config/server:

./config/server.js
module.exports = {
webhooks: {
defaultHeaders: {
Authorization: "Bearer my-very-secured-token",
},
},
};

If you are developing the webhook handler yourself you can now verify the token by reading the headers.

Available events

By default Strapi webhooks can be triggered by the following events:

NameDescription
entry.createTriggered when a Content Type entry is created.
entry.updateTriggered when a Content Type entry is updated.
entry.deleteTriggered when a Content Type entry is deleted.
entry.publishTriggered when a Content Type entry is published.*
entry.unpublishTriggered when a Content Type entry is unpublished.*
media.createTriggered when a media is created.
media.updateTriggered when a media is updated.
media.deleteTriggered when a media is deleted.
review-workflows.updateEntryStageTriggered when content is moved between review stages (see review workflows).
This event is only available with the Enterprise edition of Strapi.

*only when draftAndPublish is enabled on this Content Type.

Payloads

💡 NOTE

Private fields and passwords are not sent in the payload.

Headers

When a payload is delivered to your webhook's URL, it will contain specific headers:

HeaderDescription
X-Strapi-EventName of the event type that was triggered.

entry.create

This event is triggered when a new entry is created.

Example payload

{
"event": "entry.create",
"createdAt": "2020-01-10T08:47:36.649Z",
"model": "address",
"entry": {
"id": 1,
"geolocation": {},
"city": "Paris",
"postal_code": null,
"category": null,
"full_name": "Paris",
"createdAt": "2020-01-10T08:47:36.264Z",
"updatedAt": "2020-01-10T08:47:36.264Z",
"cover": null,
"images": []
}
}

entry.update

This event is triggered when an entry is updated.

Example payload

{
"event": "entry.update",
"createdAt": "2020-01-10T08:58:26.563Z",
"model": "address",
"entry": {
"id": 1,
"geolocation": {},
"city": "Paris",
"postal_code": null,
"category": null,
"full_name": "Paris",
"createdAt": "2020-01-10T08:47:36.264Z",
"updatedAt": "2020-01-10T08:58:26.210Z",
"cover": null,
"images": []
}
}

entry.delete

This event is triggered when an entry is deleted.

Example payload

{
"event": "entry.delete",
"createdAt": "2020-01-10T08:59:35.796Z",
"model": "address",
"entry": {
"id": 1,
"geolocation": {},
"city": "Paris",
"postal_code": null,
"category": null,
"full_name": "Paris",
"createdAt": "2020-01-10T08:47:36.264Z",
"updatedAt": "2020-01-10T08:58:26.210Z",
"cover": null,
"images": []
}
}

entry.publish

This event is triggered when an entry is published.

Example payload

{
"event": "entry.publish",
"createdAt": "2020-01-10T08:59:35.796Z",
"model": "address",
"entry": {
"id": 1,
"geolocation": {},
"city": "Paris",
"postal_code": null,
"category": null,
"full_name": "Paris",
"createdAt": "2020-01-10T08:47:36.264Z",
"updatedAt": "2020-01-10T08:58:26.210Z",
"publishedAt": "2020-08-29T14:20:12.134Z",
"cover": null,
"images": []
}
}

entry.unpublish

This event is triggered when an entry is unpublished.

Example payload

{
"event": "entry.unpublish",
"createdAt": "2020-01-10T08:59:35.796Z",
"model": "address",
"entry": {
"id": 1,
"geolocation": {},
"city": "Paris",
"postal_code": null,
"category": null,
"full_name": "Paris",
"createdAt": "2020-01-10T08:47:36.264Z",
"updatedAt": "2020-01-10T08:58:26.210Z",
"publishedAt": null,
"cover": null,
"images": []
}
}

media.create

This event is triggered when you upload a file on entry creation or through the media interface.

Example payload

{
"event": "media.create",
"createdAt": "2020-01-10T10:58:41.115Z",
"media": {
"id": 1,
"name": "image.png",
"hash": "353fc98a19e44da9acf61d71b11895f9",
"sha256": "huGUaFJhmcZRHLcxeQNKblh53vtSUXYaB16WSOe0Bdc",
"ext": ".png",
"mime": "image/png",
"size": 228.19,
"url": "/uploads/353fc98a19e44da9acf61d71b11895f9.png",
"provider": "local",
"provider_metadata": null,
"createdAt": "2020-01-10T10:58:41.095Z",
"updatedAt": "2020-01-10T10:58:41.095Z",
"related": []
}
}

media.update

This event is triggered when you replace a media or update the metadata of a media through the media interface.

Example payload

{
"event": "media.update",
"createdAt": "2020-01-10T10:58:41.115Z",
"media": {
"id": 1,
"name": "image.png",
"hash": "353fc98a19e44da9acf61d71b11895f9",
"sha256": "huGUaFJhmcZRHLcxeQNKblh53vtSUXYaB16WSOe0Bdc",
"ext": ".png",
"mime": "image/png",
"size": 228.19,
"url": "/uploads/353fc98a19e44da9acf61d71b11895f9.png",
"provider": "local",
"provider_metadata": null,
"createdAt": "2020-01-10T10:58:41.095Z",
"updatedAt": "2020-01-10T10:58:41.095Z",
"related": []
}
}

media.delete

This event is triggered only when you delete a media through the media interface.

Example payload

{
"event": "media.delete",
"createdAt": "2020-01-10T11:02:46.232Z",
"media": {
"id": 11,
"name": "photo.png",
"hash": "43761478513a4c47a5fd4a03178cfccb",
"sha256": "HrpDOKLFoSocilA6B0_icA9XXTSPR9heekt2SsHTZZE",
"ext": ".png",
"mime": "image/png",
"size": 4947.76,
"url": "/uploads/43761478513a4c47a5fd4a03178cfccb.png",
"provider": "local",
"provider_metadata": null,
"createdAt": "2020-01-07T19:34:32.168Z",
"updatedAt": "2020-01-07T19:34:32.168Z",
"related": []
}
}

review-workflows.updateEntryStage Enterprise

This event is only available with the Enterprise edition of Strapi.
The event is triggered when content is moved to a new review stage (see Review Workflows).

Example payload

{
"event": "review-workflows.updateEntryStage",
"createdAt": "2023-06-26T15:46:35.664Z",
"model": "model",
"uid": "uid",
"entity": {
"id": 2
},
"workflow": {
"id": 1,
"stages": {
"from": {
"id": 1,
"name": "Stage 1"
},
"to": {
"id": 2,
"name": "Stage 2"
}
}
}
}
Payload format for Strapi v4.11.4+

The payload format for the review-workflows.updateEntryStage webhook changed between Strapi v4.11.3 and Strapi v4.11.4. Please notice the payload format differences in the following examples and update your integration code accordingly:

Payload formats for Strapi v4.11.3 vs. Strapi v4.11.4

In Strapi v4.11.3 the webhook payload has the following structure:

{
"event": "review-workflows.updateEntryStage",
"createdAt": "2023-06-30T11:40:00.658Z",
"model": "model",
"uid": "uid",
"entry": {
"entityId": 2,
"workflow": {
"id": 1,
"stages": {
"from": 1,
"to": 2
}
}
}
}

In Strapi v4.11.4 the webhook payload has the following structure:

{
"event": "review-workflows.updateEntryStage",
"createdAt": "2023-06-26T15:46:35.664Z",
"model": "model",
"uid": "uid",
"entity": {
"id": 2
},
"workflow": {
"id": 1,
"stages": {
"from": {
"id": 1,
"name": "Stage 1"
},
"to": {
"id": 2,
"name": "Stage 2"
}
}
}
}