Skip to content
This repository was archived by the owner on Jul 16, 2026. It is now read-only.

Latest commit

 

History

159 Commits

Folders and files

NameName
Last commit message
Last commit date
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Heartbeat

Set and forget uptime monitoring

Coverage

Beautiful status pages and real-time monitoring for your services. Built with Next.js, Convex, and Clerk.

Quick Start

Prerequisites

1. Install Dependencies

bun install

2. Set Up Convex

# Login to Convex
bunx convex login

# Initialize Convex project (creates deployment)
bunx convex dev

This will:

  • Create a new Convex deployment
  • Generate convex/_generated/ types
  • Start the Convex dev server
  • Print your deployment URL

Copy the deployment URL - you'll need it for .env.local

3. Set Up Clerk

  1. Go to dashboard.clerk.com
  2. Create a new application
  3. Get your API keys from the "API Keys" section
  4. Get your JWT issuer domain from "JWT Templates" → Default → Issuer

4. Configure Environment Variables

Copy the example env file and fill in your values:

cp .env.example .env.local

Required variables for local development:

  • CONVEX_DEPLOYMENT and NEXT_PUBLIC_CONVEX_URL (from step 2)
  • NEXT_PUBLIC_CLERK_PUBLISHABLE_KEY, CLERK_SECRET_KEY, and CLERK_JWT_ISSUER_DOMAIN (from step 3)

See .env.example for all available options including Stripe, Sentry, and PostHog.

5. Run the Development Server

# Runs Next.js + Convex + Stripe webhook forwarder concurrently
bun dev

Note: This runs all processes in one terminal with colored output:

  • Cyan: Next.js dev server
  • Magenta: Convex dev server
  • Yellow: Stripe webhook forwarder (if configured)

If you prefer to run them separately:

# Terminal 1: Convex dev server
bun dev:convex

# Terminal 2: Next.js dev server
bun dev:next

6. Open the App

Navigate to http://localhost:3000

Features

Core Functionality

  • HTTP Monitoring: Check any URL every 1-5 minutes
  • Status Pages: Public status pages at /s/[project-slug]
  • Is It Down Tool: Public checker at /is-it-down with verdict + probe evidence
  • Real-time Dashboard: Live updates via Convex subscriptions
  • Incident Tracking: Automatic incident creation after 3 consecutive failures
  • Uptime Stats: 30-day uptime percentage and response time trends
  • Mobile Responsive: Touch-optimized interface for all devices

User Interface

  • Landing Page: / - Marketing page with feature overview
  • Dashboard: /dashboard - View and manage all monitors
  • Status Pages: /s/[slug] - Public status pages (ISR cached, 60s revalidation)
  • Is It Down: /is-it-down and /is-it-down/[hostname] - Public diagnostic pages
  • Monitor Management: Create, edit, delete monitors with real-time updates

Monitoring Engine

  • Cron-based: Runs every minute via Convex crons
  • Smart Failure Detection: 3 consecutive failures before incident
  • Status Tracking: Up / Degraded / Down states
  • Response Time: Measures and stores response times
  • Data Retention: Automatic cleanup of checks older than 30 days

Tech Stack

  • Frontend: Next.js 16, React 19, TypeScript, Tailwind CSS 4
  • Backend: Convex (serverless database + functions + cron)
  • Auth: Clerk (authentication & user management)
  • Monitoring: HTTP checks via Convex actions
  • Payments: Stripe (subscriptions)
  • Error Tracking: Sentry
  • Analytics: PostHog
  • Email: Resend (optional, for incident notifications)
  • Fonts: Geist Sans & Geist Mono
  • Icons: Lucide React
  • Charts: Recharts

Project Structure

heartbeat/
├── app/                    # Next.js App Router pages
│   ├── dashboard/         # Authenticated dashboard
│   ├── s/[slug]/          # Public status pages (ISR)
│   ├── layout.tsx         # Root layout with fonts & providers
│   └── page.tsx           # Landing page
├── components/            # React components
│   ├── StatusIndicator.tsx
│   ├── MonitorCard.tsx
│   ├── StatusHeader.tsx
│   ├── UptimeChart.tsx
│   ├── IncidentTimeline.tsx
│   ├── AddMonitorForm.tsx
│   ├── MonitorSettingsModal.tsx
│   └── DashboardMonitorCard.tsx
├── convex/                # Convex backend
│   ├── schema.ts          # Database schema
│   ├── monitors.ts        # Monitor CRUD operations
│   ├── checks.ts          # Check history queries
│   ├── incidents.ts       # Incident queries
│   ├── monitoring.ts      # Core monitoring engine
│   ├── crons.ts           # Scheduled jobs
│   └── auth.config.ts     # Clerk integration
└── public/                # Static assets

Database Schema

monitors

  • Monitor configuration (name, URL, interval, etc.)
  • User ownership via userId
  • Project grouping via projectSlug
  • Status tracking (consecutiveFailures, lastCheckAt, lastResponseTime)

checks

  • Historical check results
  • Status (up/down/degraded)
  • Response time measurements
  • Error messages for failures

incidents

  • Incident records (investigating/identified/resolved)
  • Start and end timestamps
  • Associated with specific monitors

Development Commands

# Development
bun dev               # Start Next.js + Convex (+ Stripe forwarder)
bun dev:next          # Start Next.js dev server only
bun dev:convex        # Start Convex dev server only

# Type checking
bun type-check        # Run TypeScript compiler

# Linting
bun lint              # Run ESLint
bun run lint:openapi  # Validate OpenAPI v1 contract

# Building
bun build             # Build for production
bun start             # Start Next.js + Convex concurrently
bun start:next        # Start Next.js production server only

# Convex
bunx convex deploy    # Deploy to production
bunx convex dashboard # Open Convex dashboard

API Contract Docs

Public Is-It-Down Endpoint

  • GET /api/is-it-down?target=github.com
  • Returns JSON verdict + probe evidence from Heartbeat's public checker pipeline.

Testing the App

For detailed development testing instructions, see TESTING.md.

1. Create Your First Monitor

  1. Sign in at /dashboard (Clerk will handle registration)
  2. Click "Add Monitor" button
  3. Fill in:
    • Name: "My API"
    • URL: https://httpstat.us/200 (always returns 200 OK)
    • Project Slug: my-project (auto-generated from name)
    • Check Interval: 60 seconds
  4. Click "Create Monitor"

2. View Status Page

Navigate to /s/my-project to see your public status page.

3. Test Monitoring

The monitoring cron runs every minute. You can:

  • Test success: Use https://httpstat.us/200
  • Test failure: Use https://httpstat.us/500
  • Test flaky: Use https://httpstat.us/random/200,500

After 3 consecutive failures, an incident will be created automatically.

4. Monitor Dashboard Features

  • Click on a monitor card to expand and see recent checks
  • Click the settings icon to edit monitor configuration
  • Click the play icon to manually trigger a check (TODO)

Monitoring Engine Details

How It Works

  1. Cron Job: Runs every 60 seconds via convex/crons.ts
  2. Check Due Monitors: Queries monitors where lastCheckAt + interval < now
  3. Execute Checks: Parallel HTTP requests with timeout
  4. Record Results: Store check result in checks table
  5. Update Status: Increment consecutiveFailures or reset to 0
  6. Incident Management:
    • 3+ failures → Create incident (if none exists)
    • 0 failures → Resolve open incident

Status States

  • Up: 0 consecutive failures (green)
  • Degraded: 1-2 consecutive failures (yellow)
  • Down: 3+ consecutive failures (red)

Data Retention

  • Checks: Kept for 30 days, then auto-deleted
  • Incidents: Kept forever (historical record)
  • Monitors: Kept until manually deleted

Common Issues

"Module not found" errors

Run bunx convex dev to generate types in convex/_generated/

Authentication not working

  1. Check .env.local has correct Clerk keys
  2. Verify CLERK_JWT_ISSUER_DOMAIN matches your Clerk dashboard
  3. Restart Next.js dev server after env changes

Monitors not being checked

  1. Check Convex dashboard shows cron executions
  2. Verify monitors are enabled: true
  3. Check monitor lastCheckAt is being updated
  4. Look for errors in Convex logs

Status page shows 404

Ensure monitors exist with that projectSlug in database

Production Deployment

See TODO.md Phase 7 for production deployment steps (Vercel + Convex production deployment).

License

Private project - not licensed for redistribution.

Built With

About

Beautiful, set-and-forget uptime monitoring.

Resources

Stars

3 stars

Watchers

1 watching

Forks

Releases

Packages

Contributors

Languages