Google Optimize will no longer be available after September 30, 2023. Your experiments and personalizations can continue to run until that date. Learn more

Activation events

Run Optimize experiences on dynamic websites and single-page apps.

By default, Optimize modifies the content of a webpage only during its initial load. However, dynamic websites (built with tools like AMP, React, Angular, etc.) and single-page apps (SPA) commonly load additional content long after the initial page load. Optimize supports modifying this late-appearing web content via activation events.

To activate your Optimize experience using an activation event, click Page load [Edit] and choose On custom event or Continuously from the list.

Activation event button

Activation event types

Optimize offers several types of activation events:

  • On page load – Optimize experiences are triggered on page load by default, useful for most static websites.
  • Continuously – Applies desired changes to all newly matching elements.
  • On custom event – A custom event that runs once for each data layer event.

Tips for Activation events

Regardless of whether you choose On custom event or continuously, all page targeting and audience targeting rules must be met for the Optimize experience to trigger.

Option 1: Continuous activation

Continuous activation is recommended for most dynamic sites.

When you select Activation event > Continuously, Optimize automatically applies the change list whenever possible, e.g. immediately upon detecting any newly matching elements. 

Optimize continuously monitors a page for content that's been added since the initial page load using the MutationObserver API built into modern web browsers. When it detects changes, Optimize re-scans the page and applies the change list to all newly detected matching elements.

If you see high JavaScript activity from Optimize, consider switching from continuous activation to triggering Optimize on a custom event.

Only newly detected instances of an element are modified by Optimize. For example, you may have Optimize outline in red the “buy” button of products whenever class=”sale". As a visitor scrolls, more products and their respective buy buttons appear. Optimize will only modify these newer buttons and not every single button that has loaded on the page. After Optimize modifies that instance of the element once, it's considered complete, and Optimize won't modify it again. If you wish to modify the same instance of an element more than once, use Custom activation instead.

Set up continuous activation

To use continuous activation with your Optimize experience:

  1. Create your experience (A/B, multivariate, redirect test, or personalization)
  2. Navigate to Settings > Activation event on the experience details page
  3. Click   Page load [Edit].
  4. Select Evaluate > Continuously from the dropdown menu.
  5. Click Done.

Optimize Activation event screenshot

Note: All page targeting and audience targeting rules must evaluate to true for the Optimize experience to trigger.

Automatic deactivation

If your experience's page targeting rules or audience targeting rules don't match, Optimize automatically reverts your experience to the previously-applied changes.

Note: JavaScript changes can’t be reverted automatically unless you implement a deactivation callback and provide it as the return value.

Option 2: Custom event

Custom events provide granular control over your Optimize experience, allowing you to fire an event at the precise moment the page is ready. If you give your custom event a unique name the data layer event can be implemented sitewide to trigger an Optimize experience. 

To use a custom event, fire a data layer event that triggers Optimize to apply a change list to all newly detected matching elements. A custom event only runs once for each data layer event; if you need an event to run continuously, use Continuously instead. 

Activate an Optimize experience using a custom event by following these steps:

  1. Create a custom event from your website's data layer.
  2. Create a new data layer variable.
  3. Activate the event with JavaScript.

Create a custom event

First, create a custom event from your website's data layer:

  1. Next to Activation event, click Page load [Edit].
  2. Select Evaluate > On custom event from the dropdown menu.
  3. Enter an Event name (e.g. optimize.activate) from your data layer.
  4. Click Done.

After creating your custom event, set your page and/or audience targeting rules in Optimize as you normally would, and determine if reactivation and/or deactivation are required.

Create a new data layer variable

Once you've created an activation event, you must create a data layer variable.

  1. Click Data layer variable > Create new.
  2. Enter the name of the data layer variable to read from.
  3. Name your variable
  4. Click Create variable.

Create new data layer variable in Optimize

Activate the event with JavaScript

After completing the steps above, you must fire a data layer event (using the event name that entered above) to activate your Optimize experience. When the target web page is loaded to the desired state, activate your Optimize experience with the following JavaScript:

dataLayer.push({'event': 'optimize.activate'});

Once the optimize.activate event is fired, any additional targeting conditions will be evaluated and the experience will move to an active state (change list will be applied) only if all of the conditions are true.


If you have multiple AJAX calls that all need to return before your page is ready for the experience, you could fire an event after each AJAX call and also include an additional JavaScript targeting rule that checks a certain variable value. The experience would not fire until the additional JavaScript targeting rule is true and an AJAX call has returned.

Reactivate a change list

It’s possible to configure an experiment so that all of the targeting conditions are fulfilled and the targeted event is fired multiple times.

If you fire the targeted event multiple times and the other targeting conditions are all fulfilled, the change list will be reactivated. When that happens, Optimize will check the page to see if the page has loaded any additional elements that should be changed according to the experiment’s change list. Optimize will update the newly loaded elements accordingly. Existing elements will not be altered.


Consider a page that includes a dynamic shopping cart where a user can click on products to add them to the cart. Then consider an experiment that:

  • Inserts an image after each product in the cart, and...
  • Inserts a global offer message on the top of the body when the user has at least one product in the cart

The page fires the activation event (e.g. shoppingCartChanged) every time that a user adds or removes something from the cart. Both the page condition and the applied changes can be part of the experiment.

In the example above, the targeting condition would include: "Are there any products in the cart?"

The first time that the user adds a product, the change list is activated and Optimize will:

  • Add an image after the single product in the cart
  • Add the global offer message to the top of the page

The second time that the user adds a product to the cart, the change list is re-activated and will:

  • Add an image after the second product in the cart

The second time that the user adds a product to the cart, Optimize doesn’t add a second offer message to the page, nor does Optimize add another image after the first product. The only changed element is the newly added product that was not present when the experiment’s change list was applied the first time.

Deactivate a change list

Activation Events can be used to revert an experiment’s change list. For example, in the shopping cart scenario above, we may not want to show an offer code to a user that no longer meets the experiment’s targeting condition. Likewise, many single page web apps share components across multiple sections of the site, but experiment changes may need to be restricted to a single section.

If an event is fired after a given experiment has been activated and the targeting conditions are no longer satisfied, Optimize will revert the previously applied changes associated with the experiment. In this way, the page is put back into the state it was in before the experiment was activated and the change list was applied.

In the example above, removing the last item from the cart means that the global offer message will be also removed.

JavaScript changes can’t be reverted automatically unless you implement a deactivation callback and provide it as the return value.

Single page applications and virtual pages

Targeting criteria can be used to define virtual pages for single page web apps. The right condition to use is dependent on the site’s underlying framework, but most single page web app developers will find that URL fragments are the easiest option for their sites.

There are cases where web apps do not map a virtual page to a URL fragment. For example, some sites use newsletter signup interstitials that are excellent candidates for A/B testing. These interstitials (and other similar elements) can be experimented on by adding additional targeting conditions to the Optimize experiment. JavaScript variable targeting can be used to check for the existence of specific content or elements.

Deactivation is very useful for single page apps that use CSS Rules to make style changes to components that are reused across multiple pages. The <STYLE> tags of a virtual page will be cleaned up from the <HEAD> when the app transitions to a different virtual page.

Firing activation in a single page application

Reactivating a change list does not require an additional round trip to the Optimize server. As such, a simple and effective approach to Activation Events is to fire an event after anything on the page changes.

For example, an AngularJS app could implement Activation Events in seven lines of code by firing an event after every digest loop.

The following example code snippet fires an event after every digest loop in an AngularJS app:$rootScope, $timeout) {
       dataLayer.push({'event': 'optimize.activate'});
Was this helpful?
How can we improve it?
Clear search
Close search
Google apps
Main menu
Search Help Center