Install Userorbit through Google Tag Manager when a governed GTM Web container already owns third-party browser tags. Keep the SDK bootstrap, identity, and configured product events as separate tags so consent, ordering, and failures remain visible.

Before you begin

You need:

  • edit access to a GTM Web container and its Preview mode
  • the generated Userorbit snippet from Userorbit → Settings → Widget
  • a staging URL and test user
  • a published test tour or checklist if you want to verify delivery
  • an application-owned dataLayer contract for user, account, and product-event data
  • a documented consent decision for the widget, in-app experiences, analytics, and optional session replay

The Account ID in the generated browser snippet is public. Never place API keys, access tokens, signing secrets, private identity-verification material, or server credentials in GTM.

Decide whether GTM should own the installation

Use GTM when your organization already reviews and deploys third-party browser tags through the container and can test consent, tag order, and data-layer values.

Prefer application code when:

  • authentication and tenant changes are easier to express in application state
  • a strict Content Security Policy prohibits Custom HTML
  • the product event must be emitted atomically with application code
  • engineering wants SDK lifecycle changes reviewed with the application deployment

GTM changes how the browser integration is deployed. It does not remove engineering ownership of stable IDs, consent, event semantics, or UI regression testing.

1. Define a namespaced data-layer contract

Push values with dataLayer.push(); do not replace the data-layer array.

After the application knows the authenticated person and active account, push only the approved fields:

<script>
  window.dataLayer = window.dataLayer || [];
  window.dataLayer.push({
    event: "userorbit_identify",
    userorbit: {
      userId: "USER_ID_FROM_YOUR_APP",
      email: "person@example.com",
      name: "Jane Doe",
      attributes: {
        "user.role": "admin",
        "account.id": "acct_42",
        "account.name": "Example account",
        "account.plan": "growth"
      }
    }
  });
</script>
HTML

Use opaque application IDs where possible. Email and name are optional; push them only when your privacy basis and consent flow allow it.

The current Userorbit web SDK identifies a person. It does not expose a separate company or group identification method. For multi-tenant B2B applications, keep the active tenant in stable custom attributes such as account.id, account.name, and account.plan.

Create these GTM Data Layer Variables:

GTM variable Data Layer Variable Name Default
DLV - Userorbit User ID userorbit.userId empty
DLV - Userorbit Email userorbit.email empty
DLV - Userorbit Name userorbit.name empty
DLV - Userorbit Attributes userorbit.attributes {}
DLV - Userorbit Event Name userorbitEvent.name empty
DLV - Userorbit Event Properties userorbitEvent.properties {}

Keep this schema consistent across application code, GTM, and Userorbit targeting.

2. Create the SDK bootstrap tag

  1. Open Userorbit → Settings → Widget.
  2. Select Google Tag Manager.
  3. Copy the generated snippet for the intended workspace and audience.
  4. In GTM, create a Custom HTML tag named Userorbit - Bootstrap.
  5. Paste the generated snippet.

The generated code loads https://cdn.userorbit.com/userorbit.umd.cjs asynchronously and calls window.userorbit.init() with the current workspace configuration.

To make later GTM tags wait for initialization, adapt the generated script.onload handler so it stores the returned promise and emits a readiness event:

<!-- START Userorbit SDK -->
<script>
  (function () {
    var apiHost = "https://api.userorbit.com";
    var accountId = "YOUR_PUBLIC_ACCOUNT_ID";
    var script = document.createElement("script");

    script.type = "text/javascript";
    script.async = true;
    script.src = "https://cdn.userorbit.com/userorbit.umd.cjs";
    script.onload = function () {
      window.userorbitReady = Promise.resolve(window.userorbit.init({
        accountId: accountId,
        apiHost: apiHost,
        floatingWidget: true
      })).then(function () {
        window.dataLayer.push({ event: "userorbit_ready" });
        return window.userorbit;
      });
    };
    script.onerror = function () {
      console.error("Userorbit SDK failed to load");
    };

    document.head.appendChild(script);
  })();
</script>
<!-- END Userorbit SDK -->
HTML

Before using this example, compare apiHost, accountId, widget options, and audience behavior with the current generated snippet in your workspace. Do not copy an Account ID from another environment.

Use an Initialization - All Pages trigger only if your consent policy allows Userorbit to load at that stage. Otherwise use your consent-management platform's approved event or GTM consent checks.

3. Create the identity tag

Create a second Custom HTML tag named Userorbit - Identify:

<script>
  (function () {
    var ready = window.userorbitReady;
    var userId = {{DLV - Userorbit User ID}};
    var email = {{DLV - Userorbit Email}};
    var name = {{DLV - Userorbit Name}};
    var attributes = {{DLV - Userorbit Attributes}} || {};

    if (!ready || !userId) return;

    ready.then(function (userorbit) {
      return userorbit.identify(userId, {
        email: email || undefined,
        name: name || undefined,
        attributes: attributes
      });
    });
  })();
</script>
HTML

Fire this tag on both:

  • the userorbit_ready Custom Event, so identity already in the data layer is applied after initialization
  • the userorbit_identify Custom Event, so later sign-in or tenant changes update the session

If one person switches accounts without signing out, push a new userorbit_identify event with the new account.* values.

When the application signs out, push a userorbit_logout event and fire this tag:

<script>
  if (window.userorbitReady) {
    window.userorbitReady.then(function (userorbit) {
      return userorbit.logout();
    }).then(function () {
      window.userorbitReady = undefined;
    });
  }
</script>
HTML

Do not let a later sign-in inherit the previous person's Userorbit session in a shared browser. If your single-page application supports sign-out and sign-in without a reload, ensure the bootstrap lifecycle runs again before the next identity event, or move lifecycle ownership into application code.

4. Forward only configured product events

Create the code event in Userorbit before forwarding it. The application should push the event only after the real product action succeeds:

window.dataLayer.push({
  event: "userorbit_event",
  userorbitEvent: {
    name: "workspace_created",
    properties: {
      workspaceId: workspace.id,
      template: workspace.templateKey,
    },
  },
})
TypeScript

Create a Custom Event trigger for userorbit_event, then create a Custom HTML tag named Userorbit - Track configured event:

<script>
  (function () {
    var ready = window.userorbitReady;
    var eventName = {{DLV - Userorbit Event Name}};
    var properties = {{DLV - Userorbit Event Properties}} || {};

    if (!ready || !eventName) return;

    ready.then(function (userorbit) {
      return userorbit.track(eventName, {
        hiddenFields: properties
      });
    });
  })();
</script>
HTML

Keep hiddenFields values to strings, numbers, or arrays of strings. Do not forward nested customer objects, credentials, message bodies, or arbitrary form data.

Userorbit owns the event-to-experience or event-to-checklist-task configuration. GTM forwards the application event; it does not create event definitions automatically.

Google Consent Mode does not automatically govern a non-Google Custom HTML tag. Apply the same consent decision to bootstrap, identity, and event tags.

With basic blocking, do not fire the tags until your consent-management platform emits the approved state. In Advanced Settings → Consent Settings, require the consent type your policy maps to this processing, or use the CMP's consent-granted trigger.

If an application event occurs while the tags are blocked, GTM will not automatically reconstruct that business event later. Your application must decide whether replay is allowed and technically correct.

The Userorbit initialization configuration can disable analytics, session replay, or in-app delivery separately:

analytics: { enabled: false },
sessionReplay: { enabled: false },
inApp: { enabled: true }
JavaScript

These flags do not replace consent management or legal review. If consent changes at runtime, validate the supported reinitialization path for the SDK version you deploy.

6. Apply security and governance controls

  • Keep secrets and private customer data out of GTM and browser code.
  • Treat anyone with GTM publish access as capable of changing browser JavaScript and data collection.
  • Test script-src https://cdn.userorbit.com and connect-src https://api.userorbit.com in your Content Security Policy. Do not widen CSP to *.
  • Use separate staging and production GTM environments or container versions.
  • Record the change owner, version notes, approval, and rollback plan.
  • If your organization prohibits Custom HTML, install Userorbit in application code or build and review a private GTM template. Do not weaken the policy.

7. Handle single-page navigation only when needed

The Userorbit SDK observes common pushState, replaceState, popstate, and hash changes. Verify route events before adding a GTM History Change tag.

If Analytics → Live Events misses a real client-side navigation, create a History Change trigger and this fallback tag:

<script>
  if (window.userorbitReady) {
    window.userorbitReady.then(function (userorbit) {
      return userorbit.registerRouteChange();
    });
  }
</script>
HTML

Retest. If one navigation produces two $uo_web_page_view events, remove the fallback because automatic detection already covers the router.

8. Debug and verify before publishing

Start with GTM Preview and Tag Assistant, then continue through the Userorbit layers. A fired GTM tag proves only that GTM executed the tag; it does not prove that Userorbit initialized, identified the intended person, or delivered an experience.

Layer Tool Passing evidence
Container GTM Preview / Tag Assistant Bootstrap fired under the intended consent state
Variables Tag Assistant Variables Test user ID and namespaced attributes resolve as expected
Script Browser Network userorbit.umd.cjs loads successfully
API Browser Network and Console No CSP, CORS, initialization, or rejected request error
SDK Browser Console window.userorbit exposes the expected methods
Connection Userorbit → Settings → Widget The workspace reports recent SDK activity
Environment Userorbit → Analytics → Live Events URL and user match the staging session
Identity Userorbit contact view Stable user ID and expected account.* attributes
Targeting Eligible and ineligible staging sessions Only the intended user receives the experience
Delivery Real tour or checklist run Progress, completion, or dismissal is recorded
Product event Real success action The configured experience or checklist task responds once

Publish the GTM container only after every required layer passes.

Troubleshooting

Tag Assistant says “Fired,” but Userorbit shows no activity

  • Inspect the CDN and API requests; Tag Assistant does not prove that initialization succeeded.
  • Check the browser Console for a rejected initialization promise.
  • Confirm the Account ID and API host came from the same workspace.
  • Confirm that CSP, consent, or a privacy extension did not block the runtime.

Identity variables are undefined

  • Confirm the application pushed the userorbit object before userorbit_identify.
  • Confirm each Data Layer Variable path matches the namespaced key exactly.
  • If bootstrap runs before authentication, keep it anonymous and emit userorbit_identify after auth resolves.

A product event is dropped

  • Confirm window.userorbitReady exists before the event tag runs.
  • Confirm consent did not block the tag.
  • Create the code-event key in Userorbit and match its case exactly.
  • Keep the properties within the supported value types.

The wrong account receives an experience

  • Push a new account.id before the tenant-change identity event.
  • Confirm the targeting rule reads the same attribute key and value vocabulary.
  • Call logout() between people on a shared browser.
  • Check for stale data-layer values in Tag Assistant.

Implementation ownership

GTM provides the container, variables, triggers, consent checks, environments, Preview mode, and publication workflow. Userorbit provides the browser SDK, identity and custom attributes, configured code events, targeting, tours, checklists, Live Events, and delivery analytics. Your application owns the source data, authentication timing, event success boundary, tenant switching, privacy basis, CMP behavior, CSP, and regression testing.

For additional SDK failure modes, see SDK Troubleshooting Reference in the Userorbit help center.

Was this helpful?