crexperium-sdk
v1.3.0
Published
Official TypeScript/JavaScript SDK for Crexperium CRM
Downloads
14
Maintainers
Readme
Crexperium SDK
Official TypeScript/JavaScript SDK for Crexperium CRM. Track events, manage contacts, and handle deals with ease in both Node.js and browser environments.
Features
- 🚀 Universal: Works in Node.js and browsers
- 📦 TypeScript: Full TypeScript support with type definitions
- 🔄 Auto-tracking: Automatic page view tracking for browsers
- 🎬 Session Replay: Record and replay user sessions with rrweb
- 🎯 Event Tracking: Track custom events and user interactions
- 👤 Contact Management: Identify and manage contacts
- 💼 Deal Management: Create and manage sales pipeline deals
- 🔌 Plugin System: Extensible plugin architecture
- ⚡ Retry Logic: Automatic retry with exponential backoff
- 🛡️ Error Handling: Comprehensive error classes
Installation
npm install crexperium-sdkQuick Start
Node.js
import { CRMClient } from 'crexperium-sdk';
// Initialize the client
const client = new CRMClient({
apiToken: process.env.CRX_API_TOKEN,
});
// Track an event
await client.events.track({
eventKey: 'purchase',
visitorId: 'user_123',
eventData: {
value: 99.99,
currency: 'USD',
productId: 'prod_456',
},
});
// Identify a contact
const { contact, created } = await client.contacts.identify({
externalId: 'user_123',
email: '[email protected]',
firstName: 'John',
lastName: 'Doe',
});
// Create a deal
const deal = await client.deals.create({
name: 'Enterprise Deal',
amount: 50000,
currency: 'USD',
contactEmail: '[email protected]',
priority: 'HIGH',
});Browser (ES Module)
<script type="module">
import { CRMClient } from 'https://cdn.jsdelivr.net/npm/crexperium-sdk/dist/index.mjs';
const client = new CRMClient({
apiToken: 'your-api-token',
autoPageView: true, // Automatically track page views
autoDeviceInfo: true, // Automatically collect device information
persistVisitorId: true, // Persist visitor ID in localStorage
});
// Track custom events
await client.events.track({
eventKey: 'button_click',
eventData: { button: 'signup' },
});
</script>Browser (UMD via CDN)
<script src="https://cdn.jsdelivr.net/npm/crexperium-sdk/dist/browser.js"></script>
<script>
const client = new Crexperium.CRMClient({
apiToken: 'your-api-token',
});
// The client is now available globally
client.events.track({
eventKey: 'page_load',
pageUrl: window.location.href,
});
</script>API Reference
Configuration
interface SDKConfig {
apiToken: string; // Required: Your API token
baseUrl?: string; // Optional: API base URL (default: https://crxperium.applikuapp.com)
timeout?: number; // Optional: Request timeout in ms (default: 30000)
maxRetries?: number; // Optional: Max retry attempts (default: 3)
retryDelay?: number; // Optional: Initial retry delay in ms (default: 1000)
// Browser-specific options
autoPageView?: boolean; // Optional: Auto-track page views (default: true)
autoDeviceInfo?: boolean; // Optional: Auto-collect device info (default: true)
persistVisitorId?: boolean; // Optional: Persist visitor ID (default: true)
visitorIdKey?: string; // Optional: localStorage key for visitor ID (default: 'crx_visitor_id')
// Session replay options
sessionReplay?: SessionReplayConfig; // Optional: Session replay configuration
}Events
Track a single event
await client.events.track({
eventKey: string; // Required: Event identifier
visitorId?: string; // Optional: Visitor ID
userProperties?: object; // Optional: User properties
eventData?: object; // Optional: Event data
pageUrl?: string; // Optional: Page URL
pageTitle?: string; // Optional: Page title
referrer?: string; // Optional: Referrer URL
userAgent?: string; // Optional: User agent
deviceType?: string; // Optional: Device type
browser?: string; // Optional: Browser name
os?: string; // Optional: Operating system
country?: string; // Optional: Country
city?: string; // Optional: City
eventTime?: Date | string; // Optional: Event timestamp
source?: 'web' | 'mobile' | 'server'; // Optional: Event source
});Track multiple events
await client.events.trackBatch([
{ eventKey: 'event1', eventData: { ... } },
{ eventKey: 'event2', eventData: { ... } },
// ... up to 100 events
]);Get event statistics
const stats = await client.events.stats(30); // Last 30 daysContacts
Identify a contact
const { contact, created } = await client.contacts.identify({
externalId: string; // Required: External ID
email?: string;
firstName?: string;
lastName?: string;
phone?: string;
title?: string;
company?: string;
customFields?: object;
});Create a contact
const contact = await client.contacts.create({
email: '[email protected]',
first_name: 'John',
last_name: 'Doe',
});Update a contact
const updated = await client.contacts.update(contactId, {
first_name: 'Jane',
lead_score: 85,
});List contacts
const { results } = await client.contacts.list({
lifecycle_stage: 'LEAD',
limit: 50,
});Deals
Create a deal
const deal = await client.deals.create({
name: 'Enterprise Deal',
amount: 50000,
currency: 'USD',
priority: 'HIGH',
contactEmail: '[email protected]',
expectedCloseDate: new Date('2024-12-31'),
});Move deal stage
await client.deals.moveStage(dealId, newStageId);List deals
const { results } = await client.deals.list({
status: 'OPEN',
priority: 'HIGH',
});Browser Plugins
Visitor ID Plugin
// Get current visitor ID
const visitorId = client.visitorId?.getVisitorId();
// Set a custom visitor ID
client.visitorId?.setVisitorId('custom-visitor-id');
// Reset visitor ID (generate new one)
client.visitorId?.resetVisitorId();Device Info Plugin
// Get device information
const deviceInfo = client.deviceInfo?.getDeviceInfo();
// Returns: { userAgent, deviceType, browser, os }
// Get specific device attributes
const deviceType = client.deviceInfo?.getDeviceType(); // 'desktop' | 'mobile' | 'tablet'
const browser = client.deviceInfo?.getBrowser(); // e.g., 'Chrome'
const os = client.deviceInfo?.getOS(); // e.g., 'Windows 10'Session Replay Plugin
The Session Replay plugin automatically records user sessions with DOM playback capabilities using rrweb. This powerful feature captures:
- 🎬 DOM Recording: Complete visual replay of user sessions
- 📊 Console Logs: Capture all console output (log, info, warn, error, debug)
- 🌐 Network Requests: Track all fetch/XHR requests with timing and status codes
- ⚠️ Error Capture: Automatic JavaScript error and unhandled rejection tracking
- ⚡ Performance Metrics: Navigation timing, Core Web Vitals (LCP, FID, CLS)
- 🔒 PII Masking: Automatic masking of emails, phone numbers, and credit cards
- 🎯 Custom Events: Log custom application events during the session
Basic Usage
const client = new CRMClient({
apiToken: 'your-api-token',
sessionReplay: {
enabled: true, // Enable session replay (default: true)
sampleRate: 1.0, // Record 100% of sessions (default: 1.0)
},
});
// Session replay starts automatically
// The current session is available at:
const session = client.sessionReplay?.getSession();Advanced Configuration
const client = new CRMClient({
apiToken: 'your-api-token',
sessionReplay: {
enabled: true,
sampleRate: 0.5, // Record 50% of sessions
// Recording options
recording: {
maskAllInputs: true, // Mask all input fields (default: true)
maskTextSelector: '[data-mask]', // CSS selector for elements to mask
blockSelector: '[data-block]', // CSS selector for elements to block completely
recordCanvas: false, // Record canvas elements (default: false)
collectFonts: false, // Collect fonts (default: false)
inlineStylesheet: true, // Inline stylesheets (default: true)
inlineImages: false, // Inline images (default: false)
},
// Buffering and flushing
buffering: {
flushInterval: 5000, // Flush every 5 seconds (default: 5000)
maxBufferSize: 100, // Max events before auto-flush (default: 100)
maxSessionDuration: 3600000, // Max 1 hour sessions (default: 3600000)
},
// Telemetry capture
telemetry: {
captureConsole: true, // Capture console logs (default: true)
captureNetwork: true, // Capture network requests (default: true)
captureErrors: true, // Capture JavaScript errors (default: true)
capturePerformance: true, // Capture performance metrics (default: true)
},
// Privacy settings
privacy: {
maskEmails: true, // Auto-mask email addresses (default: true)
maskPhones: true, // Auto-mask phone numbers (default: true)
maskCreditCards: true, // Auto-mask credit card numbers (default: true)
customMaskPatterns: [
{
pattern: /secret-\d+/gi,
replacement: 'SECRET-****',
},
],
},
},
});Log Custom Events
// Log a custom event during the session
client.sessionReplay?.logCustomEvent({
name: 'checkout_started',
data: {
cartValue: 129.99,
itemCount: 3,
},
});Privacy Controls
Use HTML data attributes to control what gets recorded:
<!-- Mask sensitive text -->
<div data-mask>Sensitive information here</div>
<!-- Block element completely from recording -->
<div data-block>This won't be recorded at all</div>
<!-- Password inputs are automatically masked -->
<input type="password" />Session Data Structure
interface SessionReplaySession {
sessionId: string; // Unique session ID
startTime: Date; // When session started
endTime?: Date; // When session ended (if ended)
duration?: number; // Session duration in ms
initialUrl: string; // Starting URL
referrer?: string; // Referrer URL
visitorId?: string; // Visitor ID
contactId?: string; // Contact ID (if identified)
deviceType?: string; // 'desktop' | 'mobile' | 'tablet'
browser?: string; // Browser name
os?: string; // Operating system
viewport?: { // Viewport dimensions
width: number;
height: number;
};
status: 'ACTIVE' | 'ENDED' | 'PROCESSING' | 'ERROR';
}Best Practices
- Sampling: For high-traffic sites, use
sampleRateto record a percentage of sessions - Privacy: Always use
maskAllInputs: trueand configure PII masking appropriately - Performance: Sessions are buffered and flushed every 5 seconds to minimize performance impact
- Storage: Small sessions (<50KB) are stored in PostgreSQL, larger sessions in S3
- GDPR/CCPA: Implement proper consent mechanisms before enabling session replay
Session Lifecycle
- Start: Session automatically starts when client initializes (if enabled)
- Recording: DOM mutations, console logs, network requests, errors are captured
- Buffering: Events are buffered locally
- Flushing: Events are sent to backend every 5 seconds or when buffer reaches 100 events
- End: Session ends automatically on page unload/hide
// Manually stop recording
await client.sessionReplay?.stop();
// Get current session
const session = client.sessionReplay?.getSession();
console.log('Session ID:', session?.sessionId);
console.log('Duration:', session?.duration, 'ms');Error Handling
The SDK provides specific error classes for different scenarios:
import {
CRMError,
AuthenticationError,
ResourceNotFoundError,
ValidationError,
RateLimitError,
ServerError,
NetworkError,
} from 'crexperium-sdk';
try {
await client.events.track({ eventKey: 'purchase' });
} catch (error) {
if (error instanceof AuthenticationError) {
console.error('Invalid API token');
} else if (error instanceof ValidationError) {
console.error('Validation errors:', error.errors);
} else if (error instanceof RateLimitError) {
console.error('Rate limit exceeded. Retry after:', error.retryAfter);
} else if (error instanceof NetworkError) {
console.error('Network error:', error.originalError);
}
}TypeScript Support
The SDK is written in TypeScript and includes comprehensive type definitions:
import type {
Event,
Contact,
Deal,
TrackEventOptions,
IdentifyOptions,
CreateDealOptions,
} from 'crexperium-sdk';Contributing
Contributions are welcome! Please see our Contributing Guide for details.
License
MIT License - see LICENSE file for details.
Support
- Documentation: https://docs.crexperium.com
- GitHub Issues: https://github.com/crexperium/crexperium-sdk/issues
- Email: [email protected]
