Skip to main content

Where things live

Project-local (inside your repo, not system-wide)

Quick decisions

  • Installing a CLI tool just for you?~/.local/bin (no sudo, no root pollution)
  • Config for a tool you use daily?~/.config/<tool>/ — this is the XDG Base Directory convention, the modern per-user layer on top of FHS
  • Installing/packaging something as a proper deb/rpm? → binaries in /usr/bin, config in /etc/myapp/, persistent state in /var/lib/myapp/, logs in /var/log/myapp/
  • Running a local service (DB, web server) and need its data to persist?/var/lib/<service>/
  • That service’s logs?/var/log/<service>/
  • A big third-party dev tool (Android Studio, a proprietary SDK)?/opt/
  • Built something from source you want available system-wide?/usr/local/bin
  • Just need scratch space for a build or test run?/tmp (safe to lose anytime, gone on reboot)
  • App-managed cache that’s safe to lose but you’d rather not rebuild constantly?/var/cache/<app>/
  • Something that must survive a reboot but isn’t “real” persistent state?/var/tmp/
  • A dev server’s PID or socket file while it’s running?/run/ (gone after reboot, which is what you want)
  • Plugged in a USB drive or SD card? → shows up under /media/ automatically
  • Mounting a network share or external disk yourself?/mnt/
  • Docker/container volumes? → mounted separately, doesn’t follow this hierarchy at all inside the container’s writable layer

One habit worth keeping

Never hand-edit anything under /usr/bin or /usr/lib — those are package-manager territory and get silently overwritten/removed on the next apt upgrade. If you need something persistent and yours, it goes in /usr/local or /opt, never /usr directly.