Linux Knowledge Portal All articles
Home Lab

One Mini PC, Five Distros: A Home Lab Package Cache That Keeps Your Data Cap Intact

Linux Knowledge Portal
One Mini PC, Five Distros: A Home Lab Package Cache That Keeps Your Data Cap Intact

Photo: Antti Nissinen, CC BY-SA 3.0, via Wikimedia Commons

My house has five Linux machines: two Ubuntu laptops, a Debian file server, a Fedora workstation, and a Linux Mint box that mostly runs a browser and a tax spreadsheet. Every few weeks they all want the same kernel, browser, and library updates. On a metered connection, watching three machines pull the same 600 MB update in one evening is a special kind of annoying. The router should not be the only shared service in the house.

So I built a small LAN package cache. It is not an enterprise mirror, and it does not need to be. A spare mini PC with a 2 TB SSD sits on the wired network, downloads packages once, and serves them to everyone else. The project turned into a reusable guide for our local Linux user group, which means the configs live in a sanitized Git repo instead of a scrap of paper taped to the server.

The shape of the thing: one cache host, two package ecosystems

The architecture is boring on purpose. The cache host has a static address, 192.168.50.10, and a DHCP reservation so it never wanders. It is wired to the switch, not hanging off Wi-Fi. It runs Debian stable and does two jobs: apt-cacher-ng on port 3142 for the Debian, Ubuntu, and Mint machines, and nginx on port 80 for a trimmed Fedora repository mirror.

Clients talk to the cache host first. On a miss, the cache host fetches from the upstream archive. On a hit, the package comes off local disk. That is the whole trick. The cache host still updates itself directly from upstream, and there is no port forwarding from the internet. This is a LAN service, not a public mirror.

Debian, Ubuntu, and Mint: let apt-cacher-ng be boring

apt-cacher-ng is one of those tools that does not get exciting, which is exactly why I like it. Install it on the cache host, confirm it is listening on 3142, and point the Debian-family clients at it with an apt proxy line. The cache directory is usually /var/cache/apt-cacher-ng, and the built-in report page at http://192.168.50.10:3142/acng-report.html tells you whether requests are hits, misses, or errors.

On each client, drop a file in /etc/apt/apt.conf.d/ that contains:

Acquire::http::Proxy "http://192.168.50.10:3142";

That is enough for ordinary HTTP archive traffic. Here is the honest caveat: apt-cacher-ng cannot cache encrypted HTTPS package payloads. If your sources are HTTPS-only, the cache will not help for those repos unless you switch to an HTTP mirror, and that is a trade-off, not a free lunch. For official archives, I use HTTP endpoints where they exist because apt still verifies package and metadata signatures. I do not terminate TLS at the cache to force caching. HTTPS-only third-party repos stay direct.

Also remember what this does not cover: Snap packages, Flatpaks, container images, and browser self-updaters are separate download paths. The cache is for apt traffic. Do not expect it to solve every byte on your monthly ISP statement.

Fedora: mirror less than you think

dnf does not use apt-cacher-ng, so the Fedora side needs its own answer. A full Fedora mirror is enormous. Do not do that in a basement. Mirror only what your house actually runs: the release and updates repositories for x86_64, newest packages only, no source RPMs, no debuginfo, no test days, no rawhide.

The pieces are reposync from dnf-plugins-core, createrepo_c, and nginx. A daily systemd timer runs reposync with --newest-only and --delete, then refreshes the repository metadata. On the client, point a local repo file at the cache host and keep gpgcheck=1. Never disable GPG checking just to make a mirror work. The exact baseurl depends on how reposync lays out the directories, so check the tree with find before you write the repo file.

A minimal client repo file looks roughly like this, with the real paths filled in:

[fedora-local]
name=Fedora local mirror
baseurl=http://192.168.50.10/fedora/fedora/$releasever/$basearch/
enabled=1
gpgcheck=1
metalink=

Keep the Fedora GPG keys available locally or point gpgkey at the upstream key file. The point is not to bypass Fedora's signing. The point is to stop downloading the same signed RPM five times.

The trust question: a cache is infrastructure, not a magic tunnel

A LAN cache is another machine that can fail, fill up, or get compromised. It does not replace package signature checks. Debian packages and Fedora RPMs are signed, and apt and dnf verify them. But a cache can still serve stale metadata, withhold updates, or become a pivot point if someone gets into it.

So treat it like infrastructure. Put it on a trusted VLAN or at least a trusted subnet. Firewall the cache ports so only your Linux clients can reach them. Do not expose the cache host to the internet. Keep it patched. Watch disk space. Back up the configuration, not the cache contents. And do not turn the cache into a TLS interception box just to squeeze out a few more hits. That trades a manageable availability risk for a much worse trust problem.

For small offices and user groups, the rule is the same: the cache should be boring, restricted, and easy to rebuild. If it dies, clients should fall back to normal upstream access with one config change.

Measure the savings like an adult

A cache that feels fast is not proof of savings. Get a baseline first. Note your router's monthly WAN counters, or run vnstat on the cache host for a full month before you roll the cache out. After the cache has warmed, compare total client package requests against upstream bytes. The apt-cacher-ng report gives you hit rates and bytes saved. nginx logs show Fedora mirror traffic. vnstat shows what actually crossed the WAN link.

My own first month was misleading because the cache was cold. The second month was the real number: five machines requested about 41 GB of package data, and the WAN side saw roughly 14 GB. Your mileage will vary with distro mix, update habits, and how many third-party repos you use. The cache host itself still downloads its own updates, and misses still happen. Count those honestly.

Make it a community asset

The best part of this project is not the bandwidth bill. It is that the setup is reusable. Write a README. Include a simple network diagram, sanitized configs, the systemd timer, a security checklist, and a measurement template. Share it with your Linux user group, a neighbor with three Ubuntu laptops, or a small office that keeps hitting a data cap. Update it when distro releases change paths or when a new package format makes part of the guide obsolete.

One home lab problem becomes a guide that saves someone else a weekend. That is the Linux Knowledge Portal spirit, and it is why the little mini PC in my basement has become the most popular box in the house.

All Articles

Related Articles

The Two-Server Problem: Auditing /etc Drift Before It Audits You

The Two-Server Problem: Auditing /etc Drift Before It Audits You

The Manual Is Already on Your Machine: Learning to Read man Pages Like a Veteran Sysadmin

The Manual Is Already on Your Machine: Learning to Read man Pages Like a Veteran Sysadmin

When the Drive Dies at 2 A.M.: A Homelab Recovery Drill You Can Actually Practice

When the Drive Dies at 2 A.M.: A Homelab Recovery Drill You Can Actually Practice