kache 0.20.0

Zero-copy, content-addressed build cache for Rust, C/C++ and more, with S3 and shared-filesystem remotes.
---
title: Kache or sccache?
description: Choose a compiler cache based on the workflow you need
---

Kache and [sccache](https://github.com/mozilla/sccache#readme) both avoid repeated compiler work. This page explains the differences for teams moving to Kache or deciding whether it covers their build today.

This page describes the current projects; it does not claim that one cache is universally faster. Test the same repository, toolchain, runner, and remote before deciding.

## Main differences

| Question | Kache | sccache |
| --- | --- | --- |
| Primary workflow | Local-first cache with optional explicit remote synchronization | Client-server compiler cache with local and remote storage |
| Rust setup | `RUSTC_WRAPPER=kache`, `kache init`, or `kache cargo` | `RUSTC_WRAPPER=sccache` |
| C/C++ setup | PATH compiler-name shims (`kache install-shims`) or `CC="kache cc"` | Prefix wrapper (`sccache gcc`); no ccache-style PATH farm |
| Remote backends | S3-compatible storage and filesystem paths | S3, Redis, Memcached, GCS, Azure, GitHub Actions, WebDAV, and others listed by sccache |
| Inspection | `monitor`, `stats`, `why-miss`, `report`, `list`, and `doctor` | `--show-stats`, logs, and server commands |
| Remote transfer | On-demand restore plus `sync`, manifests, and prefetch | Remote access is part of normal server operation |
| Rust executables | Cacheable by default on Linux and macOS | Rust crates that invoke the system linker are not cached, according to the sccache README |
| Incremental Rust builds | Kache disables or isolates incremental state according to its configured policy | Incrementally compiled Rust crates are not cached, according to the sccache README |
| Fallback | Can hand Kache passthroughs to another wrapper with `KACHE_FALLBACK` | No Kache-specific handoff needed |

## Choose Kache when

- You want cache entries shared across local worktrees without a remote.
- You want to inspect individual events and ask why a compile missed.
- You want explicit pull, push, manifest, and prefetch controls for CI.
- Caching eligible Rust executable and linker outputs matters to your workload.
- You want one `PATH` change to cache Make/CMake/PKGBUILD object compiles without wrapping `CC` in a shell.

## Where Kache may not fit yet

- You need one of its additional remote backends.
- You need a compiler Kache does not support yet, such as CUDA or HIP.
- You must keep an existing sccache deployment unchanged during a migration.

If a missing compiler, backend, or workflow blocks your use of Kache, [open a feature request](https://github.com/kunobi-ninja/kache/issues/new?template=feature_request.md). Include the build command, compiler or backend, and why the fallback described below does not fit. Concrete workloads help us prioritize support.

## Measure your own build

Compare cold, local-hit, and remote-hit cases separately. Keep these fixed:

- repository revision and lockfile
- compiler and linker versions
- target triple and build profile
- machine or CI runner class
- remote region and credentials

Run several samples after one warm-up and compare medians. A count-based hit rate does not show how much compile time was avoided, so record wall time as well.

Kache can generate benchmark artifacts with `kache report` and the repository benchmark harness. See [Benchmarks](/docs/benchmarks).

## Keep sccache during migration

You can put Kache in front of an existing sccache setup. Kache passes compiler invocations it declines to cache to sccache:

```bash
export KACHE_FALLBACK=sccache
export RUSTC_WRAPPER=kache
cargo build
```

The fallback only receives passthrough work. Kache still owns the invocations it decides to cache or isolate. Remove the fallback when Kache covers the remaining workload.