Skip to main content

Web Beacon

The kenbun Web Beacon is a lightweight JavaScript snippet that automatically tracks visitor behavior on your website. Install it once and start capturing page views, scroll depth, engagement time, and custom events — all without writing any tracking code.

What It Does

The beacon provides real-time behavioral intelligence:

  • Automatic Tracking: Page views, scroll depth, engagement time, outbound clicks
  • Custom Events: Track button clicks, form submissions, and other interactions via API
  • DataLayer Interception: Optionally capture GTM dataLayer.push() events like purchases, form submissions, and video interactions
  • Visitor Identification: Associate anonymous visitors with email/ID when they identify themselves
  • Passive Idle Detection: Distinguishes active engagement from idle time
  • Session Continuity: Maintains visitor identity across pages and sessions
  • Works with Chrome Extension: Receives events from the Chrome Extension visual tagger

The beacon is built for performance: lightweight (~5 KB gzipped), non-blocking, and privacy-friendly.

Quick Start

Installation

  1. Navigate to Settings → Integrations → Web in kenbun
  2. Copy the beacon snippet (it includes your unique token)
  3. Paste the snippet in the <head> section of your website (before </head>)
  4. Deploy to production

Govern Integrations Web page showing token configuration, beacon snippet with copy button, and tracking code examples

Example snippet:

<script src="https://app.kenbun.io/tracker.js"
data-token="YOUR_BEACON_TOKEN"
data-endpoint="https://app.kenbun.io/ingest"
defer></script>

Replace YOUR_BEACON_TOKEN with the actual token from your kenbun settings. Tokens are scoped to your Organization Unit and enforce an origin allowlist for security.

How Tokens Work

  • Each beacon token is unique to your OU
  • Tokens include an origin allowlist (domains where the token is valid)
  • No sensitive credentials are exposed in the browser
  • Tokens cannot be used from unauthorized domains, preventing token theft and abuse
  • Tokens can be rotated in Settings → Integrations → Web

Automatic Tracking

The beacon automatically captures page_view events with structured metadata:

  • Page context: path, full url, referrer, title, language, user_agent
  • UTM params: utm_source, utm_medium, utm_campaign, utm_term, utm_content
  • Dimensions: screen.width/height, viewport.width/height
  • scroll_percent: Maximum scroll depth (0–100)
  • Engagement metrics (see below)

Engagement Metrics

kenbun automatically tracks how engaged visitors are with your content. The beacon distinguishes between active engagement (when someone is reading, scrolling, or interacting) and idle time (when the tab is open but there's no activity).

MetricDescriptionExample
engaged_time_msTime actively engaging with the page180000 (3 minutes)
idle_time_msTime when the page was open but inactive720000 (12 minutes)
times_went_idleNumber of times the visitor stopped interacting2

Why this matters:

  • Lead Scoring: Use engaged time to identify high-intent leads. Someone who spends 8 minutes actively reading your pricing page is more qualified than someone who glanced at it for 30 seconds.
  • Content Performance: High scroll percentage + high engaged time = compelling content that resonates.
  • Visitor Segmentation: Engaged readers (high engaged, low idle), researchers (multiple visits, consistent engagement), quick scanners (low engaged, high scroll).
{
"engaged_time_ms": 180000,
"idle_time_ms": 720000,
"times_went_idle": 2,
"scroll_percent": 85
}

The legacy time_visible_ms field still exists for backward compatibility but reports the same value as engaged_time_ms. Use engaged_time_ms for all new integrations and scoring rules.

Other Automatic Events

Event TypeWhen It FiresKey Metadata
outbound_link_clickVisitor clicks an external linkhref, element_text, url
page_scrolledVisitor scrolls past 90% of the pagescroll_percent, url
page_unloadedVisitor leaves the page (navigates, closes)engaged_time_ms, idle_time_ms, times_went_idle, scroll_percent, url

Custom Events

Track custom interactions on your website using the beacon API.

Track an Event

window.kenbun.push(['track', 'Event Name', { metadata_key: 'value' }]);
  • Event Name (string): Name in Title Case (e.g., CTA Click, Video Play)
  • metadata (object): Key-value pairs with event details
// Track a button click
window.kenbun.push(['track', 'Pricing CTA Click', {
button: 'Get Started',
plan: 'Enterprise'
}]);

// Track video engagement
window.kenbun.push(['track', 'Video Play', {
video_id: 'demo_2024',
duration: 120
}]);

Identify a Visitor

Associate an anonymous visitor with their email or external ID.

window.kenbun.push(['identify', {
email: 'user@example.com',
external_id: 'user_123',
phone: '+1234567890'
}]);

When to identify: after user logs in, after form submission (if you capture email), when user verifies email, or when user creates an account. Once identified, all subsequent events are linked to that lead.

DataLayer Interception

If your website uses Google Tag Manager (GTM) or pushes events to window.dataLayer, the beacon can automatically capture those events and send them to kenbun. This gives you visibility into video interactions, form submissions, demo requests, and other events already flowing through GTM — without duplicating tracking code.

DataLayer interception is disabled by default. Enable it by adding the data-datalayer-events attribute to your beacon script tag.

Configuration Options

Attribute ValueBehavior
(attribute not present)DataLayer interception is completely disabled (default)
data-datalayer-events="*"Capture all non-GTM-internal dataLayer events
data-datalayer-events="demo_requested,trial_started"Capture only the listed events (comma-separated, case-insensitive)

Capture specific events:

<script src="https://app.kenbun.io/tracker.js"
data-token="YOUR_BEACON_TOKEN"
data-endpoint="https://app.kenbun.io/ingest"
data-datalayer-events="purchase,add_to_cart,generate_lead"
defer></script>

Capture all events:

<script src="https://app.kenbun.io/tracker.js"
data-token="YOUR_BEACON_TOKEN"
data-endpoint="https://app.kenbun.io/ingest"
data-datalayer-events="*"
defer></script>

How It Works

When enabled, the beacon intercepts calls to dataLayer.push() and forwards matching events to kenbun. Each intercepted event is sent with the event type DataLayer: <event_name> and includes the full dataLayer entry as structured metadata.

GTM internal events are always excluded. Events like gtm.js, gtm.dom, gtm.load, gtm.click, gtm.linkClick, gtm.scrollDepth, gtm.formSubmit, and gtm.historyChange are filtered out automatically.

When to Use Each Mode

  • Specific events (recommended for most teams): You know which GTM events matter and want predictable scoring rules.
  • All events (*): You are exploring what flows through your dataLayer, or you have a small number of custom events.
  • Disabled (default): You don't use GTM, or you prefer to track exclusively through the beacon API or Chrome Extension.

Example

When dataLayer.push({ event: 'demo_requested', form_name: 'Request a Demo', plan: 'enterprise' }) fires, kenbun receives:

  • Event type: DataLayer: demo_requested
  • Metadata: The full dataLayer entry including form_name and plan

You can then create scoring rules that award points for DataLayer: demo_requested or use triggers to notify sales when high-intent actions occur.

Interaction with Chrome Extension

If you also use the Chrome Extension, both the beacon and the extension can capture dataLayer events independently. To avoid duplicates, choose one approach per site:

  • Beacon-only: Configure data-datalayer-events on the script tag (recommended for production)
  • Extension-only: Configure the allowlist in the Chrome Extension (useful for sites where you cannot modify the beacon snippet)

Performance and Privacy

Performance:

  • Small footprint (~5 KB gzipped)
  • Non-blocking (defer attribute)
  • Efficient batching with keepalive for reliability
  • No cookies except an anonymous visitor ID

Privacy:

  • Anonymous by default — no PII collected until visitor identifies themselves
  • Visitor ID cookie is first-party only (not cross-site tracking)
  • No third-party sharing — data sent only to kenbun
  • Origin allowlist — tokens only work on authorized domains. Beacon tokens are browser-only credentials; every request must carry an Origin header that matches one of the allowed origins on the token. Requests without a browser Origin (such as curl, server-side scripts, or backend integrations) are rejected. For server-to-server event ingestion, use a Personal Access Token instead.

Browser Support: Modern browsers (Chrome, Firefox, Safari, Edge). IE11 and older browsers degrade gracefully (beacon won't load).

Troubleshooting

Events Not Appearing in kenbun

Check the browser console (F12 → Console tab):

SymptomLikely Cause
No errorsBeacon loaded successfully
401 UnauthorizedToken is invalid or expired (regenerate in Settings)
403 ForbiddenDomain not in origin allowlist (add it to the token's allowed origins). For server-to-server callers without a browser Origin header, use a Personal Access Token instead
Network errordata-endpoint URL is incorrect or backend unreachable

"Beacon Not Found on Page" (Chrome Extension)

The beacon script hasn't loaded yet or isn't installed. Verify the snippet is in <head>, check the network tab for the tracker.js request, and refresh the page after installing.

Double Page Views

Beacon snippet included multiple times (e.g., in both header and footer). Remove duplicates — the beacon should only be included once.

DataLayer Events Not Appearing

DataLayer interception is disabled by default. Add data-datalayer-events="*" (or specific event names) to the script tag. Verify your GTM container is firing events (check the console for dataLayer.push() calls). Confirm the event name is not a GTM internal event. If using a specific event list, check that names match exactly (case-insensitive).

Tracking Doesn't Work on Localhost

The beacon token's origin allowlist doesn't include localhost. Add http://localhost:3000 (or your local port) to the token's allowed origins in Settings → Integrations → Web.

Advanced Configuration

Custom Endpoint

For self-hosted deployments, set a custom endpoint:

<script src="https://your-domain.com/tracker.js"
data-token="YOUR_BEACON_TOKEN"
data-endpoint="https://your-kenbun-api.com/ingest"
defer></script>

Testing on Staging

Create a separate beacon token for staging environments:

  1. In Settings → Integrations → Web, click Create Token
  2. Name it "Staging" and add staging domains to allowed origins
  3. Use this token in your staging environment

Web beacon settings page showing the Tokens and Allowlist section with a token creation form, existing tokens table, the Installation snippet section with embed code, and Tracking Events code examples

This keeps staging events separate from production.

API Reference

window.kenbun.push()

All beacon interactions use the push method. Both commands are fire-and-forget (no return value).

// Track an event
window.kenbun.push(['track', 'Event Name', { metadata }]);

// Identify a visitor
window.kenbun.push(['identify', { email, external_id, phone }]);

Script Tag Attributes

AttributeRequiredDescription
data-tokenYesYour beacon token from Settings → Integrations → Web
data-endpointNoCustom ingest endpoint URL (defaults to kenbun SaaS)
data-datalayer-eventsNoEnable dataLayer interception: "*" for all events, or comma-separated event names
deferRecommendedLoad script without blocking page rendering

Notes

  • The beacon uses keepalive so events are sent even when the page is closing
  • No credentials sent — bearer token authentication only
  • Anonymous visitor ID stored in a first-party cookie (_lv_vid, preserved for backward compatibility)
  • Multiple events may be sent in a single request for efficiency
  • DataLayer interception is opt-in via data-datalayer-events