How to Update My Post Purchase Tracking to the Latest Recommendation

Our Upsell tracking recommendations have changed in December 2023

đŸ“˜

This guide is for users on our Shopify Source. If you are not on our Shopify, following our guide to upgrade will bring your post-purchase tracking up to speed.

Overview

What's New?

In December 2023, we updated our approach to tracking on the upsell platform. Previously, we triggered the dl_purchase event from the upsell page and then adjusted to prevent it from firing on the thank you page. We are now transitioning to a new approach where the dl_purchase event will be fired from the thank you page, aligning with standard setups. However, we will continue to enable capturing of upsell purchase events from the post-purchase page.

Why did we change our approach?

  • Made the setup easier - The new recommended setup has less tag customization and no manual updates needed to your order status scripts.
  • Allows new and returning users to be captured for your purchase event when the user navigates to the thank you page. These values can impact the way you pay on affiliate platforms! Also, allows you to target new vs returning users on your advertising platform. With the previous setup, this data would never be captured.
  • The previous advanced setup is not necessary with so many destinations available for server-side setup.
  • No longer need to be concerned with the 500ms processing time on the post-purchase page.
  • Makes future updates to your Elevar Tracking much easier!

Changes You Need to Make

Update your Order Status Additional Scripts and Remove Previous Version of Script:

  • Begin on your Shopify homepage and click on the "Settings" button or the gear icon in the lower left-hand corner of the page. Then, using the left hand-menu click on the "Checkout Settings".
  • Navigate to the "Order status page" section of the page. Here you will add the Elevar code.
    • Not sure where you code begins and ends? Looks for the comments <!-- Begin Elevar --> and <!-- End Elevar --> to mark the start and end of the scripts you'll be removing.
    • Not seeing the comments? You may have added our script before we begin included the comments. Here is an example of the script you are looking for. The identifiers will be different for your specific store, but use this as a guideline. If you are still not sure where your script begins and ends, send a file of your entire order status page additional scripts to our support team and we can help you out.
      • (See Figure 1)

Figure 1

Add the new script in your Order Status Additional Scripts:

  • Paste the code you've copied from above into the Order Status Additional Scripts.
  • Save your update!

Update your Post-Purchase Additional Scripts

  • Begin on your Shopify homepage and click on the "Settings" button or the gear icon in the lower left-hand corner of the page. Then, using the left hand-menu click on the "Checkout Settings".
  • Navigate to the "Order status page" section of the page. Here you will add the Elevar code.
    • (See Figure 2)

Figure 2

Remove any previous versions of this script before adding the new script:

  • The old script looks very similar to the new code below. It does not begin and end with the <!-- --> comments. If you are unclear where your script begins and ends, send a file of your entire post-purchase page additional scripts to our support team and we can help you out.

Add the new code with you updated GTM Container ID:

  • The code below pushes a dl_upsell_purchase event when a user takes an upsell or downsell offer.
  • Copy the script below into your Shopify post-purchase page checkout settings (shown in the previous image above). Be sure to update the GTM-xxxxx near the top of the script with your Web Container ID.

New Code:

<!-- Begin Elevar Upsell Tracking -->
<script>
// Fires an dl_upsell_purchase event when customer takes upsell offer

(function (w, d, s, l, i) {
    w[l] = w[l] || []; w[l].push({
        'gtm.start':
            new Date().getTime(), event: 'gtm.js'
    }); var f = d.getElementsByTagName(s)[0],
        j = d.createElement(s), dl = l != 'dataLayer' ? '&l=' + l : ''; j.async = true; j.src =
            'https://www.googletagmanager.com/gtm.js?id=' + i + dl; f.parentNode.insertBefore(j, f);
})(window, document, 'script', 'dataLayer', 'GTM-XXX');

var upsellCount = 0;
(function() {
// EVENT HOOKS -----------------------------------------------------------
if (!Shopify.wasPostPurchasePageSeen) {
    onCheckout(window.Shopify.order, window.Shopify);
}

Shopify.on('CheckoutAmended', function (newOrder, initialOrder) {
    onCheckoutAmended(newOrder, initialOrder, window.Shopify);
});
// END EVENT HOOKS -------------------------------------------------------

// UTILS -----------------------------------------------------------------
// Function called after original order is placed, pre upsell.
function onCheckout(initialOrder, shopifyObject) {
    window.dataLayer = window.dataLayer || [];
    pushDLPurchase(initialOrder, initialOrder.lineItems, false, null, shopifyObject);
}

// Function called when upsell is taken. Separate the new/upsell
// items from the items in the initial order and then send a purchase event
// for just the new items.
function onCheckoutAmended(upsellOrder, initialOrder, shopifyObject) {
    // identify which items were added to the initial order, if any.
    upsellCount++;
    // The line item id is unique for order items, even if the items contained are the same.
    // We can use this to seperate out items from the initial order from the upsell.
    var initialItemIds = initialOrder.lineItems.map(function (line) { return line.id; });
    var addedItems = upsellOrder.lineItems.filter(
        function (line) { return initialItemIds.indexOf(line.id) < 0; }
    );
    // if no new items were added skip tracking
    if (addedItems.length === 0) return;
    pushDLPurchase(upsellOrder, addedItems, true, initialOrder, shopifyObject);
}

function pushDLPurchase(order, addedItems, isUpsell, initialOrder, shopifyObject) {
    window.dataLayer.push({
        'event': isUpsell ? 'dl_upsell_purchase' : '',
        'event_id': getOrderId(order.id, isUpsell),
        'user_properties': getUserProperties(order),
        'ecommerce': {
            'purchase': {
                'actionField': getActionField(order, isUpsell, initialOrder, addedItems, shopifyObject),
                'products': getLineItems(addedItems),
            },
            'currencyCode': order.currency,
        },
    });
}
// Returns a user properties object
function getUserProperties(data) {
    return {
        'customer_id': data.customer.id,
        'customer_email': data.customer.email,
        'customer_first_name': data.customer.firstName,
        'customer_last_name': data.customer.lastName,
        'customer_order_count': data.customer.ordersCount,
    }
}

// Gets line items in purchase
function getLineItems(lineItems) {
    return lineItems.map(function (item) {
        return {
            'category': item.product.type,
            'variant_id': item.variant.id.toString(),
            'product_id': Number(item.product.id).toString(),
            'id': item.variant.sku,
            // We don't get variant title details
            'variant': item.title,
            'name': item.title,
            'price': item.price.toString(),
            'quantity': item.quantity.toString(),
            // Not available
            // 'brand': orderItem.brand,
        }
    });
}

function getActionField(order, isUpsell, initialOrder, addedItems, shopifyObject) {
    var revenue = isUpsell ? getAdditionalRevenue(order, initialOrder) : order.totalPrice;
    var subtotal = isUpsell ? getAdditionalSubtotal(order, initialOrder) : order.subtotalPrice;
    try {
        affiliation = new URL(shopifyObject.pageUrl).hostname;
    } catch (e){
        affiliation = '';
    }
    return {
        'action': "purchase",
        'affiliation': affiliation,
        // This is the longer order id that shows in the url on an order page
        'id': getOrderId(order.id, isUpsell).toString(),
        // This should be the #1240 that shows in order page.
        'order_name': getOrderId(order.number, isUpsell).toString(),
        // This is total discount. Dollar value, not percentage
        // On the first order we can look at the discounts object. On upsells, we can't.
        // This needs to be a string.
        'discount_amount': getDiscountAmount(order, isUpsell, addedItems),
        // We can't determine shipping & tax. For the time being put the difference between subtotal and rev in shipping
        'shipping': (parseFloat(revenue) - parseFloat(subtotal)).toString(),
        'tax': '0',
        'revenue': revenue,
        'sub_total': subtotal,
    };
}

function getDiscountAmount(shopifyOrder, isUpsell, addedItems) {
    if (shopifyOrder.discounts === null || typeof shopifyOrder.discounts === 'undefined') return '0';
    if (shopifyOrder.discounts.length === 0) return '0';
    // If this isn't an upsell we can look at the discounts object.
    if (!isUpsell) {
        // Collect all the discounts on the first order.
        return shopifyOrder.discounts.reduce(function (acc, discount) {
            return acc += parseFloat(discount.amount);
        }, 0).toFixed(2).toString();
    // If this an upsell we have to look at the line item discounts
    // The discount block provided doesn't only applies to the first order.
    } else {
        return addedItems.reduce(function (acc, addedItem) {
            return acc += parseFloat(addedItem.lineLevelTotalDiscount);
        }, 0).toFixed(2).toString();
    }

}

function getOrderId(orderId, isUpsell) {
    return isUpsell ? orderId.toString() + '-US' + upsellCount.toString() : orderId;
}


function getAdditionalRevenue(newOrder, initialOrder) {
    return (parseFloat(newOrder.totalPrice) - parseFloat(initialOrder.totalPrice)).toFixed(2);
}

function getAdditionalSubtotal(newOrder, initialOrder) {
    return (parseFloat(newOrder.subtotalPrice) - parseFloat(initialOrder.subtotalPrice)).toFixed(2);
}

function test() {
    onCheckoutAmended(newOrder, initialOrder);
}

try {
    module.exports = exports = {
        onCheckoutAmended: onCheckoutAmended,
        onCheckout: onCheckout,
        resetUpsellCount: function(){upsellCount = 0;},
    };
} catch (e) { }

})();
</script>
<!-- End Elevar Upsell Tracking -->

That's It!