A production-grade, real-time monitoring platform for network services — Web/HTTP, Database, DNS, SMTP, and full-page browser audits — with dashboards, Green/Yellow/Red alerting, synthetic checks, headless-browser performance scoring, and security monitoring.
Two apps, one monorepo, glued by a typed contract framework that bridges Go ⇄ TypeScript.
Sentinel watches N targets and decides, at the application layer (never ICMP
ping), whether each is up — measuring the full latency waterfall, rendering pages
in a real headless Chromium for a Lighthouse-style performance score, scraping
Prometheus /metrics for internal stats, and raising Green/Yellow/Red incidents
with e-mail alerts. A bundled Demo App plays the part of a monitored service:
it has a modern login and, on a failed sign-in, ships a security log to Sentinel
through the shared SDK — feeding brute-force detection and the user's own
"recent sign-in activity" view.
As-built docs:
docs/systems/· Install & first run:docs/install.md· Deployment notes:docs/Release.md
- Application-layer "up" checks for HTTP, TCP, DNS and SMTP — status family + body keyword, TCP connect, DNS resolution, SMTP
220banner. No false "down" from firewalled ICMP. - Latency waterfall via
net/http/httptrace: DNS → connect → TLS → TTFB → transfer, persisted per check (the view Datadog/New Relic show). - Headless-browser audits: real chromedp render → full-page screenshot + Web Vitals (FCP/LCP/CLS/TBT/TTFB) → 0–100 Lighthouse-style score computed in Go.
- Prometheus-model scraping: instrumented apps expose
/metrics; Sentinel pulls and normalises them (RPS, latency, active conns, DB pool stats). - Green / Yellow / Red alerting: consecutive-failure state machine + threshold rule engine → deduped incidents → SMTP e-mail (Mailpit in dev) + recovery notices.
- Security plane: sliding-window brute-force detection, z-score traffic anomaly (DDoS indicator), config-change alerts, and weak-config / vulnerability checks (HSTS/CSP/X-Frame-Options, revealing banners, outdated TLS).
- Live control-room dashboard: dark, dense UI with a real-time status wall over SSE, latency waterfalls, uptime bars, perf-score gauges and a screenshot gallery.
- Beacon contract framework: one OpenAPI spec generates the gin server interface, the Go SDK, and the TypeScript client — drift is a compile error.
DevOps/
├── apps/
│ ├── monitor-api/ Go — Sentinel backend (gin + gorm + scheduler + probes + chromedp + alerting)
│ ├── monitor-web/ TS — Sentinel dashboard (Vite + React + TanStack + recharts + shadcn/ui)
│ ├── demo-api/ Go — monitored app (login, /metrics, Beacon push on failed login)
│ ├── demo-web/ TS — monitored app (modern login + security activity view)
│ └── dns-exporter/ Go — CoreDNS dnstap sidecar (ships real DNS stats to Sentinel via Beacon)
├── packages/
│ ├── contract/ ★ OpenAPI 3.0.3 — the single source of truth (Beacon)
│ ├── beacon-go/ ★ Go SDK (ergonomic client + generated models/client)
│ ├── api-client/ ★ TS SDK (typed client + TanStack Query hooks + SSE)
│ ├── ui/ ★ shared shadcn/ui design system (both web apps)
│ ├── tsconfig/ shared TS bases
│ └── eslint-config/ shared lint config
├── deploy/ reverse-proxy & DNS config (Caddy, CoreDNS, nginx SPA)
├── docs/ install, as-built systems/, runbooks/, playbooks/, release notes
├── scripts/ dev/build/seed/up-down helpers used by the Makefile
├── go.work Go 1.26 workspace (monitor-api, demo-api, dns-exporter, beacon-go)
├── package.json bun workspaces + turbo
└── docker-compose.yml postgres ×2, mailpit, chromium
| App | Codename | Stack | Ports |
|---|---|---|---|
| Monitoring platform | Sentinel | monitor-api (Go gin/gorm) + monitor-web (Vite/React) |
API :8080, web :5173 |
| Monitored application | Demo App | demo-api (Go gin/gorm) + demo-web (Vite/React) |
API :8081, web :5174 |
Beacon is the tRPC/gRPC-equivalent for this polyglot stack. packages/contract/openapi.yaml
is the single source of truth; code generation produces all three consumers:
openapi.yaml ──oapi-codegen──► monitor-api gin ServerInterface (Go server)
──oapi-codegen──► beacon-go models + client (Go SDK for monitored apps)
──openapi-typescript──► api-client types (TS client + hooks for the web apps)
Registering a monitored app issues an API key (shown once; only a SHA-256 hash + prefix stored). The app embeds the key and calls the SDK like a local function — the SDK injects the bearer header, JSON-encodes, retries with backoff, and batches events in the background:
beacon := beacon.NewClient(beacon.Config{BaseURL: sentinelURL, APIKey: apiKey})
_ = beacon.AuthFailure(ctx, beacon.AuthFailureEvent{
Email: attempt.Email, IP: c.ClientIP(), UserAgent: c.Request.UserAgent(),
Reason: "invalid_credentials", At: time.Now(),
})| Tool | Version | Used for |
|---|---|---|
| Docker + Compose | recent | Postgres ×2, Mailpit, headless Chromium |
| Go | 1.26 | the go.work modules (monitor-api, demo-api, dns-exporter, beacon-go) |
| Bun | ≥ 1.3 | the JS/TS workspaces + turbo (the package manager — do not use npm/pnpm) |
| make | any | the task runner that fronts all of the above |
make help lists every available target. Full walkthrough in
docs/install.md.
git clone <repo-url> DevOps
cd DevOps
cp .env.example .env # then edit secrets/ports as needed (.env is git-ignored)make setup # bun install + `go mod tidy` across every Go modulemake up # postgres-sentinel, postgres-demo, mailpit, chromiummake migrate-up # apply Sentinel + Demo schemas (golang-migrate)
make seed # admin user + registered demo app + API key + demo monitors# backends — separate terminals
cd apps/monitor-api && go run ./cmd/server # Sentinel API → :8080
cd apps/demo-api && go run ./cmd/server # Demo API → :8081
# both frontends together (from the repo root)
bun run dev # monitor-web :5173, demo-web :5174Then open http://localhost:5173 and sign in with
admin@sentinel.local / changeme123 (the credentials are printed by
make seed). Captured alert e-mails land in the Mailpit UI at
http://localhost:8025.
All-in-Docker alternative:
make up-allbuilds and runs the Go services as containers too (docker compose --profile apps up -d --build) instead of running them from source. Reverse-proxy/DNS config for a real deployment lives indeploy/; seedocs/Release.md.
| Command | What it does |
|---|---|
make up / make down |
start / stop backing services |
make migrate-up |
apply both database schemas |
make seed |
seed admin + demo app + monitors |
make codegen |
regenerate Go + TS clients from the OpenAPI spec |
make build |
build all Go binaries + TS bundles |
make test |
run Go + TS tests |
make test-go / make vet |
Go-only test / vet across modules |
docs/install.md— installation & first-run.docs/systems/— as-built per-system notes (architecture, entities, monitoring engine, alerting, security, embeds, DNS, SMTP, status page, testing) with pointers to the concrete source files.docs/runbooks/— operate it: add/remove monitor, rotate API key, change alert threshold, retention & rollups, restart browser pool, backup/restore Postgres.docs/playbooks/— incident response: target down, latency degradation, brute-force, traffic spike/DDoS, DNS failures, SMTP backlog.docs/smtp-mailserver.md— production SMTP / docker-mailserver setup.docs/Release.md— deployment notes (Compose + Caddy reverse proxy, public routes).
Released under the MIT License © 2026 João Antônio Barbosa Pereira and Matheus Nilton Biolowons. Built for Redes de Computadores e Internet (IDP).