Latchkey vs GitHub hosted runners, and where each one wins
Latchkey vs GitHub hosted runners comes down to a number you can compute from two published rate cards: $0.0025 a minute against $0.006 is 58% cheaper per 2 vCPU Linux minute, but Latchkey charges a monthly plan fee and GitHub gives you included minutes, so the break-even sits near 7,700 Linux minutes a month. Below that, staying put is cheaper, and on a public repository nothing paid can compete at all.

GitHub-hosted runners are the default and the safe answer: nothing to install, an included monthly allowance, every platform GitHub sells, and larger runners up to 96 vCPU. The standard Linux runner on a private repository is 2 vCPU with 8 GB of RAM and 14 GB of disk; on a public repository the same label gives 4 vCPU and 16 GB, free and unlimited.
Latchkey sells managed runners you adopt with a runs-on change, at $0.0025 a minute for 2 vCPU and 8 GB with 100 GB of disk, rising to $0.02 at 16 vCPU. Its argument is the rate plus what happens when a job fails for a mechanical reason: the runner diagnoses the failure and retries inside the run rather than handing it back to you. Its limits are equally plain, and they are listed below rather than buried.
Every cell below was read from the vendor's own public pricing or documentation page on 20 September 2026. Where a vendor does not publish a number, the cell says "not published" instead of carrying a guess.
GitHub-hosted and Latchkey side by side (read 20 September 2026)
| GitHub-hosted | Latchkey | |
|---|---|---|
| Price per minute, 2 vCPU Linux x64 | $0.006 (2 vCPU, 8 GB RAM, 14 GB SSD on a private repo; free on public repos) | $0.0025 (2 vCPU, 8 GB RAM, 100 GB disk) |
| Price per minute, 4 vCPU Linux x64 | $0.012 as a larger runner; the free public-repo standard runner is already 4 vCPU and 16 GB | $0.005 (4 vCPU, 16 GB RAM, 100 GB disk) |
| Free tier | 2,000 minutes a month on Free, 3,000 on Team, 50,000 on Enterprise Cloud, private repos only, consumed at the runner multiplier; larger runners are always billed | 30-day trial, then 2,000 included minutes a month on Developer, 4,000 on Launch, 6,000 on Scale |
| Billing granularity | Every job is rounded up to the nearest whole minute | Per minute |
| Runner sizes and OS | Linux x64 and arm64, Windows x64 and arm64, macOS on Apple silicon and Intel; larger runners to 96 vCPU x64 and 64 vCPU arm64 | 2, 4, 8 and 16 vCPU, Ubuntu 24.04 on x86_64 only. arm64, Windows and macOS are not offered |
| Cache: type, limit, persistence | actions/cache, 10 GB per repository, entries removed after 7 days without access, restorable only from the same or the default branch | Size not published. latchkey-dev/cache-action@v1 swaps one line for actions/cache, keeping path, key and restore-keys; entries are isolated per organization, versioned by OS, kept 14 days; a failed restore warns rather than failing the job |
| Docker build acceleration | None built in. cache-to: type=gha writes into the same 10 GB store | latchkey-dev/docker-cache-action@v1, layers held in a Latchkey-managed private registry per organization |
| Concurrency limits | 20 concurrent jobs on Free, 40 on Pro, 60 on Team, 500 on Enterprise Cloud. macOS is capped separately at 5, or 50 on Enterprise | Not published; warm-pool capacity varies by plan |
| Where jobs run | GitHub's own hosted fleet | Latchkey's own AWS estate on m6a-class hosts, one job per runner, private network, destroyed after the job |
| Self-healing or retries | None. A failed job waits for a person, or for retry logic you wrote yourself | Built in: transient failures are diagnosed and retried inside the run |
| Setup change required | None; this is the default | A runs-on label change. GitHub organization accounts only |
Where GitHub-hosted wins
This is the section that decides the page, so it goes first. Four of these are structural, not a matter of taste, and on any one of them the comparison is over before the rate card matters.
- Public repositories. Standard GitHub-hosted runners are free and unlimited there, on a 4 vCPU and 16 GB machine, which is a better runner than the 2 vCPU tier anyone sells and costs nothing at all.
- Anything that is not Linux x86_64. Latchkey has no arm64, no Windows and no macOS runner. If your matrix builds an iOS app or a Windows binary, those jobs stay on GitHub-hosted and your bill has two vendors on it.
- Low volume. GitHub includes 2,000 minutes a month on Free, 3,000 on Team and 50,000 on Enterprise Cloud, and Latchkey charges $5 to $49 a month before the first minute. Under a few thousand Linux minutes, the plan fee is larger than the saving.
- Personal accounts. Latchkey works with GitHub organization accounts only, so a repository under a personal account cannot use it whatever the price.
- Sizes above 16 vCPU. GitHub sells larger runners to 96 vCPU x64 and 64 vCPU arm64; Latchkey publishes four sizes and stops at 16.
- Published concurrency. GitHub states 20 to 500 concurrent jobs by plan and 5 concurrent macOS jobs, 50 on Enterprise. Latchkey documents 20 busy runners per workspace by default, raised on request, in its runner limits read 2026-09-20, so a wide matrix queues sooner than it would on a Team plan. The same page caps a job at four hours.
The break-even, in one line of arithmetic
Both sides have a fixed part and a variable part, so a per-minute comparison on its own is misleading. On a GitHub Team plan you pay nothing until the 3,000 included minutes are gone, then $0.006 a minute. On the Latchkey Launch plan you pay $19 a month, get 4,000 included minutes, then pay $0.0025. Set the two equal and the crossover is 7,714 Linux minutes a month.
That is the number to check your own usage against, and it moves with the plan you would actually buy: on the $49 Scale plan, with 6,000 included minutes, the crossover is 14,857 minutes a month. Everything below assumes 2 vCPU Linux jobs on a private repository, which is the comparison most teams are actually making.
| Linux minutes a month, 2 vCPU | GitHub-hosted on Team | Latchkey on Launch ($19) | Cheaper |
|---|---|---|---|
| 2,000 | $0, inside the 3,000 included | $19, inside the 4,000 included | GitHub-hosted |
| 5,000 | $12 for 2,000 billed minutes | $21.50 for 1,000 billed minutes | GitHub-hosted |
| 7,714 | $28.28 | $28.29 | Level |
| 10,000 | $42 for 7,000 billed minutes | $34 for 6,000 billed minutes | Latchkey |
| 20,000 | $102 | $59 | Latchkey |
| 50,000 | $282 | $134 | Latchkey |
Speed
Not benchmarked yet; the runner benchmark report will replace this section. We have not run the same workload on these runners ourselves, and until we have, there is no number here worth quoting.
The cheap way to get a real answer is to point one slow job at each candidate for a week, because runner selection is per job and the Actions run log gives you the timings for free.
Cost: the same month, both ways
The table above nets each side's included minutes off, because that is how a Linux-only bill actually arrives. The one below does not: it is the workload every comparison here uses, stated gross on both sides so the pages are comparable, at 10,000 Linux minutes at 2 vCPU plus 2,000 macOS minutes a month on a private repository.
| 10,000 Linux minutes at 2 vCPU | 2,000 macOS minutes | Monthly total | |
|---|---|---|---|
| GitHub-hosted | $60 at $0.006/min | $124 at $0.062/min | $184 |
| Latchkey | $25 at $0.0025/min | Not offered: $124 on GitHub-hosted | $149 plus $5 to $49 a month for the plan |
Read that table with the macOS column in mind, because it is doing most of the work. Latchkey has no macOS runner, so those 2,000 minutes stay on GitHub-hosted at $0.062 a minute in both rows, and the entire difference between $184 and $149 comes from the Linux line. Latchkey's own plan is $5 to $49 a month on top of that compute, and its 2,000 to 6,000 included minutes are not netted off, so the figure is gross on both counts.
One more line that catches teams out, and it is GitHub's, not ours: included minutes are consumed at the runner multiplier, and macOS is 10x. A Team plan's 3,000 included minutes are gone after 300 macOS minutes, which is why so many Actions bills turn out to be mostly macOS. If that is your shape, macOS runner cost is a more useful page than this one, and no Linux rate will fix it.
Reliability
GitHub publishes a status history rather than an Actions SLA, and Latchkey publishes no uptime figure either, so treat both as unmeasured on that axis and do not let either of us claim otherwise. What is different is documented behavior on a bad job. On GitHub-hosted, a step that dies because a registry timed out, a browser binary did not install, or the kernel killed the process fails the job, bills the minutes it burned, and waits for a person; the re-run bills again.
Latchkey runners diagnose that class of failure and retry inside the run. It is worth being precise about what that does not cover: a compile error, a failing assertion or a genuine out-of-memory in your own code are not transient, and retrying them would be a bug rather than a feature. The way to size the difference is to count the runs in your own history that passed on the second attempt with no code change between them, which is the same measurement exit code 137 in GitHub Actions walks through for one specific failure.
Switching: the exact diff
One label per job, and nothing else in the workflow moves: steps, actions, secrets, matrix and artifacts are untouched, and reverting is the same edit backwards. Runner selection is per job, so the sensible trial is one job for a fortnight rather than a repository-wide decision, and a mixed file with macOS jobs still on GitHub-hosted is the normal end state rather than a compromise.
jobs:
test:
- runs-on: ubuntu-latest
+ runs-on: latchkey-small
build:
- runs-on: ubuntu-latest
+ runs-on: latchkey-medium
ios:
# stays on GitHub-hosted: Latchkey has no macOS runner
runs-on: macos-latestThe verdict
If your CI is public, low volume, or built on anything other than Linux x86_64, GitHub-hosted is the right answer and this comparison is not close. The case for Latchkey starts at roughly 7,700 private-repo Linux minutes a month on a Team plan, where the 58% lower rate finally clears the plan fee, and it gets stronger from there: at 20,000 minutes it is $59 against $102, and at 50,000 it is $134 against $282. The second half of the case is the one the rate cards cannot show, which is what happens to the jobs that fail for reasons that have nothing to do with your code, and the honest way to price that is to count your own re-runs rather than to take our word for it. Whatever you decide, the decision is one line per job and reversible in a minute, which is the strongest argument for testing it on one job instead of arguing about it.