Monitoring

Pulsaride includes a built-in monitoring dashboard that starts automatically at /pulsaride when the application runs. No separate agent, no SaaS account, no extra configuration.

Dashboard

Open http://localhost:8080/pulsaride (or your configured server port) to see:

  • Live run progress — rows migrated per table, current step, estimated completion
  • Per-table L1 status (row count match)
  • DLQ summary — count of rejected rows per table
  • Run history — all past runs with status, duration, and row counts

WebSocket live feed

The dashboard subscribes to a WebSocket endpoint at /pulsaride/ws. Each migrated batch emits a progress event with the table name, rows written, and elapsed time. The connection is established automatically when the dashboard is open — no manual setup.

Spring Actuator integration

Pulsaride exposes a custom Actuator health indicator:

GET /actuator/health/pulsaride
{
  "status": "UP",
  "details": {
    "last_run_id": "run-42",
    "last_run_status": "COMPLETED",
    "tables": {
      "products": { "status": "PASS", "source": 12483, "target": 12483 },
      "orders":   { "status": "PASS", "source": 4201,  "target": 4201  }
    }
  }
}

Include this endpoint in your CI cutover gate to block promotion if any table fails L1.

Alert thresholds

Configure per-table alert thresholds in application properties:

pulsaride:
  monitoring:
    alerts:
      dlq_threshold: 100       # alert if DLQ exceeds 100 rows
      row_count_tolerance: 0   # 0 = exact match required (default)

When a threshold is exceeded, Pulsaride logs a WARN and sets the Actuator health status to OUT_OF_SERVICE.

Grafana datasource

The dashboard data is also available via a JSON API at /pulsaride/api/runs, compatible with the Grafana JSON datasource plugin. Point Grafana athttp://<host>:8080/pulsaride/api to build custom dashboards from run metrics.

GET /pulsaride/api/runs
[
  {
    "run_id": "run-42",
    "started_at": "2025-01-15T10:00:00Z",
    "ended_at": "2025-01-15T10:00:04Z",
    "status": "COMPLETED",
    "tables": [
      { "name": "products", "rows": 12483, "dlq_rows": 0 },
      { "name": "orders",   "rows": 4201,  "dlq_rows": 0 }
    ]
  }
]