Back to Blog
Monitoring

Monitoring and observability for modern applications

Deep dive into monitoring tools and best practices for keeping your application healthy.

James Wilson
January 25, 2025
11 min read

Monitoring vs Observability

Monitoring tells you when something is wrong. Observability helps you understand why.

The Three Pillars of Observability

1. Metrics

Numerical measurements over time:

  • Request rate
  • Error rate
  • Response time (latency)
  • CPU and memory usage

2. Logs

Discrete events that happened in your system:

console.log({
  level: 'info',
  timestamp: new Date().toISOString(),
  message: 'User logged in',
  userId: user.id,
  ip: req.ip
});

3. Traces

The journey of a request through your system:

  • How long each service took
  • Which services were called
  • Where errors occurred

Key Metrics to Monitor

Golden Signals (Google SRE)

  1. Latency: Time to service a request
  2. Traffic: How much demand is placed on your system
  3. Errors: Rate of failed requests
  4. Saturation: How "full" your service is

Setting Up Monitoring in CupaDev

CupaDev provides built-in monitoring. Configure alerts:

{
  "alerts": {
    "errorRate": {
      "threshold": 5,
      "period": "5m",
      "channels": ["slack", "email"]
    },
    "responseTime": {
      "threshold": 1000,
      "percentile": 95,
      "channels": ["slack"]
    }
  }
}

Structured Logging

Use structured logging for better searchability:

// Good - structured
logger.info('order_created', {
  orderId: order.id,
  userId: user.id,
  amount: order.total,
  items: order.items.length
});

// Bad - unstructured
console.log(`Order ${order.id} created by user ${user.id}`);

Distributed Tracing

Track requests across multiple services:

import { trace } from '@cupadev/tracing';

async function processOrder(orderId) {
  const span = trace.startSpan('process_order');

  try {
    await validateOrder(orderId);
    await chargePayment(orderId);
    await shipOrder(orderId);
    span.setStatus({ code: 'OK' });
  } catch (error) {
    span.recordException(error);
    span.setStatus({ code: 'ERROR' });
    throw error;
  } finally {
    span.end();
  }
}

Error Tracking

Implement comprehensive error tracking:

  • Capture stack traces
  • Include contextual information
  • Group similar errors
  • Track error trends over time

Performance Monitoring

Track application performance:

// Track custom metrics
metrics.histogram('api.request.duration', duration, {
  endpoint: '/api/users',
  method: 'GET',
  status: 200
});

Dashboard Best Practices

  • Start with high-level overview
  • Allow drilling down into details
  • Show trends over time
  • Include SLO/SLA status
  • Make dashboards actionable

Alerting Strategy

Good alerts are:

  • Actionable: Require human intervention
  • Timely: Sent before users are impacted
  • Contextual: Include relevant information
  • Prioritized: Critical vs warning vs info

Conclusion

Effective monitoring and observability are essential for maintaining healthy applications. CupaDev's integrated monitoring tools help you stay informed and respond quickly to issues.

Related Articles