tutorial

How to Monitor Bytebase with Vigilmon

Bytebase manages your database schema changes — but if the platform goes down, schema migrations stall and deployments block. Learn how to monitor Bytebase availability, alert on migration pipeline failures, and heartbeat your GitOps schema workflows.

How to Monitor Bytebase with Vigilmon

Bytebase is the control plane for database schema changes: SQL review policies, GitOps-based migration workflows, multi-environment deployment pipelines, and audit logging across 20+ database engines. When your team's deploys depend on Bytebase to approve and apply schema migrations, the platform's availability is directly on the critical path of every release.

A Bytebase outage doesn't just mean the UI is unavailable — it means schema migrations queue up, deployments block, and on-call engineers start manually applying SQL scripts. This guide shows you how to monitor Bytebase availability, heartbeat your migration pipelines, and get alerted before a platform issue becomes a release incident.


What can go wrong with a Bytebase deployment

The Bytebase service goes down. Bytebase is a Go-based server that you self-host (or run via Docker). A crash, OOM kill, or misconfigured container restart policy can take it offline. Any in-flight migration approvals and deployments stop.

Database connectivity breaks. Bytebase maintains connections to all your registered database instances. If those connections drop — network changes, rotated credentials, IP allowlist changes — migrations fail silently and SQL review stops working.

GitOps webhook deliveries fail. In GitOps mode, Bytebase receives webhook events from your VCS (GitHub, GitLab, Bitbucket) to trigger migration pipelines. If webhooks start failing — a misconfigured secret, a network rule change, a Bytebase restart — schema changes stop flowing to your databases automatically.

Migration pipelines stall in approval. A migration stuck in the approval stage doesn't fail — it just sits there. If no one notices, it blocks a deploy. You need proactive monitoring, not reactive discovery.


Step 1: Expose and monitor the Bytebase health endpoint

Bytebase exposes a built-in health endpoint at /healthz. Verify it's working:

curl https://bytebase.yourcompany.com/healthz
# {"status":"ok"}

This endpoint returns HTTP 200 when Bytebase is healthy. If the service is starting up, it returns a non-200 status — useful for liveness probes.

For a more detailed status check, use the Bytebase API to verify it can reach its registered database instances:

# Get API token
curl -X POST https://bytebase.yourcompany.com/v1/auth/login \
  -H "Content-Type: application/json" \
  -d '{"email":"service-account@yourcompany.com","password":"...","web":false}'

# List instances to verify DB connectivity
curl https://bytebase.yourcompany.com/v1/instances \
  -H "Authorization: Bearer $TOKEN"

You can wrap this into a script-based health check that runs periodically and serves as a Vigilmon heartbeat:

#!/bin/bash
# scripts/bytebase_health_check.sh
set -euo pipefail

BYTEBASE_URL="${BYTEBASE_URL:-https://bytebase.yourcompany.com}"
BYTEBASE_EMAIL="${BYTEBASE_EMAIL}"
BYTEBASE_PASSWORD="${BYTEBASE_PASSWORD}"
HEARTBEAT_URL="${BYTEBASE_HEALTH_HEARTBEAT_URL:-}"

# Step 1: Authenticate
TOKEN=$(curl -sf -X POST "$BYTEBASE_URL/v1/auth/login" \
  -H "Content-Type: application/json" \
  -d "{\"email\":\"$BYTEBASE_EMAIL\",\"password\":\"$BYTEBASE_PASSWORD\",\"web\":false}" \
  | python3 -c "import sys,json; print(json.load(sys.stdin)['token'])")

# Step 2: List instances — fails if Bytebase can't reach its metadata DB
INSTANCES=$(curl -sf "$BYTEBASE_URL/v1/instances" \
  -H "Authorization: Bearer $TOKEN" \
  | python3 -c "import sys,json; d=json.load(sys.stdin); print(len(d.get('instances', [])))")

echo "Bytebase healthy — $INSTANCES instance(s) registered"

# Step 3: Ping heartbeat
if [ -n "$HEARTBEAT_URL" ]; then
  curl -sf "$HEARTBEAT_URL" > /dev/null
  echo "Heartbeat pinged"
fi

Step 2: Set up HTTP monitoring with Vigilmon

Point Vigilmon at your Bytebase instance:

  1. Sign up at vigilmon.online — free tier, no credit card
  2. Click New Monitor → HTTP
  3. Enter https://bytebase.yourcompany.com/healthz
  4. Set the check interval (5 minutes on free tier)
  5. Save

For a complete Bytebase monitoring setup, create monitors for multiple surfaces:

| Endpoint | What it catches | |---|---| | /healthz | Bytebase process availability | | / | Web UI availability | | /v1/instances (with auth) | Database connectivity (via API probe) |

Vigilmon probes from multiple geographic regions. A non-2xx response from any region opens an incident and alerts you immediately.


Step 3: Heartbeat monitoring for migration pipelines

The most dangerous Bytebase failure mode is a migration that silently stalls. Add heartbeat monitoring to your CI/CD pipeline that triggers schema migrations.

For GitOps-based migrations, your CI pipeline typically:

  1. Merges a SQL migration file to a designated branch
  2. Bytebase's VCS webhook triggers and creates a migration issue
  3. The migration runs through approval stages
  4. CI waits for the migration to complete before deploying the app

Add a heartbeat at the end of a successful migration workflow:

# scripts/wait_for_migration.py
"""
Poll Bytebase for a migration issue to complete, then ping heartbeat.
Called from CI after a migration SQL file is merged.
"""
import os
import sys
import time
import httpx

BYTEBASE_URL = os.environ["BYTEBASE_URL"]
ISSUE_ID = os.environ["BYTEBASE_ISSUE_ID"]
HEARTBEAT_URL = os.environ.get("MIGRATION_HEARTBEAT_URL", "")
POLL_INTERVAL = 30  # seconds
TIMEOUT = 1800  # 30 minutes


def get_token() -> str:
    r = httpx.post(
        f"{BYTEBASE_URL}/v1/auth/login",
        json={
            "email": os.environ["BYTEBASE_EMAIL"],
            "password": os.environ["BYTEBASE_PASSWORD"],
            "web": False,
        },
        timeout=10,
    )
    r.raise_for_status()
    return r.json()["token"]


def check_issue_status(token: str, issue_id: str) -> str:
    r = httpx.get(
        f"{BYTEBASE_URL}/v1/issues/{issue_id}",
        headers={"Authorization": f"Bearer {token}"},
        timeout=10,
    )
    r.raise_for_status()
    return r.json().get("status", "UNKNOWN")


def main():
    token = get_token()
    elapsed = 0

    print(f"Waiting for Bytebase issue {ISSUE_ID} to complete...")

    while elapsed < TIMEOUT:
        status = check_issue_status(token, ISSUE_ID)
        print(f"  Status: {status} (elapsed: {elapsed}s)")

        if status == "DONE":
            print("Migration completed successfully")
            if HEARTBEAT_URL:
                httpx.get(HEARTBEAT_URL, timeout=10)
                print("Heartbeat pinged")
            return

        if status in ("CANCELED", "FAILED"):
            print(f"Migration {status} — not pinging heartbeat")
            sys.exit(1)

        time.sleep(POLL_INTERVAL)
        elapsed += POLL_INTERVAL

    print(f"Migration timed out after {TIMEOUT}s")
    sys.exit(1)


if __name__ == "__main__":
    main()

In Vigilmon:

  1. Click New Monitor → Heartbeat
  2. Set the expected interval to match your deploy frequency (e.g. 48 hours for daily deploys with buffer)
  3. Copy the unique ping URL
  4. Add it to your CI secrets:
MIGRATION_HEARTBEAT_URL=https://vigilmon.online/api/heartbeat/your-unique-token

Step 4: Monitor GitOps webhook delivery

In GitOps mode, Bytebase receives webhook events from your VCS. A broken webhook means migrations stop flowing automatically. Add a check to your CI pipeline that verifies the webhook fired:

# .github/workflows/schema-migration.yml
name: Schema Migration

on:
  push:
    branches: [main]
    paths:
      - 'migrations/**'

jobs:
  migrate:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4

      - name: Wait for Bytebase to pick up migration
        env:
          BYTEBASE_URL: ${{ secrets.BYTEBASE_URL }}
          BYTEBASE_EMAIL: ${{ secrets.BYTEBASE_EMAIL }}
          BYTEBASE_PASSWORD: ${{ secrets.BYTEBASE_PASSWORD }}
        run: |
          # Give Bytebase 60s to receive and process the webhook
          sleep 60

          # Verify a new issue was created for this commit
          TOKEN=$(curl -sf -X POST "$BYTEBASE_URL/v1/auth/login" \
            -H "Content-Type: application/json" \
            -d "{\"email\":\"$BYTEBASE_EMAIL\",\"password\":\"$BYTEBASE_PASSWORD\",\"web\":false}" \
            | python3 -c "import sys,json; print(json.load(sys.stdin)['token'])")

          ISSUES=$(curl -sf "$BYTEBASE_URL/v1/issues?filter=status==OPEN" \
            -H "Authorization: Bearer $TOKEN")

          echo "Open migration issues: $(echo $ISSUES | python3 -c 'import sys,json; print(len(json.load(sys.stdin).get("issues", [])))')"

      - name: Ping heartbeat on webhook delivery confirmed
        if: success()
        run: curl -s "${{ secrets.WEBHOOK_DELIVERY_HEARTBEAT_URL }}"

If a migration file merges but this job silently fails to verify webhook delivery, Vigilmon alerts within your configured interval.


Step 5: SQL review policy monitoring

Bytebase's SQL review enforces policies (naming conventions, index requirements, forbidden operations) on migration files. Add a pre-commit check that verifies the review policy is active:

# scripts/verify_sql_review_policy.py
"""
Verify that SQL review policies are active for all environments.
Run this as a periodic check or pre-deploy gate.
"""
import os
import sys
import httpx

BYTEBASE_URL = os.environ["BYTEBASE_URL"]
REQUIRED_ENVIRONMENTS = ["prod", "staging"]


def get_token() -> str:
    r = httpx.post(
        f"{BYTEBASE_URL}/v1/auth/login",
        json={
            "email": os.environ["BYTEBASE_EMAIL"],
            "password": os.environ["BYTEBASE_PASSWORD"],
            "web": False,
        },
    )
    r.raise_for_status()
    return r.json()["token"]


def check_review_policies(token: str) -> list[str]:
    """Return list of environments missing active SQL review policies."""
    missing = []
    for env in REQUIRED_ENVIRONMENTS:
        r = httpx.get(
            f"{BYTEBASE_URL}/v1/environments/{env}/policies/sql-review",
            headers={"Authorization": f"Bearer {token}"},
        )
        if r.status_code == 404 or not r.json().get("enforce"):
            missing.append(env)
    return missing


def main():
    token = get_token()
    missing = check_review_policies(token)

    if missing:
        print(f"SQL review policies missing or inactive for: {', '.join(missing)}")
        sys.exit(1)

    print(f"SQL review policies active for all {len(REQUIRED_ENVIRONMENTS)} environments")

    heartbeat_url = os.environ.get("SQL_REVIEW_HEARTBEAT_URL")
    if heartbeat_url:
        httpx.get(heartbeat_url, timeout=10)
        print("Heartbeat pinged")


if __name__ == "__main__":
    main()

Schedule this check daily and add a Vigilmon heartbeat:

# crontab
0 9 * * * cd /app && python scripts/verify_sql_review_policy.py

Step 6: Alerts and notifications

Configure alert delivery in Vigilmon:

For Slack:

  1. Create an incoming webhook in your Slack workspace
  2. In Vigilmon go to Notifications → New Channel → Slack
  3. Paste the URL and enable it on your monitors

You'll receive immediate alerts like:

🔴 DOWN: bytebase.yourcompany.com/healthz
Status: 503 Service Unavailable
Regions: US-East, EU-West
Started: 3 minutes ago

And for missed migration pipelines:

🔴 MISSED: prod-schema-migration heartbeat
Expected every: 48 hours
Last ping: 55 hours ago

For DBA teams with an on-call rotation, route critical alerts to PagerDuty:

  1. In Vigilmon go to Notifications → New Channel → PagerDuty
  2. Paste your PagerDuty integration key
  3. Enable it on the Bytebase HTTP monitor (Bytebase down = immediate page) and migration heartbeats

Create a public status page for your engineering team:

  1. Go to Status Pages → New Status Page
  2. Add your Bytebase monitors
  3. Name it "Database Migration Infrastructure"
  4. Share with the engineering team

What you've built

| What | How | |---|---| | Bytebase uptime monitoring | Vigilmon HTTP monitor on /healthz (multi-region) | | Instance connectivity check | Periodic health script + heartbeat | | Migration pipeline monitoring | CI wait script + heartbeat on DONE status | | GitOps webhook monitoring | CI verification step + heartbeat | | SQL review policy monitoring | Daily check script + heartbeat | | Instant alerts | Slack or PagerDuty notifications | | Engineering status page | Vigilmon status page for migration infrastructure |

Database schema changes are among the riskiest operations in a production system. Bytebase manages that risk — but only if it's running. This setup ensures you know immediately when any part of your schema change infrastructure goes dark.


Get started free at vigilmon.online — your first monitor is running in under a minute.

Monitor your app with Vigilmon

Free plan — 5 monitors, no credit card required. Up and running in 60 seconds.

Start free →