@self-vectra/sdk
v0.2.3
Published
Vectra analytics browser SDK
Readme
@self-vectra/sdk
Browser analytics SDK for Vectra — self-hosted product analytics. Autocapture (pageview, clicks, forms), behavioral events (rage click, dead click, scroll depth), and metadata enrichment. Batches events and sends to your server.
Install
npm install @self-vectra/sdkOr load via script tag (global Vectra):
<script src="https://unpkg.com/@self-vectra/sdk/dist/vectra.min.js"></script>Usage
Vanilla / any framework
import vectra from '@self-vectra/sdk';
vectra.init({
apiKey: 'pk_test_xxxxxxxx',
apiHost: 'https://vectra.yourdomain.com',
});
// Autocapture is on by default: pageview, click, form submit, history changes.
// Behavioral: rage click, dead click, scroll depth (25/50/75/100%).
// Optional: custom events and identify
vectra.track('signup', { plan: 'pro' });
vectra.identify('user_123');
vectra.page(); // manual page view if needed
vectra.flush(); // flush queue now
await vectra.shutdown(); // flush and stop (e.g. on app unload)Next.js (React)
Wrap your app with VectraProvider so the SDK initializes once on the client:
// app/layout.tsx
import { VectraProvider } from '@self-vectra/sdk';
export default function RootLayout({ children }) {
return (
<html>
<body>
<VectraProvider
apiKey="pk_test_xxx"
apiHost="https://vectra.yourdomain.com"
>
{children}
</VectraProvider>
</body>
</html>
);
}Then use vectra anywhere (e.g. in components or server components don’t run in browser, so use in client components):
'use client';
import vectra from '@self-vectra/sdk';
vectra.track('button_clicked', { name: 'pricing_cta' });Configuration
| Option | Type | Default | Description |
|-----------------|---------|---------|-------------|
| apiKey | string | — | Required. Project API key (ingest scope). |
| apiHost | string | — | Required. Vectra server base URL (no trailing slash). |
| flushInterval | number | 5000 | Ms between batch flushes. |
| batchSize | number | 20 | Max events per batch. |
| maxRetries | number | 3 | Retries with exponential backoff on send failure. |
| debug | boolean | false | Log send attempts and results to the console (for debugging). |
| maskText | boolean | true | Strip element text longer than 200 chars. |
| maskInputs | boolean | true | Never capture password, email, textarea. |
Event types (autocapture + behavioral)
$pageview— On load,pushState,replaceState,popstate. Properties:page_url,pathname,referrer,title.$click— Every click. Properties:element_tag,element_text,element_id,element_class,element_href,css_selector,click_x,click_y.$form_submit— Form submit. Properties:form_id,form_action,form_method,input_count(no input values).$rage_click— 3+ clicks within 1.5s and 30px. Properties:click_count,element_selector,page_url.$dead_click— Click with no navigation and no DOM change within 2s. Properties:element_selector,page_url.$scroll_depth— When user reaches 25%, 50%, 75%, 100%. Properties:depth_percent,page_url.
All events include context: page_url, referrer, browser, os, device, screen_resolution, timezone, language. Session ID (30min inactivity) and distinct ID are sent on every event. Geo is not captured in the browser; the server can enrich from IP (GeoIP).
API
init(config)— Initialize the SDK (call once). Enables autocapture and behavioral listeners.track(eventName, properties?)— Send a custom event.page(properties?)— Send a page view (also sent automatically on navigation).identify(distinctId)— Set user ID for subsequent events (stored inlocalStorage).flush()— Flush the queue immediately (returns a Promise).shutdown()— Flush remaining events and stop the timer (returns a Promise).getDistinctId()/getSessionId()— Read current IDs.
Events are sent as POST /api/v1/event/batch with header X-API-Key. Batches run every 5s or when the queue reaches 20 events, with up to 3 retries and exponential backoff.
Debugging
- Browser: Set
debug: trueininit()to see[Vectra]logs in the console: when a batch is sent, success (status +acceptedcount), or failure (status/error and retries). Use this to confirm the SDK is sending and whether the server responds. - Server (Docker): To see if requests reach the API, run
docker compose -f docker/docker-compose.yml logs api -f. Each batch is logged asevent/batch receivedwithproject_id,accepted,requested, andorigin. If you see no such lines when the SDK sends, the request is not reaching the API (e.g. CORS, network, or wrong URL).
License
MIT
