@chaseleto/sessions-sdk
v1.0.14
Published
Privacy-conscious session recording SDK for self-hosted session tracking
Maintainers
Readme
Session SDK
A privacy-conscious, self-hosted session recording SDK for capturing user sessions with essential metadata, network requests, console logs, and session replays.
Features
- 🎥 Session Recording: Full session replay using rrweb
- 📝 Console Logging: Capture console.log, warn, error, info, debug
- 🌐 Network Monitoring: Track fetch and XHR requests
- 🔒 Privacy First: Respects Do Not Track headers
- 📊 Sampling: Configurable sampling rates
- 🚀 Lightweight: Minimal bundle size with tree-shaking
- 🔄 Reliable Upload: Retry queue with exponential backoff
- 📱 Cross-Platform: Works in all modern browsers
Installation
NPM
npm install client-sdkCDN
<script src="https://unpkg.com/client-sdk@latest/dist/index.umd.min.js"></script>Development
Prerequisites
- Node.js 16+
- npm or yarn
Setup
# Install dependencies
npm install
# Run tests
npm test
# Run tests with coverage
npm run test:coverage
# Run tests in watch mode
npm run test:watch
# Type checking
npm run type-check
# Build (includes tests and type checking)
npm run build
# Full CI process (tests + type check + build)
npm run ciBuild Process
The build process automatically runs:
- Tests - Ensures all functionality works correctly
- Type checking - Validates TypeScript types
- Build - Creates distribution files
This ensures that any published version has passed all quality checks.
Quick Start
Basic Usage
import { init } from 'client-sdk';
// Initialize with your API key
init('your-api-key-here', {
projectId: 'your-project-id',
userId: 'user-123',
attributes: {
plan: 'premium',
environment: 'production'
}
});Next.js Usage (Recommended - Like HyperDX)
// pages/_app.tsx or app/layout.tsx
import { initSessionRecording } from '@chaseleto/sessions-sdk';
// Initialize session recording (runs once on app load)
initSessionRecording(process.env.NEXT_PUBLIC_SESSION_API_KEY!, {
projectId: 'my-nextjs-app',
userId: 'user-123',
attributes: {
environment: process.env.NODE_ENV,
framework: 'nextjs',
},
});
export default function App({ Component, pageProps }) {
return <Component {...pageProps} />;
}Next.js with React Hooks (Alternative)
// pages/_app.tsx or app/layout.tsx
import { useSessionRecording } from '@chaseleto/sessions-sdk';
export default function App({ Component, pageProps }) {
const { sessionId, isActive } = useSessionRecording(
process.env.NEXT_PUBLIC_SESSION_API_KEY!,
{
projectId: 'my-nextjs-app',
userId: 'user-123',
attributes: {
environment: process.env.NODE_ENV,
framework: 'nextjs',
},
}
);
return <Component {...pageProps} />;
}CDN Usage
<script>
// Initialize with your API key
SessionSDK.init('your-api-key-here', {
projectId: 'your-project-id'
});
</script>Configuration Options
| Option | Type | Default | Description |
|--------|------|---------|-------------|
| endpoint | string | 'https://api.sessions.chxse.dev/api/v1/sessions' | API endpoint for sending session data |
| projectId | string | '' | Project ID for the session |
| userId | string | '' | User ID to associate with sessions |
| attributes | object | {} | Custom attributes to attach to all sessions |
| captureConsole | boolean | true | Whether to capture console logs |
| captureNetwork | boolean | true | Whether to capture network requests |
| samplingRate | number | 1.0 | Sampling rate (0-1) for session recording |
| maxSessionDuration | number | 1800000 | Maximum session duration in milliseconds (30 min) |
| uploadInterval | number | 10000 | Upload interval in milliseconds (10 sec) |
| respectDNT | boolean | true | Whether to respect Do Not Track headers |
| headers | object | {} | Custom headers to include in requests |
API Reference
Core Functions
init(apiKey, options?)
Initialize the session SDK.
const sdk = init('your-api-key', {
endpoint: 'https://your-backend.com/sessions',
projectId: 'project-123'
});Next.js Integration
The SDK includes Next.js-specific utilities for easy integration:
useSessionRecording(apiKey, options?)
React hook for Next.js applications:
import { useSessionRecording } from '@chaseleto/sessions-sdk';
function MyComponent() {
const { sessionId, isActive, setUserId, setAttributes } = useSessionRecording(
'your-api-key',
{
projectId: 'my-app',
userId: 'user-123',
enabled: process.env.NODE_ENV === 'production',
}
);
return <div>Session ID: {sessionId}</div>;
}SessionRecorder Component
Invisible component for easy integration:
import { SessionRecorder } from '@chaseleto/sessions-sdk';
export default function App({ Component, pageProps }) {
return (
<>
<SessionRecorder
apiKey={process.env.NEXT_PUBLIC_SESSION_API_KEY!}
projectId="my-app"
userId="user-123"
/>
<Component {...pageProps} />
</>
);
}withSessionRecording(Component, apiKey, options?)
HOC for wrapping components:
import { withSessionRecording } from '@chaseleto/sessions-sdk';
const MyComponent = () => <div>My App</div>;
export default withSessionRecording(MyComponent, 'your-api-key', {
projectId: 'my-app',
});destroy()
Stop recording and destroy the SDK instance.
destroy();setAttributes(attributes)
Add custom attributes to the current session.
setAttributes({
plan: 'premium',
userType: 'admin',
page: 'checkout'
});setUserId(userId)
Set the user ID for the current session.
setUserId('user-123');getSessionId()
Get the current session ID.
const sessionId = getSessionId();
console.log('Current session:', sessionId);isActive()
Check if recording is currently active.
if (isActive()) {
console.log('Session recording is active');
}Advanced Usage
Using the SessionSDK Class
For more control, you can use the SessionSDK class directly:
import { SessionSDK } from 'client-sdk';
const sdk = new SessionSDK('your-api-key', {
endpoint: 'https://your-backend.com/sessions',
projectId: 'project-123'
});
// Start recording
sdk.init();
// Add attributes
sdk.setAttributes({ plan: 'premium' });
// Stop recording
sdk.stop();
// Destroy instance
sdk.destroy();Data Structure
The SDK sends session data in the following format:
interface SessionData {
sessionId: string;
projectId: string;
userId?: string;
attributes: Record<string, any>;
metadata: {
userAgent: string;
url: string;
referrer: string;
viewport: { width: number; height: number };
timestamp: number;
timezone: string;
language: string;
};
events: Array<{
type: 'rrweb';
data: any;
timestamp: number;
}>;
consoleLogs: Array<{
level: 'log' | 'warn' | 'error' | 'info' | 'debug';
message: string;
args: any[];
timestamp: number;
stack?: string;
}>;
networkRequests: Array<{
method: string;
url: string;
status?: number;
statusText?: string;
requestHeaders?: Record<string, string>;
responseHeaders?: Record<string, string>;
requestBody?: any;
responseBody?: any;
duration: number;
timestamp: number;
error?: string;
}>;
timestamp: number;
duration: number;
}Privacy & Compliance
Do Not Track
The SDK respects the Do Not Track (DNT) header by default. When DNT is enabled, no session data is recorded.
Data Minimization
- Only essential metadata is collected
- Sensitive input fields (passwords) are automatically masked
- Console logs and network requests are truncated to prevent data bloat
- Session data is automatically cleaned up after upload
Data Size Limits & Memory Management
The SDK implements comprehensive size limits to prevent memory issues and ensure reliable uploads:
Individual Item Limits
| Item Type | Size Limit | Description | |-----------|------------|-------------| | Console Logs | 5KB per log | Large console objects are truncated | | Network Requests | 10KB per request | Large request/response data is limited | | Request Bodies | 1KB | Request payloads are truncated | | Console Arguments | 1KB per argument | Large objects in console calls are limited |
Total Collection Limits
| Data Type | Maximum Items | Server Validation | |-----------|---------------|-------------------| | Events (rrweb) | 10,000 | 10,000 | | Console Logs | 1,000 | 1,000 | | Network Requests | 1,000 | 1,000 |
Memory Management Features
- Preventive Filtering: Items that would exceed size limits are skipped entirely
- Frequent Cleanup: Data is cleaned up every 5 seconds to prevent accumulation
- Progressive Truncation: If upload data is too large, items are progressively reduced
- Automatic Cleanup: Old data is automatically removed after successful uploads
- Size Validation: Data is validated before upload to prevent server rejections
Upload Limits
- Client-side limit: 25MB per upload
- Server-side limit: 50MB per upload
- Automatic retry: Failed uploads are retried with exponential backoff
- Graceful degradation: If data is still too large after truncation, upload is skipped
Best Practices
- Avoid large objects in console logs: The SDK will truncate them, but it's better to log smaller, focused data
- Monitor network requests: Large API responses will be limited to metadata only
- Use sampling for high-traffic sites: Reduce the sampling rate to limit data collection
- Set appropriate session durations: Long sessions accumulate more data
GDPR Compliance
- No personally identifiable information is collected by default
- Users can opt-out by setting DNT headers
- Session data can be easily deleted by session ID
Browser Support
- Chrome 60+
- Firefox 55+
- Safari 12+
- Edge 79+
Development
Building
npm install
npm run buildDevelopment Mode
npm run devTesting
npm testLicense
MIT License - see LICENSE file for details.
