Skip to content

JavaScript SDK

The @graph8/js SDK gives you typed access to every graph8 capability from any JavaScript or TypeScript project. 14 modules, one g8.init() call.

Installation

Terminal window
npm install @graph8/js

Auth Modes

The SDK has two auth modes depending on what you’re building:

ModeKeyUse caseSafe in browser?
Client-sidewriteKeyTracking, visitor ID, copilot, chat, calendar, formsYes
Server-sideapiKeyEnrichment, sequences, campaigns, integrations, voice, pagesNo
// Client-side (browser)
g8.init({ writeKey: 'YOUR_WRITE_KEY' });
// Server-side (Node.js)
g8.init({ apiKey: 'YOUR_API_KEY' });
// Both (full access)
g8.init({ writeKey: 'YOUR_WRITE_KEY', apiKey: 'YOUR_API_KEY' });

Quick Start

import { g8 } from '@graph8/js';
g8.init({ writeKey: 'YOUR_WRITE_KEY' });
// Track events
g8.track('signup', { plan: 'pro', source: 'landing_page' });
// Identify users
g8.identify('user@acme.com', {
name: 'Jane Smith',
company: 'Acme Corp',
job_title: 'VP Engineering',
});
// Know who's visiting
const visitor = await g8.visitors.identify();
// { company_name: 'Acme Corp', industry: 'SaaS', employee_count: '200-500' }
// Open AI copilot
g8.copilot.open({ greeting: 'How can I help?' });
// Show booking widget
g8.calendar.show({ username: 'thomas', eventType: 'demo-30min' });

React / Next.js

app/layout.tsx
import { G8Provider } from '@graph8/js/react';
export default function RootLayout({ children }) {
return (
<G8Provider writeKey="YOUR_WRITE_KEY">
{children}
</G8Provider>
);
}
// Any component
import { useG8 } from '@graph8/js/react';
function PricingPage() {
const { track, visitors, copilot, calendar } = useG8();
useEffect(() => {
visitors.identify().then(v => {
if (v.company_name) setCompany(v.company_name);
});
}, []);
return (
<button onClick={() => {
track('book_demo', { page: 'pricing' });
calendar.show({ username: 'thomas', eventType: 'demo' });
}}>
Book a Demo
</button>
);
}

The hook returns: track, identify, page, reset, visitors, copilot, chat, calendar, forms, signals, and g8 (the full client).


Visitor Intelligence

Identify anonymous visitors by IP address - know which company is on your site before they fill out a form.

// Resolve visitor's company
const visitor = await g8.visitors.identify();
// {
// company_name: 'Acme Corp',
// company_domain: 'acme.com',
// industry: 'SaaS',
// employee_count: '200-500',
// city: 'San Francisco',
// country: 'United States',
// confidence: 0.92
// }
// Get engagement score
const score = await g8.visitors.score();
// { engagement: 82, intent: 'high', signals: ['pricing_page', 'case_study'] }
// React to high-intent visitors in real-time
const stop = g8.visitors.onIntent('high', (visitor) => {
showBanner(`${visitor.company_name} is checking us out!`);
g8.copilot.open(); // proactively open copilot
});
// Stop listening
stop();

AI Copilot

Embed an AI assistant in your product that knows your org’s knowledge base.

// Open as a floating widget
g8.copilot.open({
greeting: 'Hi! How can I help you today?',
position: 'bottom-right', // or 'bottom-left'
theme: 'dark', // 'light', 'dark', or 'auto'
});
// Send a message programmatically
const answer = await g8.copilot.ask('What integrations do you support?');
// Register custom actions the AI can trigger
g8.copilot.registerAction('book_demo', async (params) => {
router.push(`/book?date=${params.date}`);
});
// Listen for events
g8.copilot.on('tool_used', (data) => {
analytics.track('copilot_action', data);
});
// Close
g8.copilot.close();

Webchat

Live chat + AI chat embedded in your product.

// Open chat widget
g8.chat.open({
position: 'bottom-right',
theme: 'auto',
greeting: 'Hi! Ask me anything.',
});
// Send a message
g8.chat.send('I need help with billing');
// Listen for events
g8.chat.on('message', (msg) => { /* new message from agent */ });
g8.chat.on('human_transfer', () => { /* transferred to human */ });
// Configure appearance
g8.chat.configure({
position: 'bottom-left',
avatar: '/logo.png',
});
// Close
g8.chat.close();

Calendar Booking

Embed scheduling directly in your product - no Calendly redirect.

// Show as a modal overlay
g8.calendar.show({
username: 'thomas',
eventType: 'demo-30min',
prefill: { name: 'Jane', email: 'jane@acme.com' },
});
// Embed inline in a container
g8.calendar.embed('#booking-container', {
username: 'thomas',
eventType: 'discovery-call',
});
// Get available slots programmatically
const slots = await g8.calendar.slots('thomas', 'demo-30min', {
start: '2026-04-07',
end: '2026-04-11',
});
// Book programmatically
const booking = await g8.calendar.book({
event_type_id: 123,
slot: '2026-04-08T10:00:00Z',
attendee: { name: 'Jane', email: 'jane@acme.com' },
});
// Listen for bookings
g8.calendar.on('booked', (booking) => {
showConfirmation(booking);
});

Progressive Forms

Smart forms that skip fields graph8 already knows - higher conversion, same data.

// Check what's already known
const result = await g8.forms.lookup('user@acme.com');
if (result.found) {
console.log('Known:', result.known_fields);
// { name: 'Jane Smith', company: 'Acme Corp' }
console.log('Still need:', result.missing_fields);
// ['phone', 'job_title']
}

Enrichment

// Initialize with API key
g8.init({ apiKey: 'YOUR_API_KEY' });
// Look up a person (1 credit)
const person = await g8.enrich.person({ email: 'jane@acme.com' });
// { found: true, confidence: 0.95, data: { name, title, company, phone, linkedin, ... } }
// Look up a company (1 credit)
const company = await g8.enrich.company({ domain: 'acme.com' });
// { found: true, data: { name, industry, revenue, headcount, tech_stack, ... } }
// Verify an email (1 credit)
const result = await g8.enrich.verifyEmail('jane@acme.com');
// { email: 'jane@acme.com', valid: true, deliverable: true, catch_all: false }
// Search 300M+ contacts with filters
const leads = await g8.enrich.search([
{ field: 'seniority_level', operator: 'any_of', value: ['VP', 'Director'] },
{ field: 'company_industry', operator: 'contains', value: ['SaaS'] },
{ field: 'company_employee_count', operator: 'between', value: [50, 500] },
], 1, 25);

Intent Signals

Know when target accounts are in-market.

// Get signals for a specific company
const signals = await g8.signals.company('acme.com');
// { domain: 'acme.com', score: 87, intent: 'high', signals: ['pricing_3x', 'case_study'] }
// Stream signals for multiple domains (polls every 30s)
const stop = g8.signals.stream(['acme.com', 'startup.io'], (signals) => {
const hot = signals.filter(s => s.intent === 'high');
if (hot.length > 0) notifySDR(hot);
});
// Stop streaming
stop();

Sequences

// List available sequences
const sequences = await g8.sequences.list();
// Add contacts to a sequence
await g8.sequences.add({
sequenceId: sequences[0].id,
contactIds: [5028106, 5028105],
listId: 637,
});

Campaigns

// List campaigns
const campaigns = await g8.campaigns.list();
// Create a campaign
const campaign = await g8.campaigns.create({
name: 'Q2 Enterprise Push',
category: 'Outbound',
target_persona: 'VP Engineering at SaaS 200-1000',
});
// Launch
await g8.campaigns.launch(campaign.id);
// Get stats
const stats = await g8.campaigns.stats(campaign.id);
// { sent: 500, opened: 230, replied: 45, meetings: 12 }

CRM Integrations

// List connected CRMs
const integrations = await g8.integrations.list();
// Connect a new CRM
await g8.integrations.connect('hubspot', { apiKey: '...' });
// Trigger sync
await g8.integrations.sync('hubspot', { direction: 'bidirectional' });

Analytics

const overview = await g8.analytics.overview({ period: '30d' });
// { visitors: 12500, contacts_created: 340, emails_sent: 2100, replies: 89, meetings_booked: 23 }

Voice AI

// Start an AI voice call
const session = await g8.voice.start({
agent: 'sales-discovery',
contactId: 123,
});
// Get call analysis after completion
const analysis = await g8.voice.analysis(session.id);
// { sentiment: 'positive', summary: '...', next_steps: [...], objections: [...] }

Landing Pages

// Clone from any URL
const page = await g8.pages.clone('https://competitor.com/pricing');
// Create from template
const page = await g8.pages.create({
template: 'lead_magnet',
title: 'The Future of Sales',
});
// Publish to CDN
const { url } = await g8.pages.publish(page.id);
// https://g8-lp-abc12345.pages.dev

Webhooks

Listen for events from graph8 (server-side).

g8.webhooks.on('reply_received', (event) => {
slack.send(`${event.contact} replied to ${event.sequence}`);
});
g8.webhooks.on('meeting_booked', (event) => {
crm.updateDeal(event.dealId, { stage: 'meeting' });
});
// Stop all listeners
g8.webhooks.stop();

Available events: reply_received, meeting_booked, contact_enriched, contact_created, sequence_completed, campaign_launched, form_submitted, visitor_identified


Privacy

g8.init({
writeKey: 'YOUR_WRITE_KEY',
privacy: {
dontSend: true, // Disable all cookies and event sending
dontStoreUserIds: true, // Don't store user identifiers
ipPolicy: 'remove', // 'keep' | 'stripLastOctet' | 'remove'
},
});

SSR Support

All methods are no-ops on the server and execute on the client after hydration. Safe in Next.js, Nuxt, Remix, and any SSR framework.

Config Options

OptionTypeDefaultDescription
writeKeystring-Write key for client-side features
apiKeystring-API key for server-side features
hoststringhttps://t.graph8.comTracking host URL
apiUrlstringhttps://be.graph8.comBackend API URL
debugbooleanfalseEnable debug logging
privacy.dontSendbooleanfalseDisable cookies and event sending
privacy.dontStoreUserIdsbooleanfalseDon’t store user identifiers
privacy.ipPolicystringkeepkeep, stripLastOctet, or remove

Get Your Keys

  1. Go to graph8 Settings > MCP & API
  2. Write key is in the tracking snippet section (client-side)
  3. API key is in the API tab (server-side)