
Company News
/Security News
Socket Selected for OpenAI's Cybersecurity Grant Program
Socket is an initial recipient of OpenAI's Cybersecurity Grant Program, which commits $10M in API credits to defenders securing open source software.
@layers/node
Advanced tools
Server-side Node.js SDK for Layers Analytics. Designed for multi-tenant server environments where each request may come from a different user.
npm install @layers/node
# or
pnpm add @layers/node
Requires Node.js >= 18.
import { LayersNode } from '@layers/node';
const layers = new LayersNode({
apiKey: 'your-api-key',
appId: 'your-app-id',
environment: 'production'
});
// Every call requires a distinctId (the user who triggered the event)
layers.track('user-123', 'api_call', { endpoint: '/users', method: 'GET' });
// Graceful shutdown (flushes remaining events)
await layers.shutdown();
All fields for LayersNodeConfig:
| Field | Type | Default | Description |
|---|---|---|---|
apiKey | string | required | Layers API key |
appId | string | required | Application identifier |
environment | 'development' | 'staging' | 'production' | required | Deployment environment |
enableDebug | boolean | false | Verbose console logging |
baseUrl | string | https://in.layers.com | Override the ingest endpoint |
flushIntervalMs | number | 10000 | Periodic flush interval (ms) |
flushThreshold | number | 20 | Queue depth that triggers auto-flush |
maxQueueSize | number | 10000 | Max events in queue before dropping |
maxBatchSize | number | 1000 | Max events per HTTP batch |
shutdownFlushTimeoutMs | number | 5000 | Max wait time for final flush |
handleSignals | boolean | true | Register SIGTERM/SIGINT handlers |
Automatically track HTTP requests as events:
import { LayersNode } from '@layers/node';
import { layersExpressMiddleware } from '@layers/node/express';
import express from 'express';
const app = express();
const layers = new LayersNode({
apiKey: 'your-api-key',
appId: 'your-app-id',
environment: 'production'
});
app.use(layersExpressMiddleware(layers));
// Middleware tracks `http_request` events with:
// - method, path, status_code, response_time_ms
// - distinctId resolved from X-User-Id or X-App-User-Id headers
app.use(
layersExpressMiddleware(layers, {
trackRequests: true, // default: true
trackResponseTime: true, // default: true
ignorePaths: ['/health'] // default: ['/health', '/healthz', '/ready', '/favicon.ico']
})
);
Use AsyncLocalStorage-based request context to thread the user ID through server-side code:
import { LayersNode } from '@layers/node';
import {
getLayersContext,
trackServerAction,
trackServerPageView,
withLayersContext
} from '@layers/node/nextjs';
const layers = new LayersNode({
apiKey: 'your-api-key',
appId: 'your-app-id',
environment: 'production'
});
// In middleware.ts — set the request context
export function middleware(request: NextRequest) {
const userId = request.headers.get('x-user-id') ?? 'anonymous';
return withLayersContext(
{ distinctId: userId, properties: { path: request.nextUrl.pathname } },
() => NextResponse.next()
);
}
// In a Server Component or Server Action
trackServerPageView(layers, '/dashboard');
trackServerAction(layers, 'createPost', { category: 'blog' });
// Or read context manually
const ctx = getLayersContext();
if (ctx) {
layers.track(ctx.distinctId, 'custom_event', ctx.properties);
}
The Node SDK never throws from track(), screen(), or flush(). Instead, register error listeners:
layers.on('error', (err) => {
console.error('Layers SDK error:', err.message);
// Forward to Sentry, Datadog, etc.
});
// Remove a listener
layers.off('error', myListener);
When enableDebug is true and no error listeners are registered, errors are logged to console.warn.
By default, the SDK registers SIGTERM and SIGINT handlers that flush all queued events before the process exits. This ensures no events are lost during deployments or container restarts.
To disable this (e.g. if you manage signals yourself):
const layers = new LayersNode({
...config,
handleSignals: false
});
// Manual shutdown in your own signal handler
process.on('SIGTERM', async () => {
await layers.shutdown();
process.exit(0);
});
// Manual flush (async, with retry)
await layers.flush();
// Check queue depth
console.log(layers.queueDepth());
// Graceful shutdown: flushes remaining events, then stops
// Waits up to shutdownFlushTimeoutMs (default 5s)
await layers.shutdown();
After shutdown(), all subsequent track()/screen() calls are silently dropped.
Enable enableDebug: true for detailed logging:
[Layers] track("api_call", 2 properties, distinctId="user-123")
[Layers] screen("dashboard", 0 properties, distinctId="user-123")
[Layers] setUserProperties(3 properties, distinctId="user-123")
MIT
FAQs
Layers Analytics Node.js SDK — thin wrapper over Rust core via WASM
The npm package @layers/node receives a total of 149 weekly downloads. As such, @layers/node popularity was classified as not popular.
We found that @layers/node demonstrated a healthy version release cadence and project activity because the last version was released less than a year ago. It has 4 open source maintainers collaborating on the project.
Did you know?

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Company News
/Security News
Socket is an initial recipient of OpenAI's Cybersecurity Grant Program, which commits $10M in API credits to defenders securing open source software.

Security News
Socket CEO Feross Aboukhadijeh joins 10 Minutes or Less, a podcast by Ali Rohde, to discuss the recent surge in open source supply chain attacks.

Research
/Security News
Campaign of 108 extensions harvests identities, steals sessions, and adds backdoors to browsers, all tied to the same C2 infrastructure.