This article covers the integration architecture, data flows, and processing behavior for implementers.
Architecture overview
The connector runs as an ASP.NET Core application on AWS Lambda. Incoming BigCommerce webhooks are validated synchronously for signature integrity, then handed off asynchronously via SQS. A separate Lambda function polls the SQS queue and processes events in parallel batches.
Webhook authentication
Every incoming webhook from BigCommerce is verified before processing:
- The connector extracts the store hash from the
producer field of the payload.
- It looks up the client secret for that store from the secrets store.
- It computes an HMAC-SHA256 digest of the raw request body using the client secret.
- The result is compared against the
X-BC-Signature request header.
If the signature doesn’t match, the request is rejected with 401 Unauthorized. If validation passes, the payload is queued for asynchronous processing.
Real-time webhook flow
The following BigCommerce webhook scopes trigger contact upserts in Engage:
| Scope | Action |
|---|
store/customer/created | Create or update contact |
store/customer/updated | Create or update contact |
store/customer/address/updated | Re-fetch customer by ID, then create or update contact |
store/customer/deleted | Delete contact in Engage |
store/subscriber/created | Newsletter opt-in — create or update contact |
store/subscriber/updated | Newsletter opt-in — create or update contact |
When a created or updated event arrives, the connector:
- Fetches full customer data from BigCommerce v3 (
customers?id:in={id}&include=addresses).
- Extracts the
origin_channel_id to resolve which sales channel the customer belongs to.
- Checks whether a contact with that email already exists in Engage.
- Creates a new contact or updates the existing one.
| BigCommerce field | Voyado contact field |
|---|
first_name | firstName |
last_name | lastName |
email | email |
birthday | birthDay |
id | externalId |
date_created | registrationDate (ISO 8601 with offset) |
phone (from address, E.164 normalised) | mobilePhone |
| Country from first address | Used to resolve registration store ID and phone country code |
addresses[0].* | Address fields (street, city, zip, country) |
Phone numbers are validated and normalised to E.164 format using the libphonenumber library. Invalid numbers are omitted rather than stored in a broken format
Order sync
Webhook events
| BigCommerce scope | Trigger |
|---|
store/order/created | New order placed |
store/order/statusUpdated | Any order status transition |
store/order/refund/created | Refund or partial refund created |
When store/order/statusUpdated fires for a refund status (status ID 4 or 14), the connector skips it. The authoritative event for refunds is store/order/refund/created.
Two-phase processing
- Stage — When a webhook arrives, the connector fetches order and line item data from BigCommerce and writes a
Pending record with the full payload.
- Process — The event processor picks up pending records and sends the order to Engage.
If processing fails, the event is retried automatically up to 10 times. Records that exhaust all retries are marked as failed.
Order status mapping
| BigCommerce status | Status ID | Voyado order type | Voyado order status | Voyado order action |
|---|
| Awaiting Fulfillment | 11 | PURCHASE | InProgress | ConfirmOrder |
| Partially Shipped | 3 | PURCHASE | InProgress | ConfirmShipment |
| Shipped | 2 | PURCHASE | InProgress | ConfirmShipment |
| Awaiting Pickup | 8 | PURCHASE | InProgress | ConfirmCompletion |
| Completed | 10 | PURCHASE | Completed | ConfirmCompletion |
| Cancelled | 5 | PURCHASE | Cancelled | ConfirmCancellation |
| Refunded | 4 | RETURN | Completed | ConfirmOrder |
| Partially Refunded | 14 | RETURN | Completed | ConfirmOrder |
The following statuses are skipped — no action is taken in Engage:
- Awaiting Payment (7)
- Awaiting Shipment (9)
- Manual Verification Required (12)
- Declined (6)
- Any unrecognised status ID
When status_id is 2 (Shipped) and a product has quantity_shipped > 0, the connector generates shipment-level line items in addition to the order-level items.
For each order, the connector:
- Maps each line item to a Voyado line item (SKU, quantity, price, discount) using
v2/orders/{id}/products.
- Fetches payment methods from BigCommerce and attaches them to the order payload.
- Looks up any coupon code applied to the order and redeems the matching Engage promotion if found.
Return orders
When store/order/refund/created fires:
- The
refund_id is extracted from the payload.
- The connector fetches the parent order data.
- A pending record is written with the return type and
refund_id as a sub-identifier.
- The event processor processes it as a RETURN order using the status mapping table above.
Cart tracking
The storefront posts cart data to the connector. The connector:
- Resolves the store and channel from
hash and saleschannelUrl.
- Checks that Cart tracking is enabled.
- Fetches the store locale from BigCommerce (
v3/settings/store/locale).
- Builds a cart payload and posts it to Voyado’s Collect API.
The cart payload includes: cart ID, line items with SKU and quantity, session ID, contact ID, URL, locale, and UTM tags.
Cart-converted webhook
When BigCommerce fires store/cart/converted, the connector:
- Extracts the
orderId from the payload.
- Fetches the order from BigCommerce to get the
channel_id and billing_address.email.
- Looks up the Engage contact ID for that email.
- Posts a cart event to the Collect API with the resolved contact ID, linking an empty cart session to the identified contact.
Product tracking
The storefront posts product view data to the connector. The connector:
- Resolves the store and channel from
hash and saleschannelUrl.
- Checks that Product tracking is enabled.
- Fetches the product from BigCommerce by SKU (
v3/catalog/products?sku={sku}).
- Resolves up to 5 category names from the product’s category IDs (most specific categories). Category names are joined with
/ and capped at 255 characters.
- Fetches the store locale.
- Builds a
productview payload and posts it to the Collect API.
If the product SKU category is not found in BigCommerce, the category is extracted from the product URL path as a fallback.
If the BigCommerce API returns a 5xx error, the connector retries the request up to 3 times before dropping the event.
Multi-channel support
A single BigCommerce store can have multiple sales channels, each with its own configuration and site record. The connector resolves the correct configuration by matching store hash and sales channel ID. For webhook scopes that don’t include a channel_id, the connector fetches the customer or order from BigCommerce to discover the channel before routing.
Webhook health and self-healing
A background job periodically checks all registered BigCommerce webhooks. It:
- Re-activates inactive webhooks via a PUT to BigCommerce’s
v3/hooks/{id}.
- Detects missing webhook scopes and registers them.
This keeps the connector operational after periods of inactivity or after BigCommerce automatically deactivates low-volume webhooks. The job does not replay events missed while a webhook was inactive.