# tlswatch > tlswatch is a self-hosted, open-source (MIT) TLS/SSL certificate monitor. It probes the certificates that are actually served on your hostnames and IP addresses, on any port (HTTPS, SMTP, IMAP, POP3, FTP, PostgreSQL, SIP, anything with TLS or STARTTLS), checks expiry, chain of trust, hostname, signature strength and legacy TLS 1.0/1.1, notices certificate changes, and alerts by e-mail, Telegram, Slack, Discord, ntfy or webhook before something expires. One Go binary with a web UI and a SQLite file; nothing else to run. Nodes probe from inside networks the server cannot reach. Website: https://tlswatch.nl/ Source and releases: https://github.com/sjoerd305/tlswatch Licence: MIT Language: Go (server-rendered HTML, small TypeScript helpers, no framework) Docker image: ghcr.io/sjoerd305/tlswatch (linux/amd64, linux/arm64, linux/arm/v7) Release binaries: Linux amd64, arm64, armv7; macOS amd64, arm64 ## What it does - Probes every address behind a name (IPv4 and IPv6), so one stale node behind a load balancer is caught. - Checks expiry against warning and critical thresholds, with separate defaults for manual and ACME-managed (Let's Encrypt) certificates. - Verifies the chain of trust for server authentication against the system store, a private CA bundle, or a pinned self-signed certificate. - Checks the hostname and the signature algorithm. - Tests once a day whether a server still accepts TLS 1.0 or TLS 1.1, and RC4, 3DES, RSA key exchange or CBC cipher suites, and grades the configuration A to F per target with reasons; weak suites and old versions are findings. - Certificate Transparency watching: domain watches follow the public logs (Cert Spotter or crt.sh) for every certificate issued for a domain and match it against what the targets serve; a certificate no target serves opens a finding, a renewal on its way does not. - Detects certificate and issuer changes; ACME renewals are recognised and stay quiet. - Reports when the addresses behind one name serve different certificates. - Keeps a certificate inventory (every certificate seen, where, until when), exportable as CSV. - Alerts on transitions, not on every run: a finding opens once, reminds, and sends a recovery notice; findings can be acknowledged, also in bulk. Optional weekly digest. - Alert channels: SMTP e-mail (plain text and HTML), Telegram, Slack (also Mattermost and Rocket.Chat incoming webhooks), Discord, ntfy, generic JSON webhook signed with HMAC-SHA256. Each channel has its own severity floor. - Nodes: `tlswatch node` on a host inside another network connects out to the server over HTTPS (long-poll, no WebSocket, no inbound port) and probes from there. The schedule, inventory, findings and alerts stay on the server. One install command; nodes update themselves with rollback. CA bundles stay on the server. - Targets can be added in bulk (one host per line) and edited as a selection. - Live pages (overview, targets, findings) update as checks land; every list column sorts. - Roles (viewer, operator, admin), local accounts and Google sign-in, an audit log. - Encrypted backup and restore from the UI, also on the setup screen of a new installation. - Optional Prometheus metrics at /metrics (targets, findings, outbox, expiry, grades, Certificate Transparency). Health endpoint at /healthz. - Everything is configured in the browser under Settings; environment variables are optional overrides. ## Install Docker, from a checkout: git clone https://github.com/sjoerd305/tlswatch cd tlswatch docker compose up --build -d open http://127.0.0.1:8081/ Or the released image `ghcr.io/sjoerd305/tlswatch:` with a volume on /data and port 8080. Binary: make build # or download a release binary from GitHub ./tlswatch serve # creates ./data/ and a secret key on first start open http://127.0.0.1:8080/ On first start a setup screen creates the first admin account, or restores a backup. Put a reverse proxy with TLS in front before exposing it, then set the public URL under Settings › General. Optional environment variables: TLSWATCH_LISTEN (127.0.0.1:8080), TLSWATCH_DB (./data/tlswatch.db), TLSWATCH_SECRET_KEY_FILE, TLSWATCH_LOG_JSON, TLSWATCH_DEBUG, TLSWATCH_BASE_URL, TLSWATCH_BEHIND_PROXY, TLSWATCH_METRICS. ## Command line tlswatch check HOST[:PORT] [-protocol smtp|imap|pop3|ftp|postgres] [-servername NAME] [-ca-file FILE] [-no-legacy] Probes one endpoint without a server, prints JSON (status, grade, days_left, not_after, issuer, per-address TLS version, verification, legacy_accepted, weak_suites_accepted, grade and grade_reasons, findings) and exits 0 ok, 1 warning, 2 critical. Other commands: serve, create-admin, migrate, backup PATH, healthcheck, rotate-key, node (enrol, uninstall), version. ## Documentation - [README](https://github.com/sjoerd305/tlswatch/blob/main/README.md): overview, quick start, configuration, commands - [Operations guide](https://github.com/sjoerd305/tlswatch/blob/main/docs/operations.md): first start, environment overrides, backups and upgrades, monitoring, networks, nodes - [Specification](https://github.com/sjoerd305/tlswatch/blob/main/docs/specification.md): the complete behaviour, kept in step with the code - [Changelog](https://github.com/sjoerd305/tlswatch/blob/main/CHANGELOG.md) - [Security policy](https://github.com/sjoerd305/tlswatch/blob/main/SECURITY.md) - [Releases](https://github.com/sjoerd305/tlswatch/releases)