Middleware.io gives your engineering team rich, full-stack observability: distributed traces, infrastructure metrics, log aggregation, and real-user monitoring in a single pane of glass. What it doesn't provide is an external, independent health check — a probe that fires even when Middleware.io's own ingestion pipeline or your cloud provider has a problem. Vigilmon fills that gap. It pings your application from outside your network and alerts you the moment something breaks, regardless of what your internal observability stack is reporting.
This tutorial walks through integrating Vigilmon's external uptime monitoring alongside an existing Middleware.io setup for a cloud-native application.
What You'll Build
- A
/healthendpoint that surfaces real dependency status - A Vigilmon HTTP monitor pointing at your application
- A heartbeat monitor for background jobs and data pipelines
- A unified alert routing strategy that keeps Middleware.io and Vigilmon alerts in separate lanes
Prerequisites
- A Middleware.io account with at least one application instrumented
- Your application deployed and reachable via a public URL
- A free account at vigilmon.online
Step 1: Add a Structured Health Endpoint
Middleware.io collects metrics and traces from inside your app, but Vigilmon needs an HTTP endpoint it can probe from the outside. Add a /health route that checks your real dependencies — not just a static 200.
Node.js / Express
// routes/health.js
const { createClient } = require("redis");
const { Pool } = require("pg");
const db = new Pool({ connectionString: process.env.DATABASE_URL });
const cache = createClient({ url: process.env.REDIS_URL });
async function healthHandler(req, res) {
const checks = {};
let ok = true;
// Database probe
try {
await db.query("SELECT 1");
checks.database = "ok";
} catch (err) {
checks.database = `error: ${err.message}`;
ok = false;
}
// Cache probe
try {
await cache.ping();
checks.cache = "ok";
} catch (err) {
checks.cache = `error: ${err.message}`;
ok = false;
}
// Middleware.io agent connectivity (optional sanity check)
checks.middleware_agent = process.env.MW_API_KEY ? "configured" : "missing_key";
res.status(ok ? 200 : 503).json({
status: ok ? "ok" : "degraded",
version: process.env.APP_VERSION || "unknown",
checks,
});
}
module.exports = { healthHandler };
// app.js
const { healthHandler } = require("./routes/health");
app.get("/health", healthHandler);
Python / FastAPI
# routers/health.py
import os
import asyncpg
import redis.asyncio as aioredis
from fastapi import APIRouter
from fastapi.responses import JSONResponse
router = APIRouter()
@router.get("/health")
async def health():
checks = {}
ok = True
try:
conn = await asyncpg.connect(os.environ["DATABASE_URL"])
await conn.fetchval("SELECT 1")
await conn.close()
checks["database"] = "ok"
except Exception as e:
checks["database"] = f"error: {e}"
ok = False
try:
r = await aioredis.from_url(os.environ["REDIS_URL"])
await r.ping()
checks["cache"] = "ok"
except Exception as e:
checks["cache"] = f"error: {e}"
ok = False
status_code = 200 if ok else 503
return JSONResponse(
content={"status": "ok" if ok else "degraded", "checks": checks},
status_code=status_code,
)
Deploy the endpoint and confirm it responds:
curl -s https://your-app.example.com/health | jq .
# {"status":"ok","checks":{"database":"ok","cache":"ok"}}
Step 2: Configure a Vigilmon HTTP Monitor
- Log in to Vigilmon and click Add Monitor → HTTP.
- URL:
https://your-app.example.com/health - Check interval: 60 seconds — a sensible default for most production APIs.
- Response timeout: 10 seconds.
- Expected status code:
200. - Under Advanced, enable JSON body assertion:
- Path:
status - Expected value:
ok
- Path:
- Click Save.
Vigilmon now probes your endpoint from multiple external locations. If the response code is non-200 or the JSON assertion fails, you get an alert.
Protecting the endpoint
If your health endpoint returns sensitive internal data, gate it with a shared secret instead of leaving it open:
app.get("/health", (req, res, next) => {
const token = req.headers["x-health-token"];
if (token !== process.env.HEALTH_TOKEN) {
return res.status(401).json({ error: "unauthorized" });
}
next();
}, healthHandler);
In Vigilmon's monitor settings, add a Custom header: X-Health-Token: <your-secret>.
Step 3: Alert Routing — Vigilmon and Middleware.io in Separate Lanes
Both Middleware.io and Vigilmon will fire alerts, but they serve different purposes. Keep them in separate channels to avoid confusion.
| Alert type | Source | Recommended channel |
|---|---|---|
| External uptime down | Vigilmon | PagerDuty / on-call rotation |
| High error rate / latency spike | Middleware.io | Slack #alerts-internal |
| Dependency failure | Both | Merge in Slack #alerts-critical |
In Vigilmon, configure alert channels under Alerts → Add channel:
- Email: your on-call distribution list for immediate page-level alerts.
- Webhook: a Slack incoming webhook or PagerDuty endpoint.
Set the Middleware.io alert destinations to a separate Slack channel so the two streams are easy to distinguish during an incident.
Step 4: Heartbeat Monitor for Pipelines and Workers
Middleware.io traces your background jobs when the instrumentation SDK is active, but if the job process crashes or gets stuck, the traces just stop — no explicit failure signal. Vigilmon's heartbeat monitor catches this case.
Add a heartbeat ping at the end of each successful job run:
// workers/data-pipeline.js
const fetch = require("node-fetch");
async function runPipeline() {
try {
await processRecords();
// Ping Vigilmon heartbeat on success
await fetch(process.env.VIGILMON_HEARTBEAT_URL, { method: "POST" });
console.log("Pipeline complete — heartbeat sent");
} catch (err) {
// Do NOT ping — silence triggers the Vigilmon alert
console.error("Pipeline failed:", err);
process.exit(1);
}
}
runPipeline();
In Vigilmon, go to Add Monitor → Heartbeat and set the grace period to slightly longer than your job's scheduled interval (e.g., 70 minutes for an hourly job). Store the heartbeat URL in your secret manager and inject it as VIGILMON_HEARTBEAT_URL.
Step 5: Status Page for External Stakeholders
Middleware.io dashboards are internal-only. When customers or partners want to check service health, they need a public status page.
- In Vigilmon, go to Status Pages → Create.
- Add your HTTP monitor and any heartbeat monitors.
- Set a custom domain or use the default
*.vigilmon.onlinesubdomain. - Embed the badge in your documentation:
<img src="https://vigilmon.online/badge/<monitor-id>.svg" alt="API Status" />
Now stakeholders get real-time status without requiring access to your Middleware.io account.
What Vigilmon Catches That Middleware.io Misses
| Scenario | Middleware.io | Vigilmon | |---|---|---| | App returns 5xx to external users | Traces show errors (if SDK is running) | HTTP monitor fires immediately | | DNS or CDN misconfiguration | Not detectable — inside the app | External probe catches DNS failures | | Background job silently stops running | Traces go quiet — no explicit alert | Heartbeat grace period fires alert | | Middleware.io agent itself crashes | No data ingested — silent gap | Vigilmon is independent — still probing | | Cloud provider regional outage | Metrics may also be affected | External monitor from unaffected region |
Middleware.io gives you deep insight into what's happening inside your application. Vigilmon tells you whether the application is reachable at all. Together they give you complete observability coverage — internal signals and external truth.
Add external uptime monitoring to your Middleware.io stack today — register free at vigilmon.online.