3 Cool Tricks for the Adobe Client Data Layer Extension
Quite possibly the best discovery I happened into 2 years was that of the Adobe Client Data Layer. When considering the best method to implement a data layer structure, it was the one I immediately gravitated towards. It reminded me of a more polished GTM Data Layer, the only difficulty being that there was no direct way to integrate directly in the UI via Adobe Launch extensions. Until…
One day, the invention of the Adobe Client Data Layer extension appeared on the Adobe Exchange thanks to the efforts of Jean-Christophe Kautzmann, Laurentiu Magureanu & Benedikt Wedenik. Immediately, the ease of using the ACDL with Adobe Launch was now accessible to many! Jim Gordon has already written a great summary about this tool’s architecture in depth, so I wanted to focus on some cool tips / tricks for getting the most of using this extension!
Use %event.message% for non-computed state
Probably the best trick I’ve learned was from Ben’s guest post on the “Web Analytics for Developers” blog, of using %event.message.<insert-path-through-dot-notation>% to set values passed in data layer without creating a data element for “Computed Data Layer” value.
For most case scenarios, the “Computed Data Layer” data element that is available with this extension will work great for your use case, but I specifically had a situation where there was a rapid firing of events in succession (almost 2 at the same time) made using the computed data layer state for an object tricky as a race condition existed even with “run rule components in sequence” setting turned on inside Launch. The article specifically mentions %event.message.eventInfo% which is the standard accepted way to pass event related information that will not persist to the ACDL computedState, but it will work on any part of the data layer outside of “eventInfo” as well, and works amazingly.
Build Rules That Trigger Data Layer Events that can Trigger Adobe Launch Rules
Something I’ve been actively working on is the conversion of CSS selector firing rules to data layer events that trigger rules and correctly set variables. Why do this, especially since it feels like a duplication of work? That is a fantastic question, and the answer from my perspective is proof of concept on your shape of data layer.
In the process of transitioning existing events to data layer, you will likely have to determine how these will convert while maintaining parity with previous rules, some of them which used custom code to parse values on page and perform replacement functions for report friendly values. While this sounds easy in theory, as soon as you start doing this work with a development team, you will immediately find use cases where this won’t be a 1:1 conversion, or will need some more work to define / shape, and now you’re on borrowed time to get this done. In addition, the world of XDM is coming, and with the sun rising for our new cookieless future, you’ll need to start working with shaping your data for the schemas to support event forwarding.
If you’re firing to a data layer already, this changeover is simple. Just set an additional attribute in your data layer push action JSON such as “trigger-source: launch” that can be checked as a variable for firing in your data layer event. When development finishes building their changes to the data layer event, their rule won’t have this variable, and won’t accidentally trigger your rule until you release your new Adobe Launch Library that no longer checks for this attribute, which will also contain the disabling of your CSS selector rule.
If you were wondering what to use this action type for, you’re welcome! Make sure you follow JSON formatting when using. You could always use a tool like JSON Formatter & Validator!
An example trigger condition you could create to prevent development release of a data layer event from triggering your rule if their release schedule doesn’t align with yours.
Build Rules That Trigger Data Layer Events that can Trigger Adobe Launch Rules
Something I’ve been actively working on is the conversion of CSS selector firing rules to data layer events that trigger rules and correctly set variables. Why do this, especially since it feels like a duplication of work? That is a fantastic question, and the answer from my perspective is proof of concept on your shape of data layer.
In the process of transitioning existing events to data layer, you will likely have to determine how these will convert while maintaining parity with previous rules, some of them which used custom code to parse values on page and perform replacement functions for report friendly values. While this sounds easy in theory, as soon as you start doing this work with a development team, you will immediately find use cases where this won’t be a 1:1 conversion, or will need some more work to define / shape, and now you’re on borrowed time to get this done. In addition, the world of XDM is coming, and with the sun rising for our new cookieless future, you’ll need to start working with shaping your data for the schemas to support event forwarding.
If you’re firing to a data layer already, this changeover is simple. Just set an additional attribute in your data layer push action JSON such as “trigger-source: launch” that can be checked as a variable for firing in your data layer event. When development finishes building their changes to the data layer event, their rule won’t have this variable, and won’t accidentally trigger your rule until you release your new Adobe Launch Library that no longer checks for this attribute, which will also contain the disabling of your CSS selector rule.
Convert GTM Events to ACDL Events Yourself!
Quite possibly one of the most fun use cases I’ve had was taking existing tag manager events sent by Google and reformatting to send to Adobe Client Data Layer. Sure, you could just set “dataLayer = adobeDataLayer” in either GTM or Adobe Launch custom code (or the extension configuration for ACDL), but I’m personally not a huge fan of that due to all the Google specific events that are sent to “dataLayer” when both GTM & Adobe Launch are on a site. “gtm.init” as an event in your ACDL isn’t relevant and honestly, you can take this as an opportunity to improve shape and build some expectations for data governance on what should pass to your “adobeDataLayer”
Inside GTM, you can create a “Custom HTML” tag as shown, and encase your “adobeDataLayer.push” event to trigger based on specific “page view” or “custom events” (ideally, the custom events you want to track are already sending correctly to the dataLayer for Google, otherwise why are you making work for yourself?). This creates a 1:1 match where the event is sent in Google, and then immediately triggers the push event for adobeDataLayer, without compromising the shape of either data layer. This is fantastic when you’ve worked with a development team to build a data layer structure for “dataLayer” already, and don’t want them to have to re-do their work converting it to “ACDL” standards immediately. Combine it with my above suggestion of adding to your JSON “trigger-source: launch” and you’ll be ready when they’re able to start sending to adobeDataLayer even if they don’t turn off the dataLayer events when they start sending.
Slightly modified screenshot to obfuscate some data, this would take a trigger of “your-event” pushed to “dataLayer” in GTM and grab the values of the custom variables sent in the “dataLayer” object and format them to send to “adobeDataLayer”. Variables may vary depending on the “dataLayer” you’re working with.
Hopefully one of the above tips you’ll find useful in your utilization and exploration of everything possible with the Adobe Client Data Layer extension! In the future, I’m hoping to publish a quick cheat sheet for your reference specifically for this extension similar to the great work done by Jim Gordon on his Adobe Launch Cheat Sheet, and I’ll link it here. The future is now! I’ve made a first version of the Adobe Client Data Layer Cheat Sheet. Let me know if there are any other topics you’d find interesting that you’d like me to cover in the world of analytics implementation!
Hey Andy,
Do you have an example/suggestion to set the product string?
Hey Umar!
That’s a great question.
Probably the biggest pain point I have with the ACDL is the way it handles arrays, as my normal recommendation would be to have a “product” object with an array underneath it that you could store the values you need for your product string, and then use the ACDL extension to grab the full array, and then work with the array either in a data element that pulls from array (extract) or to use custom code to iterate and shape it into the product string.
The issue you will need to determine is whether for your implementation it makes sense to request ALL products be sent, or to have the data layer cleared out of the products by setting products to “undefined” in a push, as the way the arrays work with ACDL is if you make an additional push, it will overwrite the existing array if values exist there.
If it makes sense to treat each product separately and you don’t have many situations where you have multiple products in your product string at once, you might just need to add an action to clear the products field in the ACDL afterwards. If that’s not the case, either development will need to send the full products detail (i.e., for a cart) each push, or you will need to maintain an array in a data element / JavaScript variable that pulls from the ACDL. I’d recommend the development approach if possible, since it adds an extra layer of complexity to your implementation.
Andy
I feel there has been a big miss by Adobe when creating the ext for Launch. The issue to me is using an OTB implementation with AEM core components runs into the issue where the page value has a random number attached at the end of it with every page load. So while your guid and even Adobe’s guide is to use the getState(page.XXXXX) it never works because page may be page-25er4boe then the next page is page-3d8s3swe. So using the guides that are on the internet or trying to use Adobe’s documentation never works. Do you have an answer for this?
{
“page-b2cbbae5dc”: {
“@type”: “core/components/page/v2/page”,
“repo:modifyDate”: “2023-08-24T23:00:00Z”,
“dc:title”: “TITLE”,
“dc:description”: “DESCRIPTION”,
“xdm:template”: “/conf/settings/templates/generic”,
“xdm:language”: “en-US”,
“xdm:tags”: [],
“repo:path”: “/content/home/path.html”
},
Hey Brandon!
One of the reasons I started diving more into the ACDL extension was some of the pain points I had working with an AEM set-up OOTB with the exact issue you call out. I think this is more to do with the limitations chosen for the OOTB configuration for AEM not being an ideal set-up for analytics rather than an issue with the extension.
I believe the random ID attached to the page is related to the ID assigned to the page, so I have not found a guide myself online on how to set this up with minimal effort in Launch. Ideal state; have the developers customize the data layer to match your specs: https://experienceleague.adobe.com/docs/experience-manager-learn/sites/integrations/adobe-client-data-layer/data-layer-customize.html?lang=en
Without developer partnership, this is a much trickier ask but there is a workaround I’ve found works. The “cmp:show” event that triggers on page initial loading start contains the actual page ID in the eventInfo object that can be accessed via %event.message.eventInfo.path% and below is a solution I use to grab the getState for the appropriate object as a workaround:
Rule Condition
Since we’ve verified that the output is exactly matching, we can just use the “adobeDataLayer.getState(“page.pageDetails”) if using my set-up above to access these details. You also don’t have to push to the AEM data layer and can just use this to set the variable that we populate for “adobeDataLayer.getState(pageID)” for a less modified AEM data layer if there are restraints to pushing values to this shape.
Hopefully this helps solve your use case!