Webhooks make it easy to keep your local database in sync with Piano's entitlements.

Every time an access creation, modification, or revocation event occurs in Piano, our system can be configured to send an encrypted JSON packet to a pre-configured endpoint with what access event has occurred and what access should be granted, modified, or revoked.

This ensures that your local database has all the information you need to properly manage entitlements for your users.

Configuring your Endpoint

Webhooks can be sent to any HTTP or HTTPS endpoint. Login to your Piano dashboard, then click Manage > Webhooks. Toggle the webhooks indicator to the “on” position, and click on the blue URL to edit the endpoint and enter your endpoint URL.

Your endpoint must respond with a 200 OK HTTP status code for it to be configured successfully.

Queueing, Blocking, and Skipping

All webhooks are sent sequentially; this prevents problems that would occur if they were sent out of order. For example, if someone cancels their annual subscription and then resubscribes at the monthly rate - we would need to process those events in order for the user to maintain their access. If the cancel event was sent after the resubscribe event, the user would incorrectly end up without any access.

So, whenever an access event occurs in Piano, we place the webhook event into a single queue for processing. Every successful response that we get back from your endpoint will tell us to proceed with the next webhook. If your endpoint responds with a non-200 HTTP status code, this informs Piano that the endpoint was down or unable to process the webhook.

Because webhooks are sent sequentially and are inherently “blocking”, you should only respond with a non-200 HTTP status code in the case of true, exceptional failure.

Any failures of business logic should be properly caught and handled inside of your application.

Checkout Integration

Webhooks are sent asynchronously. Because of this, webhooks should not be used to determine access after new purchases.

If the user completes their purchase and the page refreshes and you are checking your local entitlements database, it's possible that the user would still see the “doesn't-have-access” state until the webhook event arrived from Piano. If there is a failed webhook that is blocking future processing, this situation would exacerbate itself.

Piano recommends using an approach similar to this, where you register the complete callback which can be used to synchronously fetch new entitlements. In this case, you would implement a /verify-conversion page that would perform the action of fetching the new user entitlements from the Piano API and updating your local datastore.

    offerId: "O1234",
    templateId: "OTABCDEF",
    complete: function(conversion) {
            url: "/verify-conversion",
            method: "POST",
            data : {
                conversion : conversion
            success: function(data) {
                // reload the page, update the user state, etc.

Viewing Webhooks

There are two ways to view all previously-sent webhooks in your account. You can either call the /publisher/webhook/list API method directly, or you can log into your publisher account and navigate to the Webhooks screen.

On this screen you'll see any webhooks that have been sent. You'll also see an indicator that shows the current overall status.

This indicates that webhooks are processing normally and no action is needed. If the webhooks indicator is red, this means that there is a webhook that is blocking future processing. In this case, you should filter the webhooks to find only the failing ones and either skip or resend them.

If you've determined that your system does not need to receive this webhook, you can skip it manually from the dashboard. From the webhooks page, click the down arrow next to the failing webhook and press the Skip button. After you do this, Piano will attempt to send the next webhook.

Exponential Backoff on Failure

Piano will automatically attempt to resend a webhook event in case your server is unavailable at any given moment. After six consecutive failures, an email will be sent to you notifying you of the issue.

The system will cease its attempt to send webhooks after 2 days of failures, at which point the webhook endpoint will be deactivated in the publisher dashboard. You will have to manually turn back on webhooks to continue processing, and any access events that happened between the deactivation and re-enabling will be lost.

Any access events that happen between deactivation due to failure and re-enabling will be lost. You will have to manually query our API to resync your local datastore.

Viewing Responses

The webhooks dashboard will provide you with a list of past webhook requests, the status of each request (success, pending, or failed), the date attempted, the associated user, and an option to resend the request. You can also view the webhook’s header, body and response messages.