Uptime Kuma is a self-hosted alternative to services like UptimeRobot. It checks your websites, APIs, servers and services as often as every 20 seconds, over HTTP, TCP, ping, DNS, WebSocket, keyword and JSON-query checks, Docker container status, game servers and push heartbeats, and tells you the moment something goes down. Alerts go out through more than 90 services, including Telegram, Discord, Slack, email and Pushover.
It is known for being pleasant to use: a fast, reactive dashboard with response-time charts and certificate expiry warnings, plus public status pages you can map to your own domain to show customers what is up. Setup is one Docker command and everything is configured from the browser, with two-factor login available.
It is MIT-licensed, with about 92,600 stars and 1,145 contributors, at version 2.5.6 when scanned. Version 2 is the current line, and the project has a live demo that resets every ten minutes.
- Repository: github.com/louislam/uptime-kuma
- Licence: MIT (MIT License)
- Language: JavaScript. Stars: 92.6K. Forks: 8,569. Last push: Oct 19, 2026.
- Scan: safe, Oct 19, 2026, commit b092505
Who it is for
Home-lab users, freelancers and small teams who want to know when a site or service goes down without paying for a monitoring subscription, and who can keep one small server or container running.
Getting started
1. Run it with Docker, reachable only from this machine
docker run -d --restart=always -p 127.0.0.1:3001:3001 -v uptime-kuma:/app/data --name uptime-kuma louislam/uptime-kuma:22. Open the dashboard and create the admin account
open http://localhost:3001The README's own command publishes port 3001 on every network interface; the version above keeps it on localhost until you put it behind a reverse proxy. Keep the data on a local disk or volume, since NFS is not supported. A Docker Compose file and a Node.js install without Docker are in the README.
Safety scan
We cloned louislam/uptime-kuma at commit b092505 on Oct 19, 2026 and ran the checks described on the GitHub Tools page: credential patterns, decode-and-execute code, install-time scripts, committed binaries, risky CI workflows, every host the code talks to, known vulnerabilities in pinned dependencies, and project hygiene. A person read every hit. This is what we found.
- The 11 secret hits are placeholders: the text BEGIN PRIVATE KEY shown as a hint in the SMTP and SFTP forms, its translations, and a test key for the SFTP monitor. No committed binaries and no bare-IP URLs across 819 files and about 154,000 lines.
- The one pattern hit is a curl | bash for the NodeSource setup script inside a Dockerfile used to build a helper image. It runs at image build time, not on your machine.
- 62 known advisories (3 critical, 27 high) in package-lock.json. Of the criticals, shell-quote is a development dependency; tar is used only by a script that downloads the front-end build; and proxy-addr, through Express, concerns trusted-proxy subnet lists, while Uptime Kuma's reverse-proxy setting is a yes or no. Many of the highs (undici, busboy) sit in test containers. Updating to each new release is still the right habit.
- The many outside hosts are its notification providers, from Telegram to regional SMS gateways, which it contacts only when you configure them.
- 21 workflows; nine use pull_request_target, and none checks out PR code: they label, comment, or check PR titles and descriptions. 26 of 28 third-party actions are pinned to commits, and CodeQL and Dependabot are on. Licence, security policy, contributing guide and code of conduct present.
What the scanner counted
| Check | Result |
|---|---|
| Secrets | 11 candidates found and read; see the notes above. |
| Suspicious code | 1 pattern hit found and read; every one is listed under the raw findings. |
| Install-time code | None: nothing runs at install beyond the package manager itself. |
| Committed binaries | None. |
| CI workflows | 21 workflows. 9 use pull_request_target, none check out the pull request head. 2 of 28 third-party actions pinned to a tag rather than a commit. |
| Network hosts | 40 distinct hosts referenced from source; most often github.com, stackoverflow.com, wikipedia.org, www.webfx.com. No URLs to bare IP addresses. |
| Known vulnerabilities | 62 advisories across 1,187 pinned packages: 3 critical, 27 high, 25 moderate, 7 low. package-lock.json: 1,303 packages, 62 advisories. |
| Project hygiene | Has security policy, automated dependency updates, CodeQL, licence file, contributing guide. |
| OpenSSF Scorecard | Not scored: the project is not in Scorecard's weekly index. |
The raw findings
Every hit the scanner wrote out, with a link to the exact line at the scanned commit. Secrets candidates are redacted.
Secret candidates (11, redacted)
| Where | Rule | Match |
|---|---|---|
| src/components/notifications/SMTP.vue:247 | private-key | -----B…--- (27 chars) |
| src/lang/ca.json:1661 | private-key | -----B…--- (35 chars) |
| src/lang/en.json:1398 | private-key | -----B…--- (35 chars) |
| src/lang/en_GB.json:1618 | private-key | -----B…--- (35 chars) |
| src/lang/fr-FR.json:1754 | private-key | -----B…--- (35 chars) |
| src/lang/pt-BR.json:1711 | private-key | -----B…--- (35 chars) |
| src/lang/sk.json:1702 | private-key | -----B…--- (35 chars) |
| src/lang/sv-SE.json:1696 | private-key | -----B…--- (35 chars) |
| src/lang/zh-CN.json:1751 | private-key | -----B…--- (35 chars) |
| test/backend-test/monitors/test-sftp.js:294 | private-key | -----B…--- (35 chars) |
| test/backend-test/monitors/test-tcp.js:25 | private-key | -----B…--- (27 chars) |
Pattern hits (1)
| Where | Rule | Match |
|---|---|---|
| docker/builder-go.dockerfile:12 | download-piped-to-shell | curl -sL https://deb.nodesource.com/setup_24.x | bash && \ |
Worst known vulnerabilities (24 of 62)
| Advisory | Severity | Package | Summary |
|---|---|---|---|
| GHSA-jqcg-44mw-7w3h | critical | proxy-addr@2.0.7 | proxy-addr vulnerable to IP spoofing via IPv4-mapped IPv6 trust subnet |
| GHSA-pqg4-j6r4-53mv | critical | shell-quote@1.10.0 | shell-quote: `quote()` command injection via a line terminator in a token after a `{ comment }` token |
| GHSA-23hp-3jrh-7fpw | critical | tar@6.2.1 | node-tar: Decompression/parse DoS via unlimited input |
| GHSA-6j4f-fj2g-mc7p | high | brace-expansion@1.1.18 | brace-expansion: DoS via uncontrolled recursion in parseCommaParts causing stack exhaustion |
| GHSA-qhr7-859c-m2p7 | high | brace-expansion@1.1.18 | brace-expansion: DoS via uncontrolled recursion on nested brace groups causing stack exhaustion |
| GHSA-x8mw-p69m-v3mx | high | @fastify/busboy@2.1.1 | @fastify/busboy vulnerable to Denial of Service via prototype-named multipart part header |
| GHSA-5375-pq7m-f5r2 | high | @grpc/grpc-js@1.8.22 | @grpc/grpc-js: A malformed request can cause a server crash |
| GHSA-99f4-grh7-6pcq | high | @grpc/grpc-js@1.8.22 | @grpc/grpc-js: An incoming malformed compressed message can cause a client or server crash |
| GHSA-m9gg-hp2v-232j | high | @grpc/grpc-js@1.8.22 | @grpc/grpc-js: In certain configurations, getAuthContext can return unauthorized certificates as though they were author… |
| GHSA-v9p9-hfj2-hcw8 | high | undici@5.29.0 | Undici has Unhandled Exception in WebSocket Client Due to Invalid server_max_window_bits Validation |
| GHSA-vrm6-8vpv-qv8q | high | undici@5.29.0 | Undici has Unbounded Memory Consumption in WebSocket permessage-deflate Decompression |
| GHSA-vxpw-j846-p89q | high | undici@5.29.0 | undici WebSocket client vulnerable to denial of service via fragment count bypass |
| GHSA-x97p-jq2g-jp4f | high | axios@0.33.0 | Axios: Prototype Pollution Gadget in axios toFormData Options |
| GHSA-6j4f-fj2g-mc7p | high | brace-expansion@2.1.4 | brace-expansion: DoS via uncontrolled recursion in parseCommaParts causing stack exhaustion |
| GHSA-qhr7-859c-m2p7 | high | brace-expansion@2.1.4 | brace-expansion: DoS via uncontrolled recursion on nested brace groups causing stack exhaustion |
| GHSA-vfj7-8cjw-p6xm | high | braces@3.0.3 | braces vulnerable to stack-exhaustion denial of service through deeply nested patterns |
| GHSA-m9gg-hp2v-232j | high | @grpc/grpc-js@1.14.4 | @grpc/grpc-js: In certain configurations, getAuthContext can return unauthorized certificates as though they were author… |
| GHSA-ch52-4w7c-c8xp | high | http-cache-semantics@4.2.0 | http-cache-semantics max-stale handling can disclose cross-user cached responses |
| GHSA-23c5-xmqv-rm74 | high | minimatch@9.0.3 | minimatch ReDoS: nested *() extglobs generate catastrophically backtracking regular expressions |
| GHSA-3ppc-4f35-3m26 | high | minimatch@9.0.3 | minimatch has a ReDoS via repeated wildcards with non-matching literal in pattern |
| GHSA-7r86-cg39-jmmj | high | minimatch@9.0.3 | minimatch has ReDoS: matchOne() combinatorial backtracking via multiple non-adjacent GLOBSTAR segments |
| GHSA-68fv-2mgg-jv7q | high | source-map-js@1.2.1 | source-map-js allows event-loop denial of service through indexed source-map section offsets |
| GHSA-34x7-hfp2-rc4v | high | tar@6.2.1 | node-tar Vulnerable to Arbitrary File Creation/Overwrite via Hardlink Path Traversal |
| GHSA-83g3-92jg-28cx | high | tar@6.2.1 | Arbitrary File Read/Write via Hardlink Target Escape Through Symlink Chain in node-tar Extraction |
Workflows worth a look
- .github/workflows/ai-slop.yml: pull_request_target
- .github/workflows/auto-test.yml: pull_request_target
- .github/workflows/conflict-labeler.yml: pull_request_target
- .github/workflows/deleted-pr.yml: pull_request_target
- .github/workflows/mark-as-draft-on-requesting-changes.yml: pull_request_target
- .github/workflows/new-contributor-pr.yml: pull_request_target
- .github/workflows/pr-description-check.yml: pull_request_target
- .github/workflows/pr-title.yml: pull_request_target
- .github/workflows/prevent-file-change.yml: pull_request_target
By the numbers
| Stars | 92.6K |
|---|---|
| Forks | 8,569 |
| Contributors | 1,145 |
| Commits | 7,384 |
| Open issues | 735 |
| Open pull requests | 112 |
| Releases | 137 |
| Latest release | 2.5.6 |
| Licence | MIT |
| Main language | JavaScript |
| Project age | 5 years |
| Last push | Oct 19, 2026 |
| Tracked files | 819 |
| Lines of code | 154.4K |
| Checkout size | 9 MB |
Lines by language: JSON 69.5K, JavaScript 45.9K, Vue 31.2K, TypeScript 1,992, YAML 1,970, Markdown 1,649.
Questions
Is Uptime Kuma free?
Yes. Uptime Kuma is MIT-licensed and free to self-host, with no limits on monitors or status pages. The only costs are the machine it runs on and any paid notification service you choose, such as SMS.
Should I run Uptime Kuma on the server it monitors?
Better not. If that server goes down, the monitor goes down with it and cannot alert you. A small VPS, a Raspberry Pi at home or a different cloud region is a better place for it.
Can Uptime Kuma make a public status page?
Yes. You can create several status pages, choose which monitors each shows, and map them to your own domain, so customers can check whether a service is up without logging in.
This post is part of GitHub Tools, where every repository is cloned and scanned before it is written up. The scan is a snapshot of one commit on one day; the repository has moved on since, so check it before you install.
