What You're Building
KeyPulse is an anomaly detection layer for cryptographic key activity. You push events when keys are used, rotated, exported, or accessed — we score them, flag outliers, and fire webhooks when something looks wrong.
Your users see your brand. Your UI. Your alerts. KeyPulse runs invisibly behind it.
https://keypulse-5pj5.polsia.app
Integration in 3 Steps
The complete integration path from zero to live anomaly detection.
Connect your platform
One API call registers your platform as a partner and returns a unique API key. Store it — it's shown once.
Push key activity events
Instrument your key operations (signing, rotation, access, export). Send each event to our ingest endpoint. We analyze patterns in real-time.
Receive anomaly alerts
When our detection engine flags something — unusual signing volume, rotation overdue, policy violation — we POST to your webhook URL. You decide how to surface it in your UI.
Step 1 — Register Your Platform
Call the registration endpoint once during your onboarding flow. No auth required. Returns a partner API key and a partner_id to identify your tenant.
# Register your platform — one-time call curl -X POST https://keypulse-5pj5.polsia.app/api/v1/partners/register \ -H "Content-Type: application/json" \ -d '{ "name": "YourPlatform" }' # Response { "partner_id": "p_8f3a2b1c", "api_key": "pk_live_a1b2c3d4e5f6..." # store this — shown once }
const response = await fetch( 'https://keypulse-5pj5.polsia.app/api/v1/partners/register', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ name: 'YourPlatform' }) } ); const { partner_id, api_key } = await response.json(); // Store in your env / secrets manager — never log this process.env.KEYPULSE_API_KEY = api_key;
Your pk_live_ key is returned once. Store it in a secrets manager (AWS Secrets Manager, HashiCorp Vault, etc.) immediately. If lost, you'll need to re-register.
Step 2 — Instrument Key Operations
Push an event every time a key operation occurs in your platform. Authentication uses the X-API-Key header.
curl -X POST https://keypulse-5pj5.polsia.app/api/v1/events/ingest \ -H "X-API-Key: pk_live_a1b2c3d4e5f6..." \ -H "Content-Type: application/json" \ -d '{ "event_type": "key_rotated", "key_id": "eth-validator-key-007", "data": { "triggered_by": "scheduled_policy", "previous_age_days": 90, "chain": "ethereum" } }' # Response (202 Accepted) { "event_id": "evt_9f2d1a3b" }
// Wrap KeyPulse ingest in a fire-and-forget helper async function trackKeyEvent(eventType, keyId, data = {}) { try { await fetch('https://keypulse-5pj5.polsia.app/api/v1/events/ingest', { method: 'POST', headers: { 'X-API-Key': process.env.KEYPULSE_API_KEY, 'Content-Type': 'application/json', }, body: JSON.stringify({ event_type: eventType, key_id: keyId, data }), }); } catch (err) { // Non-blocking — never let monitoring affect your critical path console.warn('[keypulse] ingest failed', err.message); } } // Usage: instrument your signing path await signTransaction(tx); trackKeyEvent('signing_operation', 'eth-validator-key-007', { tx_hash: tx.hash, chain: 'ethereum', amount_usd: tx.valueUsd, });
Supported Event Types
| event_type | When to send | Risk signal |
|---|---|---|
| key_created | A new key is provisioned | Unexpected provisioning spikes |
| key_rotated | Key rotation completes | Overdue rotation detection |
| key_accessed | Key material is read or exported | Unusual access patterns, new IPs |
| key_deleted | A key is revoked or destroyed | Unauthorized deletion attempts |
| signing_operation | A signing request is processed | Volume anomalies, off-hours signing |
| policy_violation | A policy rule is triggered by your system | Escalation path for your own rules |
Step 3 — Handle Webhook Alerts
Configure a webhook URL during onboarding. When our detection engine flags an event, we POST to your endpoint within seconds. Respond with 200 OK to acknowledge; we retry up to 3× with exponential backoff on failure.
Each webhook includes an X-KeyPulse-Signature header — HMAC-SHA256 of the raw body using your webhook secret. Verify it before processing.
{
"event": "anomaly_detected",
"timestamp": "2026-05-04T03:17:22Z",
"partner_id": "p_8f3a2b1c",
"alert": {
"key_id": "eth-validator-key-007",
"rule": "signing_volume_spike",
"severity": "critical",
"description": "Signing rate 14× above 7-day baseline",
"baseline_rph": 42,
"current_rph": 601,
"triggered_at": "2026-05-04T03:17:22Z"
}
}
{
"event": "rotation_overdue",
"timestamp": "2026-05-04T09:00:01Z",
"partner_id": "p_8f3a2b1c",
"alert": {
"key_id": "custody-signing-key-btc-02",
"severity": "warning",
"description": "Key not rotated in 97 days (policy: 90d)",
"last_rotated": "2026-01-27T12:00:00Z",
"overdue_by_days": 7,
"policy_window_days": 90
}
}
{
"event": "threshold_breach",
"timestamp": "2026-05-04T14:32:08Z",
"partner_id": "p_8f3a2b1c",
"alert": {
"key_id": "mpc-signing-pool-01",
"severity": "warning",
"rule_name": "daily_signing_cap",
"description": "Daily signing cap 80% reached (rule threshold)",
"threshold": 1000,
"current": 807,
"window": "24h"
}
}
import crypto from 'crypto'; app.post('/webhooks/keypulse', (req, res) => { // 1. Verify signature const sig = req.headers['x-keypulse-signature']; const expected = crypto .createHmac('sha256', process.env.KEYPULSE_WEBHOOK_SECRET) .update(JSON.stringify(req.body)) .digest('hex'); if (sig !== expected) return res.status(401).end(); // 2. Handle event const { event, alert } = req.body; if (event === 'anomaly_detected') { createIncident(alert); // your platform's alert system } else if (event === 'rotation_overdue') { notifyKeyOwner(alert); } else if (event === 'threshold_breach') { logToAuditTrail(alert); } // 3. Acknowledge — respond quickly, process async res.status(200).json({ received: true }); });
Endpoints
All partner API endpoints use the X-API-Key header except registration. Base URL: https://keypulse-5pj5.polsia.app
partner_id and api_key. No auth required.
event_id on 202.
event_type_match and webhook_url. Fires on every matching ingest event.
100 requests/hour per partner key. High-volume partners should batch events using the data array field or contact us for an Enterprise plan with higher limits.
Alert Rules
Alert rules let you subscribe to specific event types in real time. When an ingested event matches a rule's event_type_match, KeyPulse immediately POSTs to your webhook_url. Use these for incident response, paging, and audit pipelines.
# Create an alert rule — fires on every matching ingest event curl -X POST https://keypulse-5pj5.polsia.app/api/v1/rules \ -H "X-API-Key: pk_live_a1b2c3d4e5f6..." \ -H "Content-Type: application/json" \ -d '{ "name": "Rotation alert", "event_type_match": "key_rotated", "webhook_url": "https://your-platform.com/webhooks/keypulse", "severity": "warning" }' # Response 201 { "success": true, "rule": { "id": 7, "name": "Rotation alert", "event_type_match": "key_rotated", "severity": "warning", "is_active": true } }
# List all active rules for your account curl https://keypulse-5pj5.polsia.app/api/v1/rules \ -H "X-API-Key: pk_live_a1b2c3d4e5f6..." # Response 200 { "success": true, "partner_id": 42, "count": 1, "rules": [ { "id": 7, "name": "Rotation alert", "event_type_match": "key_rotated", "webhook_url": "https://your-platform.com/webhooks/keypulse", "severity": "warning", "is_active": true } ] }
# Deactivate a rule (soft-delete — delivery history preserved) curl -X DELETE https://keypulse-5pj5.polsia.app/api/v1/rules/7 \ -H "X-API-Key: pk_live_a1b2c3d4e5f6..." # Response 200 { "success": true, "deactivated": 7 }
Webhook Payload
When a rule fires, KeyPulse POSTs this payload to your webhook_url. Respond with 200 to acknowledge — we retry once automatically on failure.
{
"event_id": 8847,
"event_type": "key_rotated",
"key_id": "key_mpc_eth_signer_01",
"timestamp": "2026-05-22T04:00:00.000Z",
"metadata": { "reason": "scheduled_90d_rotation" },
"rule_id": 7
}
import crypto from 'crypto'; app.post('/webhooks/keypulse', (req, res) => { // Verify HMAC-SHA256 signature const sig = req.headers['x-keypulse-signature']; const expected = crypto .createHmac('sha256', process.env.KEYPULSE_API_KEY) .update(JSON.stringify(req.body)) .digest('hex'); if (sig !== expected) return res.status(401).end(); const { event_type, key_id, rule_id } = req.body; // Handle event here — respond fast, process async res.status(200).json({ received: true }); });
Every webhook POST includes X-KeyPulse-Signature: HMAC-SHA256 of the raw JSON body, signed with your partner API key. Always verify before processing.
Request API Access
We onboard partners in batches. Tell us about your platform — we'll provision credentials and a sandbox within 48 hours.