Linux servers,
watched while you sleep.

A Python monitor that runs on your server, checks 12 things every 4 hours, and only contacts you when something needs attention. Tap a notification on your phone and the security update installs itself. No SSH session. We set it all up for you.

Get it deployed: admin@belikebee.com
v0.5.3 โ€“ released Managed service Python 3.10+ systemd-native REST API + mobile app
Watchlog โ€” live server monitoring dashboard on a phone receiving real-time metrics from a server rack

01.What watchlog watches

Twelve checks, all built on standard Linux tools you already trust โ€” apt, systemctl, openssl, dig, fail2ban-client, AIDE. One systemd timer runs them every four hours. No agents, no SaaS dependency, no telemetry โ€” nothing leaves the box unless you explicitly point a reporter at it.

apt_updates Counts upgradable packages, escalates ones from the -security suite. CRITICAL on security
ssl_certs Let's Encrypt cert expiry across every live cert on the host. WARN <30d
disk_space Filesystem usage per mount, tmpfs and snap loops ignored. WARN >80%
memory MemAvailable from /proc/meminfo. WARN <500 MB
services systemctl is-active for every unit you mark critical. CRITICAL if down
docker_images Local image digest vs registry :latest โ€” flags stale containers. INFO if outdated
ip_blacklist Spamhaus, Barracuda, SpamCop, SORBS lookup for the host's IPv4 and IPv6. CRITICAL if listed
dns_records SPF, DKIM, DMARC, MX, A presence โ€” catches accidental DNS regressions. CRITICAL if missing
ssh_brute Failed SSH logins in the last 24h, ranked by source IP. WARN >threshold
fail2ban_stats Jail count, currently banned IPs, and verifies your required jails are active. CRITICAL if down
open_ports Listening-port diff vs baseline. New external listener = intrusion signal. Loopback-only changes are quietly ignored. WARN on new ports
file_integrity AIDE checksums of /etc, /usr, /bin โ€” flags tampering with system binaries and configs. CRITICAL on changes

One Python file per check: a clean, auditable codebase. Need a check that is specific to your setup? We add it for you as part of the service.

02.Three places watchlog can reach you

Every channel runs side by side and shares one state โ€” snooze a check on the mobile app and Telegram stops pinging you about it too. Pick the channel that fits the moment.

๐Ÿ“จ Telegram bot

long-polling ยท no webhook ยท no public endpoint
Action buttons on every alert
Apply / Snooze / Ignore on every CRITICAL
/runnow, /status, /clearignores
Chat-id whitelist; everything else logged and rejected

๐Ÿ–ฅ๏ธ Web dashboard

FastAPI ยท auto-refresh 60s ยท Bearer auth
One tab, every check at a glance
Color-coded severity banner
Per-check snooze/ignore in one click
Output drawer for command results

๐Ÿ“ฑ Mobile app

Flutter ยท Android ยท iOS in progress
Pocket dashboard, tap-to-fix push
Multi-server overview as home
Live disk/RAM bars, 90-day calendar
QR pairing in 5 seconds, biometric lock
๐Ÿ‘๏ธ watchlog @ ticklist.eu

๐Ÿ”ด apt_updates
   2 packages can be upgraded (2 security)
   Tap to apply โ€” no SSH needed.
    โ€ข SECURITY: openssl
    โ€ข SECURITY: libssl3
โœ… Apply security updates
โฐ Snooze apt_updates 4h
๐Ÿšซ Ignore apt_updates
๐Ÿ”„ Run watchlog now

Telegram bot โ€” the same action buttons reach the mobile app as push notifications.

Watchlog self-hosted web dashboard โ€” color-coded status tiles, severity banner, and sidebar navigation

Self-hosted web dashboard at api.watchlog.pl โ€” one tab for every server you run.

Watchlog mobile app โ€” phone screen showing host status, live disk and RAM bars, calendar history, and a push-notification banner

Native Flutter app โ€” pair with one QR scan, fix things straight from the lock screen.

03.End-to-end automated patching

watchlog detects; unattended-upgrades applies. Both are battle-tested, both ship with Ubuntu, both run as systemd timers. Wire them together once and the loop closes itself โ€” from Ubuntu releasing a security patch to your box being fully updated, with one one-time setup and no SSH afterwards.

Typical security update โ€” start to finish

14:00 UTC

Ubuntu releases a security update

New package appears in the -security suite. Mirrors usually sync within 30 minutes.

16:00 UTC ยท max +4h

watchlog notices it (every 4 hours)

  • Detects via apt list --upgradable
  • Escalates to CRITICAL because of the -security suite
  • Telegram + mobile push + email: "2 security updates available"
  • /status.json heartbeat updated for external monitors
Anytime ยท one tap

You tap the green button from your phone

The daemon runs unattended-upgrade -v, command output comes straight back to chat or to the mobile app, and the action is written to the audit log. From your couch, in seconds, with biometric confirmation on the app side.

Or 06:00 UTC next day

unattended-upgrades runs anyway (daily)

  • Installs only packages from the -security suite
  • Reboots automatically if a kernel update needs it (default 03:30, skipped if anyone is logged in)
  • Emails you the install log on change
Next watchlog tick

watchlog confirms the fix

Worst severity drops back to OK or INFO. The alert thread closes itself. No follow-up emails, no daily-digest spam.

End-to-end: seconds if you tap, โ‰ค16 hours if you ignore. Either path is fully automated. No SSH session required at any point.

Two cooperating timers

watchlog.timer

every 4 hours ยท 00, 04, 08, 12, 16, 20 UTC
Detects + notifies
๐Ÿ“ง email when WARN/CRITICAL
๐Ÿ“ฑ FCM push to paired phones
๐Ÿ’ฌ Telegram with action buttons
๐Ÿ“‹ /status.json + /var/log/watchlog/

apt-daily-upgrade.timer

daily ~06:00 UTC
Installs security updates
๐Ÿ“ง email on change
๐Ÿ” reboot if a kernel update needs it
๐Ÿ“ /var/log/unattended-upgrades/

04.REST API + OpenAPI docs

Every action the Telegram bot and the mobile app perform sits behind a documented FastAPI endpoint. Bind the daemon to localhost, terminate TLS with your existing nginx or Caddy, and integrate watchlog with anything that can speak HTTP. Full OpenAPI / Swagger docs live next to the API itself.

watchlog-api.service

FastAPI + uvicorn, localhost only
Bearer-authenticated, never exposed directly
Two scopes: read and act
Per-device tokens, SHA-256 hashed at rest
Token issuance + revocation auditable

Pair via QR

no-auth, rate-limited, single-use code
sudo watchlog api qr on the server
6-character code expires after 5 min
Locks out after 3 failed attempts
Token travels once over HTTPS at redemption

Endpoints (selected)

GET /api/v1/health
Public liveness probe (no auth) โ€” for external uptime monitors.
GET /api/v1/status
Latest heartbeat plus computed age_seconds. Structured metrics per check (status.json v2).
GET /api/v1/host
Hostname, OS, kernel, RAM/disk totals, uptime, IPs, timezone, watchlog version (used by mobile's "update available" banner).
GET /api/v1/checks/info
Bilingual (EN+PL) explainers for every check. Mobile clients fetch and cache.
GET /api/v1/reports[/{date}]
90-day archive of past runs with worst severity per day โ€” drives the mobile history calendar.
POST /api/v1/runs
Trigger a fresh watchlog run; returns combined output.
POST /api/v1/state/{snooze,ignore}
Cross-channel silencing. Telegram, email, and push all respect the same state file.
POST /api/v1/actions/apply-security
Runs unattended-upgrade -v. Whitelisted command; never arbitrary shell.
POST /api/v1/actions/restart-service
Restarts a whitelisted unit. Body: {"service": "nginx"}. Audit-logged.
POST /api/v1/actions/reboot
Disabled by default. Schedules shutdown -r +1 when enabled โ€” 60-second abort window.
POST /api/v1/actions/logs
Last N journalctl lines for a whitelisted unit. Read-only.
GET /api/v1/actions
Lists which action shortcuts the operator enabled. Mobile renders them as buttons.
GET ยท PATCH /api/v1/push/preferences
Per-device quiet hours, severity floor, per-check muting, smart cooldown grouping. Backend filters at FCM-send time, so rules apply even when the app is closed.
POST /api/v1/pair
Exchange a single-use code from watchlog api qr for a per-device token. No auth, rate-limited.
GET /api/v1/audit
Recent audit-log entries โ€” pair, token, and action events. Filterable by event-name prefix.

Roughly 25 endpoints in total. Full schema is browsable at api.watchlog.pl/docs (Bearer token required).

05.Security & privacy by default

watchlog runs on a server, executes commands as root, and talks to your phone โ€” so the security model matters more than the features. Every default is the safe one; every dangerous endpoint is off until you switch it on.

๐Ÿ”’

Localhost-bound by default

The API daemon listens on localhost only, never directly to the internet. Outside connections come through encrypted TLS on the reverse proxy in front of it.

๐Ÿ”‘

Per-device tokens

Every paired phone gets its own token. Lose a device, run watchlog api tokens revoke tok_xxx โ€” the other devices keep working.

๐Ÿ›ก๏ธ

SHA-256 hash at rest

Plaintext token is shown once at issuance and never again. The daemon stores only the hash.

๐Ÿ“ต

QR pair, not paste

The QR contains a 6-character single-use code (not the token). 5-minute expiry, lock-out after 3 failed attempts. The real token travels once during redemption.

๐Ÿ“‹

Newline-delimited audit log

Every auth, pair, token-issue, token-revoke, and action lands in /var/log/watchlog/audit.log as JSON. The mobile app surfaces it; nothing is hidden.

๐Ÿงฑ

Whitelisted actions only

Restart-service, apply-security, tail-logs, reboot โ€” each is a fixed command list the operator opts into. No arbitrary shell.

๐Ÿ”‡

Telegram chat-id whitelist

The bot accepts callbacks only from the chat_id you configured. Anything else is silently rejected and logged.

๐Ÿ‘†

Biometric app lock

Optional Face ID / fingerprint / device PIN gate on mobile. Android FLAG_SECURE hides content from screenshots and task switcher. Tokens live in Keystore / Keychain.

๐Ÿ’พ

Encrypted backup

Mobile app exports server list + tokens + preferences to a passphrase-encrypted blob (AES-256-GCM, PBKDF2 600k). Restore on a new phone without re-pairing.

๐Ÿ“Š

Opt-in telemetry, off by default

No crash reports, no usage stats leave the device until you turn them on in Settings. No tokens, hostnames, or personal data are ever collected.

๐Ÿ“ค

Your server, your data

watchlog has no cloud component. Every check runs locally; only reporters you enable (Telegram, email, FCM) emit anything outward.

โš–๏ธ

Auditable codebase

Roughly 4k lines of Python, readable end to end. No license keys, no calls home, no hidden cloud component.

Is tapping "Apply" from your phone safe?

Yes. The phone app never sends a command for the server to run. It only tells the server which button you pressed, and the server already knows exactly what it is allowed to do. There is no way to append or slip in a command of your own.

The phone only picks from a fixed list of actions you approved in advance: install security updates, restart a named service, show logs. Anything outside that list is simply refused and written to the audit log.

Every action needs your device's own private key (lose the phone and you revoke its access with one command), the connection is encrypted, and the service is never exposed to the open internet. In the worst case, someone holding your phone could at most tap the same safe buttons you can. They cannot get into the server or run anything off the list.

06.Deployed on your server, as a service

watchlog is not a download. We deploy and run it for you as a managed service. Installation, check configuration, Telegram, push notifications and the mobile app are all handled on our side, so you never touch a config file or a systemd unit.

Get in touch

Write to admin@belikebee.com and tell us what you want monitored. We scope it to your infrastructure and reply with the next steps.

We deploy and configure

We install watchlog on your server, wire up the checks, notification channels and the API, and run the first check together with you.

You get access

Once it is live you pair the mobile app and start receiving alerts. For any change or an extra server, just reach out to admin@belikebee.com.

Request deployment: admin@belikebee.com