Webhooks are basically reliable HTTP POST callbacks. By subscribing to our webhooks, you can listen for events such as new signups and changes in contracts to keep your system synchronized to billwerk. This is particularly useful if you want to use our ready-to-use customer portal and signup pages.

Webhook Security & Reliability

Reliability is achieved by repeating the request until it is responded to with a 200 OK, 201 Created, 202 Accepted or 204 NoContent success response. Make sure your application only returns a success code after it has persisted important information. We'll repeat the request a dozen times until we will drop the hook.

The delay between two attempts doubles after every failed attempt, so keep in mind that webhooks could be up to two days old!

A common approach to secure webhooks is to use HMAC-SHA* message signing. While that is not a bad method, it forces you to provide SSL on your site, validate the request hash and read the data out of the webhook. That drags versioning and security issues along, and it must be secured against replay attacks.

In contrast, billwerk webhooks only contain an Event field and, depending on the event, an id field such as ContractId. That means that you'll have to query the billwerk API to retrieve the current state of the referenced object in your handler. This makes it possible to receive webhooks on non-SSL-pages and it's easier to handle hooks that are delayed or potentially arrive in the wrong order. So, even though webhooks use POST and aren't generally required to, we recommend your webhook handler be idempotent.

Available Hooks

OrderSucceeded

Sent when an order was finished successfully. This includes all order types (signup, upgrade, ...).

Typical Scenario

You want to listen to this hook to send an order confirmation by email to the customer.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "OrderSucceeded",
                    "ContractId" : "51d970c8eb596a1168df119a"
                }
            

ContractCreated

Sent when a contract was created either via self-service or Admin UI.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "ContractCreated",
                    "ContractId" : "51d970c8eb596a1168df119a"
                }
            

Typical Scenario

Upon receving this hook, you'll want to query the billwerk API for the given contract to create a new account in your system and send a welcome email. To do so, you might have to also fetch the customer whose id is given in the contract.

ContractChanged

Sent whenever the state of a contract has changed. There are various reasons why the contract could have changed, e.g.
  • The trial has ended
  • The contract has ended
  • The contract was up- or downgraded
  • A component subscription was added or removed

Typical Scenario

You want to listen to this hook to make sure your customers gets what he ordered (and only what he paid for). Together with ContractCreated, this is the most important hook. To find out what the current state of the contract is, simply fetch the referenced contract by id and make sure to configure your service to deliver what is configured in the contract.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "ContractChanged",
                    "ContractId" : "51d970c8eb596a1168df119a"
                }
            

ContractCancelled

Sent when the cancellation was triggered, NOT when the contract actually ends. If you want to get notified when a contract ends, use the ContractChanged webhook instead. Usually a cancellation is triggered some time before the contract actually ends (notice period).

Typical Scenario

You might want to listen to this hook to get into contact with the customer to make him a special offer if he withdraws his cancellation.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "ContractCancelled",
                    "ContractId" : "51d970c8eb596a1168df119a"
                }
            

CustomerCreated

Sent whenever a customer has been created, e.g. through a signup.
                        HTTP/1.1
                        POST /billwerk-hook
                        Host: example.com
                        Content-Type: application/json

                        {
                            "Event" : "CustomerCreated",
                            "CustomerId" : "51d970c8eb596a1168df119a"
                        }
                    

Typical Scenario

Usually, you want to listen to this hook to notice new customers on billwerk. After receiving the webhook, fetch the customer by id and create a new customer on your side.

CustomerChanged

Sent whenever the base information of a customer has changed because it was modified via the customer portal.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json

                {
                    "Event" : "CustomerChanged",
                    "CustomerId" : "51d970c8eb596a1168df119a"
                }
            

Typical Scenario

Usually, you want to listen to this hook to keep your customer data in sync between your system and billwerk. To do so, fetch the customer by id and apply all necessary changes on your side.

CustomerDeleted

Sent whenever the base information of a customer has deleted.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json

                {
                    "Event" : "CustomerDeleted",
                    "CustomerId" : "51d970c8eb596a1168df119a"
                }
            

Typical Scenario

Usually, you want to inform about that customer deleted. To do so, fetch the customer by id and apply all necessary changes on your side.

DunningCreated

This webhook is triggered when a new dunning PDF was created and sent/archived.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "DunningCreated",
                    "DunningId" : "51d97067cb596a1239fff424"
                }
            

InvoiceCreated

This webhook is triggered when a new invoice or credit note PDF was created and sent/archived.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "InvoiceCreated",
                    "InvoiceId" : "51d97067cb596a1239fff423"
                }
            

InvoiceCorrected

This webhook is triggered when a new invoice or credit note PDF was corrected and sent/archived.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "InvoiceCorrected",
                    "OldInvoiceId" : "51d97067cb596a1239fff423", //Deprecated. Do not use this anymore
                    "NewInvoiceId" : "51d97067cb596a1239fff424", //Deprecated. Do not use this anymore
                    "OldInvoiceDraftId" : "51d97067cb596a1239fff423",
                    "NewInvoiceDraftId" : "51d97067cb596a1239fff424"
                }
            

RecurringBillingApproaching

This webhook is triggered when a billing period ended. Depending on your billing delay settings you can use this webhook to pass remaining metered usage or rated items before the actual recurring billing is processed.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "RecurringBillingApproaching",
                    "ContractId" : "51d970f8cb596a2269df14ab"
                }
            

TrialEndApproaching

Sent when the trial period of a contract is about to expire. The warning time can be defined per plan.

Typical Scenario

You want to send a reminder to your customer if the trial expires in x days.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "TrialEndApproaching",
                    "ContractId" : "51d970c8eb596a1168df119a"
                }
            

AccountCreated (deprecated)

Replaced by ContractCreated
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "AccountCreated",
                    "ContractId" : "51d970c8eb596a1168df119a"
                }
            

PaymentBearerExpiring

                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "PaymentBearerExpiring",
                    "ContractId" : "51d970c8eb596a1168df119a",
                    "ExpiryDate" : "2013-12-22T11:11:11Z"
                }
            
Notifies you about a payment bearer that is due to expire soon (typically a credit card). You probably want to inform your customer and ask them to provide new payment information. This hook will be triggered even for contracts that have ended, but you can filter such contracts in your web hook handler.

PaymentBearerExpired

                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "PaymentBearerExpired",
                    "ContractId" : "51d970c8eb596a1168df119a",
                    "ExpiryDate" : "2013-12-22T11:11:11Z"
                }
            
Notifies you about a payment bearer that just expired. The next payment will fail and you probably want to take approriate action.

DebitAuthCancelled

Webhook is triggered when the authorization to debit money has been revoked either by customer or PSP. The next payment will fail and you probably want to take approriate action.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "DebitAuthCancelled",
                    "ContractId" : "51d970c8eb596a1168df119a",
                    "CustomerId" : "51d140d8fc787ac88a4afc4a",
                    "YourCustomerId" : "23213",
                    "PaymentProvider" : "Skrill",
                }
           

PaymentDataChanged

Webhook is triggered when a new payment bearer is assigned to a contract. (e.g. customer has entered new credit card data after the old card expired)
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "PaymentDataChanged",
                    "ContractId" : "51d970c8eb596a1168df119a"
                }
           

PaymentEscalated

Triggered based on your payment escalation settings.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "PaymentEscalated",
                    "ContractId" : "51d970c8eb596a1168df119a",
                    "CustomerId" : "51d140d8fc787ac88a4afc4a",
                    "YourCustomerId" : "23213",
                    "TriggerDays" : 6,
                    "DueDate" : "2012-11-15T19:28:34Z",
                    "PaymentProvider" : "Skrill",
                    "PaymentEscalationProcessId" : "50c257d8fc923ac88a49fdc0"
                }
            
You can use this hook to react to your customer's non-payment, for example by sending a notification email or by suspending the account. The value of TriggerDays is the number of days since the payment's due date. This is based on the oldest unpaid receivable, so it's possible that you receive a five-day-hook, then a ten-day-hook and a five-day-hook again.

PaymentEscalationReset

Triggered when an escalation process was reset automatically or manually. An automatic reset happens when the customer paid the vacant positions. The process can also be reset manually by you.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "PaymentEscalationReset",
                    "ContractId" : "51d970c8eb596a1168df119a",
                    "CustomerId" : "51d140d8fc787ac88a4afc4a"
                }
            

PaymentFailed

In most cases, it's not required nor suggested to handle this webhook yourself. Use payment escalation instead.
Sent when a payment failed. Usually, it's not required that you worry about this in your application, because billwerk has configurable payment escalation that can be configured in the billwerk UI. Please also note that coping with payment errors can be somewhat complicated since there are both permanent, irrecoverable errors and temporary errors
            HTTP/1.1
            POST /billwerk-hook
            Host: example.com
            Content-Type: application/json
            {
                "Event" : "PaymentFailed",
                "PaymentTransactionId" : "51d970c8eb596a1168df119a"
            }
        

PaymentSucceeded

In most cases, it's not required nor suggested to handle this webhook yourself. Use payment escalation instead.
Sent when a payment was successfully completed. Usually, it's not required that you worry about this in your application.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json

                {
                    "Event" : "PaymentSucceeded",
                    "PaymentTransactionId" : "51d970c8eb596a1168df119a"
                }
            

PaymentProcessStatusChanged

There are different reasons why a payment processes for a contract is paused, e.g several payment retries failed. In such cases billwerk stops any further payment processes. You might want to get informed about these events to take appropriate action. This webhook will be triggered if the process is stopped or started.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json
                {
                    "Event" : "PaymentProcessStatusChanged",
                    "ContractId" : "51d970f8cb596a2269df14ab"
                }
            

PaymentRegistered

Sometimes you might have external payments/refunds outside of billwerk (e.g. bank transfer by your customer). These payments are either registered manually or via account reconciliation. This webhook will be triggered when a new external payment/refund is registered in billwerk.
                HTTP/1.1
                POST /billwerk-hook
                Host: example.com
                Content-Type: application/json

                {
                    "Event" : "PaymentRegistered",
                    "ContractId" : "51d970f8cb596a2269df14ab"
                }