API Reference
Metrics API
Track KPIs, OKRs, and business metrics for analytics and monitoring
Track KPIs, OKRs, and business metrics for analytics and monitoring. Measure business performance and make data-driven decisions.
Overview
Business metrics provide quantitative measurements for:
- Key Performance Indicators (KPIs)
- Objectives and Key Results (OKRs)
- Counters (incremental values)
- Gauges (current values)
- Histograms (distributions)
import { createBusinessApi } from 'business-as-code'
const api = createBusinessApi({
apiKey: process.env.APIS_DO_KEY,
})
// Record a metric
await api.metrics.record({
name: 'Monthly Recurring Revenue',
type: 'kpi',
value: 125000,
unit: 'USD',
timestamp: new Date().toISOString(),
})record()
Record a business metric.
Signature
record(
metric: Omit<BusinessMetric, 'id'>
): Promise<BusinessMetric>Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
| metric | object | Yes | Metric data without ID |
Metric Properties
| Property | Type | Required | Description |
|---|---|---|---|
| name | string | Yes | Metric name |
| type | string | Yes | Metric type ('kpi', 'okr', 'counter', 'gauge', 'histogram') |
| value | number | string | Yes | Metric value |
| target | number | string | No | Target value (for KPIs/OKRs) |
| unit | string | No | Unit of measurement |
| timestamp | string | No | When measured (ISO 8601) |
| metadata | object | No | Additional context |
Returns
Promise that resolves to the recorded BusinessMetric with generated ID.
Example
// Record revenue metric
const metric = await api.metrics.record({
name: 'Monthly Recurring Revenue',
type: 'kpi',
value: 125000,
target: 150000,
unit: 'USD',
timestamp: new Date().toISOString(),
metadata: {
period: '2024-10',
growth: 0.15,
newCustomers: 12,
},
})
console.log('Metric recorded:', metric.id)Metric Types
KPI (Key Performance Indicator)
// Revenue metrics
await api.metrics.record({
name: 'Monthly Recurring Revenue',
type: 'kpi',
value: 125000,
target: 150000,
unit: 'USD',
})
await api.metrics.record({
name: 'Annual Recurring Revenue',
type: 'kpi',
value: 1500000,
target: 2000000,
unit: 'USD',
})
// Customer metrics
await api.metrics.record({
name: 'Customer Acquisition Cost',
type: 'kpi',
value: 250,
target: 200,
unit: 'USD',
})
await api.metrics.record({
name: 'Customer Lifetime Value',
type: 'kpi',
value: 5000,
target: 6000,
unit: 'USD',
})
await api.metrics.record({
name: 'Churn Rate',
type: 'kpi',
value: 0.05,
target: 0.03,
unit: 'percentage',
})
// Product metrics
await api.metrics.record({
name: 'Daily Active Users',
type: 'kpi',
value: 15000,
target: 20000,
unit: 'users',
})
await api.metrics.record({
name: 'Net Promoter Score',
type: 'kpi',
value: 45,
target: 50,
unit: 'score',
})OKR (Objectives and Key Results)
// Objective: Increase revenue
await api.metrics.record({
name: 'Q4 Revenue Growth',
type: 'okr',
value: 0.18, // 18% growth
target: 0.25, // 25% target
unit: 'percentage',
metadata: {
objective: 'Accelerate Revenue Growth',
keyResult: 'Achieve 25% QoQ growth',
quarter: 'Q4-2024',
},
})
// Objective: Improve product
await api.metrics.record({
name: 'Feature Adoption Rate',
type: 'okr',
value: 0.42, // 42% adoption
target: 0.6, // 60% target
unit: 'percentage',
metadata: {
objective: 'Increase Product Engagement',
keyResult: 'Reach 60% feature adoption',
feature: 'automation-builder',
},
})
// Objective: Expand market
await api.metrics.record({
name: 'Enterprise Customers',
type: 'okr',
value: 45,
target: 100,
unit: 'customers',
metadata: {
objective: 'Expand Enterprise Market',
keyResult: 'Acquire 100 enterprise customers',
},
})Counter
// Incrementing counters
await api.metrics.record({
name: 'Total Orders',
type: 'counter',
value: 1523,
unit: 'orders',
})
await api.metrics.record({
name: 'API Requests',
type: 'counter',
value: 1000000,
unit: 'requests',
})
await api.metrics.record({
name: 'Emails Sent',
type: 'counter',
value: 50000,
unit: 'emails',
})Gauge
// Current state values
await api.metrics.record({
name: 'Active Subscriptions',
type: 'gauge',
value: 1250,
unit: 'subscriptions',
})
await api.metrics.record({
name: 'Server CPU Usage',
type: 'gauge',
value: 0.65,
unit: 'percentage',
metadata: {
server: 'api-server-1',
region: 'us-west',
},
})
await api.metrics.record({
name: 'Queue Length',
type: 'gauge',
value: 42,
unit: 'items',
})Histogram
// Distribution of values
await api.metrics.record({
name: 'Order Value Distribution',
type: 'histogram',
value: JSON.stringify({
buckets: [
{ range: '0-50', count: 120 },
{ range: '50-100', count: 85 },
{ range: '100-500', count: 45 },
{ range: '500+', count: 12 },
],
}),
metadata: {
period: '2024-10',
totalOrders: 262,
},
})
await api.metrics.record({
name: 'Response Time Distribution',
type: 'histogram',
value: JSON.stringify({
p50: 150,
p90: 300,
p95: 450,
p99: 1000,
}),
unit: 'milliseconds',
})list()
List all metrics, optionally filtered.
Signature
list(): Promise<BusinessMetric[]>Returns
Promise that resolves to an array of BusinessMetric objects.
Example
const metrics = await api.metrics.list()
console.log(`Found ${metrics.length} metrics`)
// Filter by type
const kpis = metrics.filter((m) => m.type === 'kpi')
const okrs = metrics.filter((m) => m.type === 'okr')
// Filter by date
const thisMonth = metrics.filter((m) => {
const metricDate = new Date(m.timestamp)
const now = new Date()
return metricDate.getMonth() === now.getMonth() && metricDate.getFullYear() === now.getFullYear()
})
// Calculate progress
kpis.forEach((kpi) => {
const progress = kpi.target ? (Number(kpi.value) / Number(kpi.target)) * 100 : null
console.log(`${kpi.name}: ${kpi.value} / ${kpi.target} (${progress?.toFixed(1)}%)`)
})get()
Retrieve a specific metric by ID.
Signature
get(id: string): Promise<BusinessMetric>Parameters
| Parameter | Type | Required | Description |
|---|---|---|---|
| id | string | Yes | Unique identifier of the metric |
Returns
Promise that resolves to a BusinessMetric object.
Example
const metric = await api.metrics.get('metric-abc123')
console.log('Metric:', metric.name)
console.log('Type:', metric.type)
console.log('Value:', metric.value)
console.log('Target:', metric.target)
console.log('Progress:', (Number(metric.value) / Number(metric.target)) * 100 + '%')Complete Examples
SaaS Dashboard Metrics
// Revenue metrics
await api.metrics.record({
name: 'Monthly Recurring Revenue',
type: 'kpi',
value: 125000,
target: 150000,
unit: 'USD',
timestamp: new Date().toISOString(),
})
await api.metrics.record({
name: 'Annual Run Rate',
type: 'kpi',
value: 1500000,
unit: 'USD',
})
// Customer metrics
await api.metrics.record({
name: 'Total Customers',
type: 'gauge',
value: 1250,
unit: 'customers',
})
await api.metrics.record({
name: 'New Customers (MTD)',
type: 'counter',
value: 42,
unit: 'customers',
})
await api.metrics.record({
name: 'Churned Customers (MTD)',
type: 'counter',
value: 5,
unit: 'customers',
})
// Engagement metrics
await api.metrics.record({
name: 'Daily Active Users',
type: 'gauge',
value: 8500,
unit: 'users',
})
await api.metrics.record({
name: 'Weekly Active Users',
type: 'gauge',
value: 15000,
unit: 'users',
})
// Financial metrics
await api.metrics.record({
name: 'Customer Acquisition Cost',
type: 'kpi',
value: 250,
target: 200,
unit: 'USD',
})
await api.metrics.record({
name: 'Customer Lifetime Value',
type: 'kpi',
value: 5000,
target: 6000,
unit: 'USD',
})
await api.metrics.record({
name: 'LTV:CAC Ratio',
type: 'kpi',
value: 20,
target: 30,
unit: 'ratio',
})E-commerce Metrics
// Sales metrics
await api.metrics.record({
name: 'Daily Revenue',
type: 'gauge',
value: 45000,
unit: 'USD',
timestamp: new Date().toISOString(),
})
await api.metrics.record({
name: 'Total Orders',
type: 'counter',
value: 523,
unit: 'orders',
})
await api.metrics.record({
name: 'Average Order Value',
type: 'kpi',
value: 86.05,
target: 100,
unit: 'USD',
})
// Conversion metrics
await api.metrics.record({
name: 'Conversion Rate',
type: 'kpi',
value: 0.035,
target: 0.05,
unit: 'percentage',
})
await api.metrics.record({
name: 'Cart Abandonment Rate',
type: 'kpi',
value: 0.68,
target: 0.5,
unit: 'percentage',
})
// Inventory metrics
await api.metrics.record({
name: 'Out of Stock Items',
type: 'gauge',
value: 12,
unit: 'items',
})
await api.metrics.record({
name: 'Inventory Turnover',
type: 'kpi',
value: 8.5,
target: 10,
unit: 'ratio',
})Marketing Metrics
// Campaign metrics
await api.metrics.record({
name: 'Campaign ROI',
type: 'kpi',
value: 3.5,
target: 4.0,
unit: 'ratio',
metadata: {
campaign: 'Q4-product-launch',
spend: 50000,
revenue: 175000,
},
})
await api.metrics.record({
name: 'Cost Per Lead',
type: 'kpi',
value: 45,
target: 35,
unit: 'USD',
})
await api.metrics.record({
name: 'Lead Conversion Rate',
type: 'kpi',
value: 0.15,
target: 0.2,
unit: 'percentage',
})
// Content metrics
await api.metrics.record({
name: 'Website Traffic',
type: 'gauge',
value: 125000,
unit: 'visitors',
})
await api.metrics.record({
name: 'Organic Search Traffic',
type: 'gauge',
value: 45000,
unit: 'visitors',
})
await api.metrics.record({
name: 'Email Open Rate',
type: 'kpi',
value: 0.28,
target: 0.35,
unit: 'percentage',
})
await api.metrics.record({
name: 'Email Click Rate',
type: 'kpi',
value: 0.05,
target: 0.08,
unit: 'percentage',
})Engineering Metrics
// Performance metrics
await api.metrics.record({
name: 'API Response Time (P95)',
type: 'kpi',
value: 250,
target: 200,
unit: 'milliseconds',
})
await api.metrics.record({
name: 'Error Rate',
type: 'kpi',
value: 0.002,
target: 0.001,
unit: 'percentage',
})
await api.metrics.record({
name: 'Uptime',
type: 'kpi',
value: 0.9985,
target: 0.999,
unit: 'percentage',
})
// Development metrics
await api.metrics.record({
name: 'Deployment Frequency',
type: 'kpi',
value: 12,
target: 20,
unit: 'deployments',
metadata: {
period: 'weekly',
},
})
await api.metrics.record({
name: 'Lead Time for Changes',
type: 'kpi',
value: 2.5,
target: 1,
unit: 'days',
})
await api.metrics.record({
name: 'Mean Time to Recovery',
type: 'kpi',
value: 45,
target: 30,
unit: 'minutes',
})
await api.metrics.record({
name: 'Change Failure Rate',
type: 'kpi',
value: 0.08,
target: 0.05,
unit: 'percentage',
})Metric Aggregation
Time-Series Aggregation
async function aggregateMetrics(metricName: string, period: 'day' | 'week' | 'month') {
const metrics = await api.metrics.list()
// Filter by name
const filtered = metrics.filter((m) => m.name === metricName)
// Group by period
const grouped = filtered.reduce(
(acc, metric) => {
const date = new Date(metric.timestamp)
let key: string
if (period === 'day') {
key = date.toISOString().split('T')[0]
} else if (period === 'week') {
const weekStart = new Date(date)
weekStart.setDate(date.getDate() - date.getDay())
key = weekStart.toISOString().split('T')[0]
} else {
key = `${date.getFullYear()}-${String(date.getMonth() + 1).padStart(2, '0')}`
}
if (!acc[key]) acc[key] = []
acc[key].push(Number(metric.value))
return acc
},
{} as Record<string, number[]>
)
// Calculate aggregates
return Object.entries(grouped).map(([period, values]) => ({
period,
count: values.length,
sum: values.reduce((a, b) => a + b, 0),
avg: values.reduce((a, b) => a + b, 0) / values.length,
min: Math.min(...values),
max: Math.max(...values),
}))
}
// Use it
const dailyRevenue = await aggregateMetrics('Daily Revenue', 'day')
console.log('Daily Revenue:', dailyRevenue)KPI Dashboard
async function getKPIDashboard() {
const metrics = await api.metrics.list()
const kpis = metrics.filter((m) => m.type === 'kpi')
return kpis.map((kpi) => {
const value = Number(kpi.value)
const target = Number(kpi.target)
const progress = target ? (value / target) * 100 : null
return {
name: kpi.name,
value,
target,
unit: kpi.unit,
progress,
status: progress >= 100 ? 'on-track' : progress >= 75 ? 'at-risk' : 'off-track',
timestamp: kpi.timestamp,
}
})
}
// Use it
const dashboard = await getKPIDashboard()
dashboard.forEach((kpi) => {
console.log(`${kpi.name}: ${kpi.value}${kpi.unit} / ${kpi.target}${kpi.unit}`)
console.log(` Progress: ${kpi.progress?.toFixed(1)}% (${kpi.status})`)
})OKR Tracking
async function trackOKRs(quarter: string) {
const metrics = await api.metrics.list()
const okrs = metrics.filter((m) => m.type === 'okr' && m.metadata?.quarter === quarter)
// Group by objective
const byObjective = okrs.reduce(
(acc, okr) => {
const objective = okr.metadata?.objective || 'Unknown'
if (!acc[objective]) {
acc[objective] = []
}
acc[objective].push({
keyResult: okr.metadata?.keyResult || okr.name,
value: Number(okr.value),
target: Number(okr.target),
progress: (Number(okr.value) / Number(okr.target)) * 100,
unit: okr.unit,
})
return acc
},
{} as Record<string, any[]>
)
// Calculate objective progress
return Object.entries(byObjective).map(([objective, keyResults]) => {
const avgProgress = keyResults.reduce((sum, kr) => sum + kr.progress, 0) / keyResults.length
return {
objective,
keyResults,
overallProgress: avgProgress,
status: avgProgress >= 70 ? 'on-track' : avgProgress >= 40 ? 'at-risk' : 'off-track',
}
})
}
// Use it
const q4okrs = await trackOKRs('Q4-2024')
q4okrs.forEach((obj) => {
console.log(`\n${obj.objective} (${obj.overallProgress.toFixed(1)}% - ${obj.status})`)
obj.keyResults.forEach((kr) => {
console.log(` ${kr.keyResult}: ${kr.value} / ${kr.target} (${kr.progress.toFixed(1)}%)`)
})
})Best Practices
1. Use Descriptive Names
// ✅ Good - clear names
await api.metrics.record({
name: 'Monthly Recurring Revenue',
type: 'kpi',
value: 125000,
})
// ❌ Avoid - abbreviations
await api.metrics.record({
name: 'MRR',
type: 'kpi',
value: 125000,
})2. Include Units
// ✅ Good - unit specified
await api.metrics.record({
name: 'Response Time',
type: 'kpi',
value: 250,
unit: 'milliseconds',
})
// ❌ Avoid - no unit
await api.metrics.record({
name: 'Response Time',
type: 'kpi',
value: 250,
})3. Set Realistic Targets
// ✅ Good - achievable target
await api.metrics.record({
name: 'Conversion Rate',
type: 'kpi',
value: 0.03,
target: 0.05, // +67% improvement
unit: 'percentage',
})
// ❌ Avoid - unrealistic target
await api.metrics.record({
name: 'Conversion Rate',
type: 'kpi',
value: 0.03,
target: 0.5, // +1567% improvement
unit: 'percentage',
})4. Track Trends
// Record metrics regularly for trend analysis
async function trackDailyMetrics() {
const timestamp = new Date().toISOString()
await api.metrics.record({
name: 'Daily Active Users',
type: 'gauge',
value: await getDailyActiveUsers(),
timestamp,
})
await api.metrics.record({
name: 'Daily Revenue',
type: 'gauge',
value: await getDailyRevenue(),
unit: 'USD',
timestamp,
})
}
// Run daily
setInterval(trackDailyMetrics, 86400000)Next Steps
- Workflows API - Trigger workflows based on metrics
- Events API - Publish events for metric changes
- Searches API - Search and analyze metrics