Once in a while I need to throw a directory online. Share a build artifact with a colleague, expose a folder of files inside a Kubernetes cluster, mount a release directory behind an internal nginx — the kind of task where a full web server is overkill and python3 -m http.server is too primitive.

That’s the niche httpfileserver fills: a single static Go binary (or a scratch-based Docker image) that serves a directory, with the few quality-of-life features I always end up wanting.

What’s in the box

httpfileserver is honest about what it is. From the README:

A simple webserver in Golang to expose a directory by http.

That’s the whole pitch. There’s no upload, no fancy UI, no markdown rendering. What you do get on top of “static files over HTTP”:

  • Optional basic auth via HTTP_USER / HTTP_PASSWORD environment variables
  • Configurable read / write / idle timeouts via flags or environment variables
  • A /health endpoint (200 + {"status":"ok"}) suitable for Kubernetes probes
  • A multi-arch scratch Docker image — no shell, no libc, just the binary

That’s it. That’s the tool.

Running it

The simplest invocation:

httpfileserver -d /data -p 8081

With basic auth, set the two environment variables before launching:

export HTTP_USER=alice
export HTTP_PASSWORD=somethingsecret
httpfileserver -d /data -p 8081

If you’ve got a long upload or a slow client, bump the timeouts:

httpfileserver -d /data -p 8081 \
  --read-timeout 60s \
  --write-timeout 120s

Same thing with environment variables (flags win when both are set):

export HTTP_WRITE_TIMEOUT=300s
export HTTP_IDLE_TIMEOUT=600s
httpfileserver -d /data

Values accept Go duration strings — 30s, 5m, 1h30m — with a minimum of 1s.

The Docker story

The container image is FROM scratch, multi-arch, and tiny. Drop it into a docker-compose.yml to share a folder on a homelab box:

services:
  files:
    image: sgaunet/httpfileserver:latest
    ports:
      - "8081:8081"
    environment:
      HTTP_USER: alice
      HTTP_PASSWORD: ${FILES_PASSWORD}
      HTTP_READ_TIMEOUT: 60s
    volumes:
      - ./shared:/data:ro
    command: ["-d", "/data", "-p", "8081"]

Or if you’re putting it on Kubernetes, the /health endpoint plugs straight into a probe:

livenessProbe:
  httpGet:
    path: /health
    port: 8081
readinessProbe:
  httpGet:
    path: /health
    port: 8081

The /health endpoint deliberately bypasses basic auth so probes don’t need credentials.

When (not) to use it

The README is upfront about scope: this project exists for fun and small-scale use, and you should reach for nginx or Caddy when you need real production hosting. I agree. What httpfileserver is good at is the in-between case where you want something more configurable than python3 -m http.server but lighter than spinning up a full reverse proxy with a config file.

I keep a copy in my homelab and pull it into CI sometimes when a job needs to expose a directory to a follow-up step over HTTP.

Where to grab it

If you ever catch yourself muttering “I just want this folder on a port for ten minutes,” give it a try. It does exactly that, and very little else — which I consider a feature.