Webhooks

Webhook Setup

You will receive notifications via a webhook whenever there are new events associated with a Connection or change in data.

Set up tunneling

We recommend using ngrok to serve your backend over a public URL.

After installing ngrok, if your backend is running on port 4000, run ngrok http 4000. This will then give you public URLs that Rutter can hit to send updates.

Configure your webhook

To let Rutter know what your webhook URL is, go to the Platforms page in the dashboard. Paste in the public URL that ngrok generated for you in the previous step.

Handle webhooks

That's it! Now, you can run through the connection flow again, and check that events are sent to your webhook URL.

Webhook Security

Webhook signatures provide additional security to webhooks emitted by Rutter by verifying that the webhook wasn't sent from an unknown or malicious entity. To do this, Rutter signs each webhook payload with a secret. The resulting signature is included in the header of the request, which you can then use to verify that the webhook received is from Rutter, guaranteeing the validity of the webhook.

Every webhook sent by Rutter contains a header called X-Rutter-Signature whose value is the prefix sha256= followed by a base64 encoded HMAC-SHA256 hash of the webhook payload, where the secret used to generate the hash is your organization's client secret.

Webhook retries

You can implement rate-limiting of Rutter webhooks to handle load on your server. If we receive a failure HTTP status code from your server when sending a webhook, we will attempt to retry the webhook up to 6 times following an exponential backoff method. The 6 attempts will take place over a period of ~15 minutes. If the webhook fails to be delivered after 6 attempts, we will stop retrying and mark the webhook as failed.

Special considerations

When working with webhooks, please keep the following in mind:

Webhooks that have the same payload may be sent multiple times. This can be caused by a variety of reasons, such as when the underlying raw platform data changes but not the standardized Rutter data object. Please make sure your webhook handler accounts for this behavior.

Webhooks are not 100% reliable. Expect a small percentage of webhooks to get dropped under normal working conditions. Make sure to handle these missing webhooks gracefully, so that the application still syncs even if no webhooks are received. We recommend calling the API endpoints regularly to check for updates in addition to using webhooks for real-time updates.


Connections Webhooks

You will receive notifications via a webhook whenever there are new events associated with a Connection. All webhooks related to a connection have a type of CONNECTION.

INITIAL_UPDATE

This webhook fires after an initial data download for a Connection has been completed. You can now send requests to Rutter to fetch merchant data.

1
{
2
"type": "CONNECTION",
3
"code": "INITIAL_UPDATE",
4
"connection_id": "3adc1519-0d6e-4222-83de-25b457cf42be",
5
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65"
6
}

Attempting to fetch data from a Connection without receiving the INITIAL_UPDATE webhook will return a PRODUCT_NOT_READY error.

If your organization has data batching enabled, this webhook will fire after a batch of historical data for a Connection has been synchronized. You can continue to fetch data while this process occurs.

Note

HISTORICAL_UPDATE will only fire if you have data batching enabled.

1
{
2
"type": "CONNECTION",
3
"code": "HISTORICAL_UPDATE",
4
"connection_id": "3adc1519-0d6e-4222-83de-25b457cf42be",
5
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
// Array containing information about which objects have been synchronized
7
"entities_included_to_time_range": [
8
{
9
"platformEntity":"ORDERS",
10
"xMonthsAgo":1
11
},
12
{
13
"platformEntity":"CREDIT_MEMOS",
14
"xMonthsAgo":1
15
}
16
],
17
}

CONNECTION_UPDATED

This webhook fires after a merchant re-authenticates an existing Connection, or after completing authentication for a created connection. The access_token value stays the same even if the Connection is updated.

1
{
2
"type": "CONNECTION",
3
"code": "CONNECTION_UPDATED",
4
"connection_id": "3adc1519-0d6e-4222-83de-25b457cf42be",
5
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"store_unique_id": "AWMFIE33LD"
7
}

CONNECTION_NEEDS_UPDATE

This webhook fires after a merchant unauthorizes/uninstalls an existing Connection, or if the authentication fails for any other reason. The webhook payload includes a URL that you can share directly with the merchant to re-authenticate them.

1
{
2
"type": "CONNECTION",
3
"code": "CONNECTION_NEEDS_UPDATE",
4
"connection_id": "3adc1519-0d6e-4222-83de-25b457cf42be",
5
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"update_url": "https://link.rutterapi.com/connection/3adc1519-0d6e-4222-83de-25b457cf42be"
7
}

CONNECTION_DISABLED

This webhook fires after Rutter has encountered a problem with a connection and has temporarily disabled access to it. For example, the merchant's store got suspended by the platform, it would cause the connection to be disabled. Usually, there are additional steps this merchant needs to do in beyond simply reauthenticating depending on circumstances. To understand why it's disabled, you can use Fetch a Connection Status to find out and take actions accordingly with merchants.

1
{
2
"type": "CONNECTION",
3
"code": "CONNECTION_DISABLED",
4
"connection_id": "3adc1519-0d6e-4222-83de-25b457cf42be",
5
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"disable_error": "Reached same error over 100 times",
7
"disable_message": "Error: HTTP server returned 500"
8
}

This webhook fires after an error occurs during the authentication process. The webhook payload includes some human-readable details around the error, and a URL that you can share directly with the merchant to re-authenticate them.

1
{
2
"type": "CONNECTION",
3
"code": "CONNECTION_LINK_ERROR",
4
"connection_id": "3adc1519-0d6e-4222-83de-25b457cf42be",
5
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"update_url": "https://link.rutterapi.com/connection/3adc1519-0d6e-4222-83de-25b457cf42be",
7
"message": "The merchant denied access during OAuth",
8
"platform": "SHOPIFY"
9
}

CONNECTION_ERROR

This webhook after an error occurs for a connection. Errors can be related to data synchronization or issues connecting to a merchant's store after authentication is complete. The error message will contain information about the connection issue.

1
{
2
"type": "CONNECTION",
3
"code": "CONNECTION_ERROR",
4
"connection_id": "3adc1519-0d6e-4222-83de-25b457cf42be",
5
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"message": "Cloudflare is enabled on this store and Rutter requests are blocked.",
7
}

CONNECTION_AUTHENTICATED

This webhook fires for an INTUIT_BANK_FEEDS connection when authentication is successfully completed between Rutter and Intuit.

1
{
2
"type": "CONNECTION",
3
"code": "CONNECTION_AUTHENTICATED",
4
"connection_id": "3adc1519-0d6e-4222-83de-25b457cf42be",
5
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"platform": "INTUIT_BANK_FEEDS"
7
}

Accounting Webhooks

Account Webhooks

To see the Rutter account schema, please see Account.

ACCOUNT_CREATED

1
{
2
"type": "ACCOUNT",
3
"code": "ACCOUNT_CREATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"account": {
7
// ... Created Account object
8
}
9
}

ACCOUNT_UPDATED

1
{
2
"type": "ACCOUNT",
3
"code": "ACCOUNT_UPDATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"account": {
7
// ... Updated Account object
8
}
9
}

Bills Webhooks

To see the Rutter Bill schema, please see Bill.

BILL_CREATED

1
{
2
"type": "BILL",
3
"code": "BILL_CREATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"bill": {
7
// ... Created Bill object
8
}
9
}

BILL_UPDATED

1
{
2
"type": "BILL",
3
"code": "BILL_UPDATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"bill": {
7
// ... Updated Bill object
8
}
9
}

Bill Payments Webhooks

To see the Rutter Bill Payment schema, please see Bill Payments.

BILL_PAYMENT_CREATED

1
{
2
"type": "BILL_PAYMENT",
3
"code": "BILL_PAYMENT_CREATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"bill_payment": {
7
// ... Created Bill payment object
8
}
9
}

BILL_UPDATED

1
{
2
"type": "BILL_PAYMENT",
3
"code": "BILL_PAYMENT_UPDATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"bill_payment": {
7
// ... Updated Bill payment object
8
}
9
}

Customers Webhooks

To see the Rutter Customer schema, please see Customer.

CUSTOMER_CREATED

1
{
2
"type": "CUSTOMER",
3
"code": "CUSTOMER_CREATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"customer": {
7
// ... Created accounting customer object
8
}
9
}

CUSTOMER_UPDATED

1
{
2
"type": "CUSTOMER",
3
"code": "CUSTOMER_UPDATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"customer": {
7
// ... Updated accounting customer object
8
}
9
}

Invoices Webhooks

To see the Rutter Invoice schema, please see Invoices.

INVOICE_CREATED

1
{
2
"type": "INVOICE",
3
"code": "INVOICE_CREATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"invoice": {
7
// ... Created invoice object
8
}
9
}

INVOICE_UPDATED

1
{
2
"type": "INVOICE",
3
"code": "INVOICE_UPDATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"invoice": {
7
// ... Updated invoice object
8
}
9
}

Invoice Credit Memos Webhooks

To see the Rutter Invoice Credit Memo schema, please see Invoices Credit Memos.

INVOICE_CREDIT_MEMO_CREATED

1
{
2
"type": "INVOICE_CREDIT_MEMO",
3
"code": "INVOICE_CREDIT_MEMO_CREATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"invoice_credit_memo": {
7
// ... Created Invoice Credit Memo object
8
}
9
}

INVOICE_CREDIT_MEMO_UPDATED

1
{
2
"type": "INVOICE_CREDIT_MEMO",
3
"code": "INVOICE_CREDIT_MEMO_UPDATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"invoice_credit_memo": {
7
// ... Updated Invoice Credit Memo object
8
}
9
}

Journal Entries Webhooks

To see the Rutter Journal Entry schema, please see Journal Entries.

JOURNAL_ENTRY_CREATED

1
{
2
"type": "JOURNAL_ENTRY",
3
"code": "JOURNAL_ENTRY_CREATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"journal_entry": {
7
// ... Created Journal Entry object
8
}
9
}

JOURNAL_ENTRY_UPDATED

1
{
2
"type": "JOURNAL_ENTRY",
3
"code": "JOURNAL_ENTRY_UPDATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"journal_entry": {
7
// ... Updated Journal Entry object
8
}
9
}

Vendors Webhooks

To see the Rutter Vendor schema, please see Vendors.

VENDOR_CREATED

1
{
2
"type": "VENDOR",
3
"code": "VENDOR_CREATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"vendor": {
7
// ... Created vendor object
8
}
9
}

VENDOR_UPDATED

1
{
2
"type": "VENDOR",
3
"code": "VENDOR_UPDATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"vendor": {
7
// ... Updated vendor object
8
}
9
}

Commerce Webhooks

Orders Webhooks

You will receive notifications via a webhook whenever there are new events associated with an order. All webhooks related to an order have a type of ORDER.

ORDER_CREATED

Fired after a new order has been created for a connection.

1
{
2
"type": "ORDER",
3
"code": "ORDER_CREATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"order": {
7
// ... New order object
8
}
9
}

ORDER_UPDATED

Fired after an order has been updated for a connection. If any field within Orders changed, including content of line_items, status, payment_status, etc, we will fire this webhook.

1
{
2
"type": "ORDER",
3
"code": "ORDER_UPDATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"order": {
7
// ... Updated order object
8
}
9
}

ORDER_DELETED

Fired after an order has been deleted.

1
{
2
"type": "ORDER",
3
"code": "ORDER_DELETED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"order": {
7
"id": "60fde312-0a7e-4bda-b838-3aa19a5c57e4"
8
}
9
}

Products Webhooks

You will receive notifications via a webhook whenever there are new events associated with a product. All webhooks related to a product have a type of PRODUCT and a code with the specific type of event which occurred.

PRODUCT_UPDATED

Fired after a product has been updated.

1
{
2
"type": "PRODUCT",
3
"code": "PRODUCT_UPDATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"product": {
7
// ... Updated product object
8
}
9
}

PRODUCT_CREATED

Fired after a product has been created.

1
{
2
"type": "PRODUCT",
3
"code": "PRODUCT_CREATED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"product": {
7
// ... New product object
8
}
9
}

PRODUCT_DELETED

Fired after a product has been deleted. This is available only to Shopify, WooCommerce, and Wix. Please see here for more explanation.

1
{
2
"type": "PRODUCT",
3
"code": "PRODUCT_DELETED",
4
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
5
"connection_id": "222c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"product": {
7
"id": "60fde312-0a7e-4bda-b838-3aa19a5c57e4"
8
}
9
}

PRODUCT_READY

In platforms where POST /product is a long running job (specifically Amazon), a job ID will be returned as a response. A PRODUCT_READY webhook will be fired when the job has completed. A product object will be returned on POST /product success, and an error message will be returned on failure.

1
{
2
"type": "PRODUCT",
3
"code": "PRODUCT_READY",
4
"job_id": "fc7e5f82-b6f3-4ad7-94d9-f00f9c864fa9",
5
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"product": {
7
"id": "60fde312-0a7e-4bda-b838-3aa19a5c57e4",
8
},
9
"error": null
10
}

PRODUCT_FINISH_FAILED

In the platforms where image upload and/or variant create run asynchronously after the initial POST /products request, we will send an error message in case variant create or image upload fails. In the case of success, we will send a PRODUCT_UPDATE webhook.

1
{
2
"type": "PRODUCT",
3
"code": "PRODUCT_FINISH_FAILED",
4
"job_id": "fc7e5f82-b6f3-4ad7-94d9-f00f9c864fa9",
5
"connection_id": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"productRequestBody": {
7
// Original product request body sent in POST /products
8
},
9
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
10
"existingProductId": "60fde312-0a7e-4bda-b838-3aa19a5c57e4",
11
"error_message": "Something went wrong. Contact support@rutterapi.com for information."
12
}

Store Webhooks

You will receive notifications via a webhook whenever there are new events associated with a Store. All webhooks related to a store have a type of STORE.

STORE_UPDATED

This webhook fires a merchant's store configuration changes (the most common changes are default currency change and default language change)

1
{
2
"type": "STORE",
3
"code": "STORE_UPDATED",
4
"connection_id": "3adc1519-0d6e-4222-83de-25b457cf42be",
5
"access_token": "313c3e00-2bbc-4b2e-a9dc-13abed546b65",
6
"store": {
7
"default_currency": "EUR",
8
"email": "example@rutterapi.com",
9
"id": "3e406708-e696-4454-9367-a6bb2bd9bdf0",
10
"store_name": "Rutter test store",
11
"url": "www.google.com"
12
}
13
}

Delete Webhooks

When Rutter detects that an entity is deleted directly from the underlying platform, you will receive a notification via webhook.

Please be aware that marking a resource as inactive is NOT the same as deleting it, and a webhook will not be sent in that case.

Delete webhooks are supported for select resources and platforms. See the table below for the currently enabled list:

Delete EventEntity NameSupported Platforms
ACCOUNT_DELETEDaccountQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE
BANK_DEPOSIT_DELETEDbank_depositQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE
BANK_TRANSFER_DELETEDbank_transferQUICKBOOKS, NETSUITE
BILL_DELETEDbillQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE
BILL_CREDIT_MEMO_DELETEDbill_credit_memoQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE
BILL_CREDIT_APPLICATION_DELETEDbill_credit_applicationQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE
BILL_PAYMENT_DELETEDbill_paymentQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE
CLASS_DELETEDclassQUICKBOOKS_DESKTOP, NETSUITE
COMPANY_INFO_DELETEDcompany_infoNETSUITE
CURRENCY_DELETEDcurrencyNETSUITE
CUSTOMER_DELETEDcustomerQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE
DEPARTMENT_DELETEDdepartmentNETSUITE
EXPENSE_DELETEDexpenseQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE
EXPENSE_REFUND_DELETEDexpense_refundQUICKBOOKS, NETSUITE
INVOICE_DELETEDinvoiceQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE
INVOICE_CREDIT_APPLICATION_DELETEDinvoice_credit_applicationQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE
INVOICE_CREDIT_MEMO_DELETEDinvoice_credit_memoQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE
INVOICE_PAYMENT_DELETEDinvoice_paymentQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE
ITEM_DELETEDitemQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE
JOURNAL_ENTRY_DELETEDjournal_entryQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE
LOCATION_DELETEDlocationNETSUITE
PAYMENT_METHOD_DELETEDpayment_methodQUICKBOOKS_DESKTOP, NETSUITE
PAYMENT_TERM_DELETEDpayment_termNETSUITE
PURCHASE_ORDER_DELETEDpurchase_orderQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE
SALES_ORDER_DELETEDsales_orderQUICKBOOKS_DESKTOP, NETSUITE
SUBSIDIARY_DELETEDsubsidiaryNETSUITE
TAX_RATE_DELETEDtax_rateQUICKBOOKS_DESKTOP, NETSUITE
VENDOR_DELETEDvendorQUICKBOOKS_DESKTOP, QUICKBOOKS, NETSUITE

The structure of the request payload will be the same between all resources, with the exception of the resource key. For example, the below payload will be sent in the case of a BILL_DELETED event. Please note that the bill key will vary between resources, but will always be equal to the entity key found in the event table above.

1
{
2
"type": "BILL",
3
"code": "BILL_DELETED",
4
"connection_id": "f53bd178-0834-456d-adc0-735a6cf64002",
5
"access_token": "c37ffdf3-48b3-4e7b-a224-1732d71e655f",
6
"bill": {
7
"id": "3ca7e1cb-48ce-4bb9-a0d7-6ab6250aff76",
8
"deleted_at": "2024-01-03T13:47:26.000Z"
9
}
10
}