Using Visual Website Optimizer With Google Tag Manager

November 4, 2014


Recently, I was working with a client to integrate Visual Website Optimizer (VWO) with Google Tag Manager. I started by following the integration guide on VWO’s support pages, but ran into a few issues that required a creative workaround.

Not only did the timing of the VWO loading present issues, but I found that the specific data that is supposed to made available on the dataLayer wasn’t being made available.

Follow the instructions below to fix both of the problems!

When to Fire

I had hoped to simply add a custom dimension to our existing Pageview tag in GTM that would add in the necessary information from VWO. However, Since both VWO and Google Tag Manager are loaded asynchronously, we ran into an issue where Google Tag Manager would inconsistently load and execute before VWO was finished loading.

This would mean that object _vwo_exp would not be appended to the page yet by VWO. This resulted in the custom dimension only being populated part of the time.

We could either delay the Pageview tag (not recommended) or come up with a better option. Luckily, VWO passes an event to the dataLayer to let us know when it has finished working. We decided to fire a Google Analytics event when that gets pushed, which fixes our first issue.

What Information to Include

Now that we decided to use an event, we had to decide what information to include. VWO is supposed to be pushing information about the current variation to the dataLayer in addition to the event. Unfortunately, we found this wasn’t working properly.

So instead of following the support guide, I had found that we could grab the same information with a custom JavaScript Macro.

 var expString = null;
   if (typeof _vwo_exp !== 'undefined') {
     expString = [];
     for(keys in _vwo_exp) {
       (typeof _vwo_exp[keys]['combination_chosen'] !== 'undefined'  ? expString.push(keys + ':' + _vwo_exp[keys]['combination_chosen']) : '' );
     (expString.length > 0 ? expString = '|' + expString.join('|') + '|' : expString = null);
 return expString;

What’s happening in this snippet of code is very simple. We want to check to make sure that the _vwo_exp object is present on the page. After that we work through each of the keys. The keys key – is actually evaluated as each campaign inside of the parent object.

We then check to make sure that the user was not excluded from the A/B test. If the user was not excluded from the A/B test, we push the key and the value into an array. Once we check for the variants of each test running we then make the array into a string.

Just a note, If you are excluded from a test, once the _vwo_exp object is appended to the page it won’t have the “combination_chosen” key inside of it, so this macro will just return null.

Sending It All to Google Analytics

Now that we know when to fire, and we have the information to pass in, we need to create the tag that sends it all to GA.

Create a new tag with type of “Universal Analytics” and choose a track type of “Event”. You can fill in the Category name and Label name with anything you like. I decided to use the {{url path}} macro to pass exactly what page this was happening on.

Remember to set Non-Interaction to TRUE, as we don’t want these events affecting our bounce rate!


For Action, you will want to use your recently-created macro. I named this “vwo get experiment,” but you can call this anything you like.

Screen Shot 2014-11-03 at 9.27.01 AM

Now that we have the info, we can still choose to pass this is a Custom Dimension. Make sure you set this up in Google Analytics first, then set the index accordingly and the put the same recently made macro into the Dimension field.

Screen Shot 2014-11-03 at 9.27.16 AM

The next step you need to do is head over to VWO, go to your campaigns settings and check the Google Tag Manager integration. The reason for this is so that the VWO script knows to push the VWO event to the page when the script is loaded.

Finally, you need to set up the rule for so that the event can be triggered.

Screen Shot 2014-11-03 at 9.43.34 AM

That’s it, it’s very simple and can be done with only a handful of lines of code and a little Google Tag Manager magic!