Continuing the ecommerce use case, you want to upload order data from your customers to Optimizely Data Platform (ODP). Orders track which products the customer has requested with additional metadata about the order.
Orders in ODP are represented both as Events and as Orders objects.
- The Events object stores item-level fields, meaning products that a customer purchased.
- The Orders object stores top-level order fields, meaning the order total, taxes, discounts, and customer information.
Each order purchase event generates a single order record (where record is a database entry) with an order purchase event per order line item.
For example, a customer places an order with 3 line items. This generates a single order record, and 3 order purchase events, one for each line item. Those 3 order purchase events are all tied to the single order record.
Top-level information about the order (for example, billing address, coupon, and tax) are stored in the order's object and linked to order's event by
All ODP events (and, as a result, order line items) are immutable, meaning you cannot change them after you upload them to ODP. If you need to process returns, refunds, or cancellations, see the Returns, refunds, and cancellations section.
|Display Name||Field Name||Data Type||Description|
|Order ID||order_id||Text||The unique identifier related to this order.|
|Product ID||product_id||Text||The unique identifier for the order line item.|
|Order Item: Price||price||Number||The price for an order line item.|
|Order Item: Quantity||quantity||Number||The number of items purchased.|
|Order Item: Discount||discount||Number||The discount (if any) for the given line item.|
|Order Item: Subtotal||subtotal||Number||The calculated subtotal for the given product and quantity, typically calculated after any discounts.|
While you cannot update order events, you can update the order summary at any point using the Update object API. Updates made using the Update object API do not generate events.
|Display Name||Field Name||Data Type||Description|
|Order ID||order_id||Text||(Required) The unique identifier related to this order.|
|Status||status||Text||(Required) The status of the order is taken from the event action.|
|Discount||discount||Number||Typically the total value of discounts for the order, including line item and order level discounts.|
|Subtotal||subtotal||Number||Subtotal may be taken either before or after discounting, but generally should be before shipping or tax. See the callout below for more information.|
|Total||total||Number||Total should include the final amount charged to the customer after all goods, discounts, tax, and shipping are calculated. See below for more information.|
|Billing Address*||bill_address||Text||The billing address for the order, lines delimited by commas. Lines should include: Street 1, Street 2, City, State/Region/Province, ZIP/Postal Code, Country. To leave a field blank, include the comma delimiter (for example, Street 1,,City)|
|Shipping Address||ship_address||Text||The shipping address for the order, lines delimited by commas. Lines should include: Street 1, Street 2, City, State/Region/Province, ZIP/Postal Code, Country. To leave a field blank, include the comma delimiter (for example, Street 1,,City)|
|Phone*||phone||Text||The phone number for the order in E.164 format|
|First Name*||first_name||Text||Should match the billed customer.|
|Last Name*||last_name||Text||Should match the billed customer.|
|Name*||name||Text||Should match the billed customer.|
You can add other identifiers (such as an ecommerce platform ID) to the order record. A minimum of one identifier is required to process an order.
This data plus any other identifiers are used to create a customer record (if one does not already exist) or to fill in missing info on an existing record. Info is not overwritten if it already exists. In the case of identifiers such as email or phone, you can store or add multiple values to a single customer record; these identifiers are also used to match the order to an existing customer.
Subtotal and total relationships
ODP does not automatically calculate totals and subtotals at the order level based on item level subtotals or tax, shipping, and discounts. Instead, you send these values as you want them to be represented.
Ecommerce platforms handle the definition of subtotal differently, with some of them including discounts before the subtotal and others including discounts after the subtotal (but before the total). Still others handle line item discounts differently than order-level discounts.
The most important thing is to be consistent between historic imports and real-time orders to ensure that subtotal and total are always calculated the same way across your customers and orders. To help you make this decision, be aware that Lifetime Value (LTV) and Average Order Value in ODP (along with similarly derived fields) are based on the order subtotal.
Import and update order data through the following methods:
- Order Purchase/Return/Refund/Cancellation REST API
- Upload a CSV file in the ODP application or Amazon (AWS) S3
The fields used in either method adhere to the schema outlined above.
To process returns, refunds, and cancellations, send an event with an event type of
order and one of the following event actions:
The following event actions treat
30as a subtotal identically. They both create new events that subtract from the original order total.
return– A customer returned some or all of the items in an order and was refunded.
refund– A customer was issued a refund for a given order. Refunds are treated the same as returns in ODP as both have a negative impact on revenue. Using both lets you distinguish between inventory being returned (
return) as opposed to money being issued to the original purchaser without any inventory being returned (
If the inventory is returned and money is issued back to the purchaser, use the
cancel– A customer cancelled their order. The order
cancelevents remain in ODP (for example, on the customer profile page and for segmentation), and revenue is negatively impacted, but the order no longer figures into determining the customer's lifecycle. This is in contrast to
refunds, where the order still counts in determining the order count, and thus lifecycle, for a customer.
Order returns, refunds, and cancels can be partial. ODP determines if they are partial by tracking whether the running tally of the order's subtotal field across events is greater than zero (partial) or not.
ODP lets the subtotal and total fields for an order go negative (for example, to support purchase and refund events received out of order or to support cases where the refund amount legitimately exceeds the purchase amount).
Be cautious not to issue duplicate refund, return, and cancel events.
You can customize the
cancel actions on the order to your business. These custom statuses are treated as follows:
- If the order exists, the order details are not updated (for example, the order total would not be incremented). You can send the order information as a pass-through to an event-triggered marketing campaign without concern about changing order details.
- If the order does not exist, the order is created according to the details on the request.
Updated 17 days ago