vTilt
Why vTiltHow It WorksFeaturesFAQDocs
Docs / Script bundles
Quick startEvent forwarding
MCP server
Guides
OverviewAuthenticationOAuthAgent skills (prompts)AI intelligenceGoogle Ads
Client setup
CursorClaude DesktopVS CodeCodex
Realtime
Debug ViewRealtime Dashboard
Integration guides
Frontend frameworks
Next.jsNuxt.jsVue.jsReactReact RouterRemixGatsbySvelte / SvelteKitAstroAngularTanStack StartDocusaurus
Backend frameworks
NestJSHonoCloudflare WorkersDjangoFlaskLaravelPhoenixRuby on Rails
Backend languages
PythonPHPRubyElixirGoJava.NET / C#Rust
Stack guides
Vue + PHP
SDK
Browser SDK
InstallScript bundlesEvent trackingAutocaptureIdentify & aliasWeb VitalsSession recordingChat widgetFeature readinessRemote configurationReverse proxyDebug logging
Node SDK
Install & setupCapture, identify & aliasContext & shutdown

Documentation

vTilt
Quick startEvent forwarding

MCP server

Realtime

Debug ViewRealtime Dashboard

Integration guides

SDK

InstallScript bundlesEvent trackingAutocaptureIdentify & aliasWeb VitalsSession recordingChat widgetFeature readinessRemote configurationReverse proxyDebug logging
DocsBrowser SDKScript bundles

Script bundles

Choose the right browser SDK bundle — default lazy loading, chat-ready, or full single-file builds for script tags and npm.

The browser SDK ships as several pre-built files under /dist/. The default snippet loads array.js — a lightweight core that fetches optional features (chat.js, recorder.js, web-vitals.js) only when you enable them.

Pick a combined bundle when you want zero extra network requests for a feature, or when you call APIs like vt.sendChatMessage() immediately after page load.

#Quick picker

Your situationUse
Standard analytics sitearray.js (default snippet)
Chat widget with hero CTAs / instant sendChatMessage()array.chat.js
Session recording + web vitals, no lazy fetchesarray.full.js
Chat + recording + web vitals in one filearray.full.chat.js
npm / Vite / webpack appmodule.es.js or a module.*.es variant

#How lazy loading works

  1. The core bundle includes thin wrappers (ChatWrapper, session recording wrapper, …).
  2. When a feature needs its heavy code, the SDK checks window.__VTiltExtensions__.
  3. If the factory is missing, it loads {api_host}/dist/{feature}.js (or {script_host}/{feature}.js when script_host is set).
  4. If the factory is already present (combined bundle), no network request is made.

All public methods (vt.openChat(), vt.sendChatMessage(), vt.updateConfig(), …) are safe to call before the heavy code is ready — the SDK queues calls internally.

Script tag only: those methods must appear in the inline stub's method list (see Install — Script tag vs npm). npm imports do not use a stub; import vt from @v-tilt/browser or a module.*.es bundle and call methods directly.

#Script-tag bundles (IIFE)

Files are served from https://www.vtilt.com/dist/ on self-hosted setups, or from your script_host CDN when configured.

#array.js — core only (default)

<script src="https://www.vtilt.com/dist/array.js"></script>
html

Lazy-loads chat.js, recorder.js, and web-vitals.js on demand. Smallest initial download.

#array.chat.js — core + chat

Equivalent to loading array.js and chat.js together. Use when chat is enabled and visitors may open it immediately after page load.

<script src="https://www.vtilt.com/dist/array.chat.js"></script>
<script>
  vt.init('YOUR_PROJECT_TOKEN', {
    api_host: 'https://www.vtilt.com',
    chat: { enabled: true },
  })
</script>
html

See also Chat widget.

#array.full.js — core + recorder + web vitals

Pre-registers session recording and web vitals. Does not include chat (same split PostHog uses for conversations — chat is large and optional).

<script src="https://www.vtilt.com/dist/array.full.js"></script>
html

Pair with disable_external_dependency_loading: true if you never want runtime script injection:

vt.init('YOUR_PROJECT_TOKEN', {
  api_host: 'https://www.vtilt.com',
  disable_external_dependency_loading: true,
})
typescript

#array.full.chat.js — core + recorder + web vitals + chat

Single file when you need every optional browser feature pre-bundled.

<script src="https://www.vtilt.com/dist/array.full.chat.js"></script>
html

#.no-external variants

FileSame asUse with
array.full.no-external.jsarray.full.jsdisable_external_dependency_loading: true
array.chat.no-external.jsarray.chat.jsdisable_external_dependency_loading: true
array.full.chat.no-external.jsarray.full.chat.jsdisable_external_dependency_loading: true

#npm / ESM bundles

When you install @v-tilt/browser, the same artifacts live under dist/:

ImportPre-registered
@v-tilt/browser → module.es.js— (lazy)
@v-tilt/browser/dist/module.chat.eschat
@v-tilt/browser/dist/module.full.esrecorder, web vitals
@v-tilt/browser/dist/module.full.chat.esrecorder, web vitals, chat

Default lazy import:

import { vt } from '@v-tilt/browser'

vt.init('YOUR_PROJECT_TOKEN', { api_host: 'https://www.vtilt.com' })
typescript

Chat-ready single import:

import { vt } from '@v-tilt/browser/dist/module.chat.es'

vt.init('YOUR_PROJECT_TOKEN', {
  api_host: 'https://www.vtilt.com',
  chat: { enabled: true },
})
typescript

Or side-effect-import an extension before the core (PostHog-style):

import '@v-tilt/browser/dist/chat'
import { vt } from '@v-tilt/browser'

vt.init('YOUR_PROJECT_TOKEN', { api_host: 'https://www.vtilt.com', chat: { enabled: true } })
typescript

#Lazy extension files

These register on __VTiltExtensions__ and are fetched automatically when needed (unless you use a combined bundle above):

FileFeature
chat.jsChat widget
recorder.jsSession recording
web-vitals.jsWeb Vitals

#CDN and script_host

By default, lazy extensions load from {api_host}/dist/{name}.js. Set script_host to serve bundles from a CDN (no /dist/ prefix):

vt.init('YOUR_PROJECT_TOKEN', {
  api_host: 'https://www.vtilt.com',
  script_host: 'https://cdn.example.com',
})
// Lazy chat loads from: https://cdn.example.com/chat.js
// Core snippet should load: https://cdn.example.com/array.js
typescript

#Full reference

BundleFormatPre-registered extensions
array.jsIIFE—
array.chat.jsIIFEchat
array.full.jsIIFErecorder, web-vitals
array.full.chat.jsIIFErecorder, web-vitals, chat
module.es.jsESM—
module.chat.es.jsESMchat
module.full.es.jsESMrecorder, web-vitals
module.full.chat.es.jsESMrecorder, web-vitals, chat
main.jsCJS— (lazy)
PreviousInstallBrowser SDKNextEvent trackingBrowser SDK

On this page

  • Quick picker
  • How lazy loading works
  • Script-tag bundles (IIFE)
  • array.js — core only (default)
  • array.chat.js — core + chat
  • array.full.js — core + recorder + web vitals
  • array.full.chat.js — core + recorder + web vitals + chat
  • .no-external variants
  • npm / ESM bundles
  • Lazy extension files
  • CDN and script_host
  • Full reference