[HN Gopher] A decade of Docker containers
___________________________________________________________________
A decade of Docker containers
Author : zacwest
Score : 201 points
Date : 2026-03-07 16:55 UTC (6 hours ago)
(HTM) web link (cacm.acm.org)
(TXT) w3m dump (cacm.acm.org)
| zacwest wrote:
| The historic information in here was really interesting, and a
| great example of an article rapidly expanding in scope and
| detail. How they combatted corporate IT "security" software by
| pretending to be a VPN is quite unexpected.
| the__alchemist wrote:
| I'm optimistic we will succeed in efforts to simplify linux
| application / dependency compatibility instead of relying on
| abstractions that which work around them.
| Joker_vD wrote:
| I am also optimistic we will succeed in efforts to properly
| annotate the data on the Internet with useful and accurate
| meta-data and achieve the semantic web vision instead of
| relying on search engines and LLMs.
| __MatrixMan__ wrote:
| Agreed.
|
| I've recently switched from docker compose to process compose
| and it's super nice not to have to map ports or mount volumes.
| What I actually needed from docker had to do less with
| containers and more with images, and nix solves that problem
| better without getting in the way at runtime.
| onei wrote:
| Assuming I've found the right process-compose [1], it struck
| me as having much overlap with the features of systemd. Or at
| least, I would tend to reach for systemd if I wanted
| something to run arbitrary processes. Is there something
| additional/better that process-compose does for you?
|
| [1]: https://github.com/F1bonacc1/process-compose
| __MatrixMan__ wrote:
| That's the one, although I tend to reference it through
| https://github.com/juspay/services-flake because that way I
| end up using the community-maintained configs for whatever
| well-known services I've enabled (I'll use postgres as an
| example below, but there are many:
| https://community.flake.parts/services-flake/services)
|
| What process-compose gives me is a single parent with all
| of that project's processes as children, and a nice TUI/CLI
| for scrolling through them to see who is happy/unhappy and
| interrogating their logs, and when I shut it down all of
| that project's dependencies shut down. Pretty much the same
| flow as docker-compose.
|
| It's all self-contained so I can run it on MacOS and it'll
| behave just the same as on Linux (I don't think systemd
| does this, could be wrong), and without requiring me to
| solve the docker/podman/rancher/orbstack problem (these are
| dependencies that are hard to bundle in nix, so while
| everything else comes for free, they come at the cost of
| complicating my readme with a bunch of requests that the
| user set things up beforehand).
|
| As a bonus, since it's a single parent process, if I decide
| to invoke it through libfaketime, the time inherited by
| subprocess so it's consistently faked in the database and
| the services and in observability tools...
|
| My feeling for systemd is that it's more for system-level
| stuff and less for project-level dependencies. Like, if I
| have separate projects which need different versions of
| postgres, systemd commands aren't going to give me a
| natural way to keep track of which project's postgres I'm
| talking about. process-compose, however, will show me logs
| for the correct postgres (or whatever service) in these
| cases: ~/src/projA$ process-compose
| process logs postgres ~/src/projB$ process-compose
| process logs postgres
|
| This is especially helpful because AI agents tend to be
| scoped to working directory. So if I have one instance of
| claude code on each monitor and in each directory, which
| ever one tries to look at postgres logs will end up looking
| at the correct postgres's logs without having to even know
| that there are separate ones running.
|
| Basically, I'm alergic to configuring my system at all. All
| dependencies besides nix, my text editor, and my shell are
| project level dependencies. This makes it easy to hop
| between machines and not really care about how they're set
| up. Even on production systems, I'd rather just clone the
| repo `nix run` in that dir (it then launches process
| compose which makes everything just like it was in my dev
| environment). I am however not in charge of any production
| systems, so perhaps I'm a bit out of touch there.
| mihaelm wrote:
| Maybe if you only look at it through the lens of building an
| app/service, but containers offer so much more than that. By
| standardizing their delivery through registries and management
| through runtimes, a lot of operational headaches just go away
| when using a container orchestrator. Not to mention better
| utilization of hardware since containers are more lightweight
| than VMs.
| the__alchemist wrote:
| Hah indeed that's my perspective. I'm used to being able to
| compile program, distribute executable, "just works", across
| win, Linux, MacOs. (With appropriate compile targets set)
| Hackbraten wrote:
| > Not to mention better utilization of hardware
|
| When compared to a VM, yes. But shipping a separate userspace
| for each small app is still bloat. You can reuse software
| packages and runtime environments across apps. From an I/O,
| storage, and memory utilization point of view, it feels
| baffling to me that containers are so popular.
| esseph wrote:
| > From an I/O, storage, and memory utilization point of
| view, it feels baffling to me that containers are so
| popular.
|
| Why? It's not virtualization, it's containerization. It's
| using the host kennel.
|
| Containers are fast.
| Hackbraten wrote:
| I was referring to the userspace runtime stack, not the
| kernel. What I criticize is that multiple containers that
| share a single host usually overdo it with filesystem
| isolation. Hundreds of MBs of libraries and tools
| needlessly duplicated, even though they could just as
| well have used distro packages and deployed their apps as
| system-level packages and systemd unit files with
| `DynamicUser=`.
|
| You can hardly call this efficient hardware utilization.
| arandomhuman wrote:
| The duplication is a necessity to achieve the isolation.
| Having shared devels and hordes of unit files for a multi
| tenant system is hell - versioning issues can and will
| break this paradigm, no serious shop is doing this.
|
| For running your own machine, sure. But this would become
| non maintainable for a sufficiently multi tenant system.
| Nix is the only thing that really can begin to solve this
| outside of container orchestration.
| Gigachad wrote:
| "bloat" has always been the last resort criticism from
| someone who has nothing valid. Containers are incredibly
| light, start very rapidly, and have such low overhead in
| general that the entire industry has been using them.
|
| Docker containers also do reuse shared components, layers
| that are shared between containers are not redownloaded.
| The stuff that's unique at the bottom is basically just
| going to be the app you want to run.
| Bratmon wrote:
| I'm curious why. To me "We updated our library to change some
| things in a way that's an improvement on net but only mostly
| backwards compatible" seems like an extremely common instinct
| in software development. But in an environment where people are
| doing that all the time, the only way to reliably deploy
| software is to completely freeze all your direct and indirect
| dependencies at an exact version. And Docker is way better at
| handling that than traditional Linux package managers are.
|
| Why do you think other tools will make a comeback?
| mrbluecoat wrote:
| > Docker repurposed SLIRP, a 1990s dial-up tool originally for
| Palm Pilots, to avoid triggering corporate firewall restrictions
| by translating container network traffic through host system
| calls instead of network bridging.
|
| Genuinely fascinating and clever solution!
| redhanuman wrote:
| repurposing a Palm Pilot dial-up tool to sneak container
| traffic past enterprise firewalls is unhinged and yet it worked
| the best infrastructure hacks are never clever in the moment
| they are just desperate that the cleverness only shows up after
| someone else has to maintain it.
| Normal_gaussian wrote:
| Exactly. "so I hung the radiator out the window" vibes.
| arcanemachiner wrote:
| I am trying to decipher the meaning of your comment, to no
| avail.
| diroussel wrote:
| So you've never improvised an air conditioning system
| from a spare bilge pump, a propane tank and a cast iron
| radiator?
|
| Sir, this is a hacker news.
| avsm wrote:
| VPNKit (the SLIRP component) has been remarkably bug free
| over the years, and hasn't been much of a burden overall.
|
| There was another component that we didn't have room to cover
| in the article that has been very stable (for filesystem
| sharing between the container and the host) that has been
| endlessly criticised for being slow, but has never corrupted
| anyone's data! It's interesting that many users preferred
| potential-dataloss-but-speed using asynchronous IO, but only
| on desktop environments. I think Docker did the right thing
| by erring on the side of safety by default.
| mmh0000 wrote:
| Until recently, Podman used slirp4net[1] for its container
| networking. About two years ago, they switched over to
| Pasta[2][3] which works quite a bit differently.
|
| [1] https://github.com/rootless-containers/slirp4netns
|
| [2] https://blog.podman.io/2024/03/podman-5-0-breaking-
| changes-i...
|
| [3] https://passt.top/passt/about/#pasta-pack-a-subtle-tap-
| abstr...
| toast0 wrote:
| I don't think SLIRP was originally for palm pilots, given it
| was released two years before.
|
| SLIRP was useful when you had a dial up shell, and they
| wouldn't give you slip or ppp; or it would cost extra. SLIRP is
| just a userspace program that uses the socket apis, so as long
| as you could run your own programs and make connections to
| arbitrary destinations, you could make a dial script to connect
| your computer up like you had a real ppp account. No incomming
| connections though (afaik), so you weren't really a peer on the
| internet, a foreshadowing of ubiquitous NAT/CGNAT perhaps.
| avsm wrote:
| > I don't think SLIRP was originally for palm pilots, given
| it was released two years before.
|
| That's a mistake indeed; "popularised by" might have been
| better. Before my beloved Palmpilot arrived one Christmas, I
| was only using SLIRP to ninja in Netscape and MUD sessions
| onto a dialup connection which wasn't a very mainstream use.
| talkvoix wrote:
| A full decade since we took the 'it works on my machine' excuse
| and turned it into the industry standard architecture ('then
| we'll just ship your machine to production').
| redhanuman wrote:
| the real trick was making "ship your machine" sound like best
| practice and ten years later we r doing the same thing with ai
| "it works in my notebook" jst became "containerize the notebook
| and call it a pipeline" the abstraction always wins because
| fixing the actual problem is just too hard.
| goodpoint wrote:
| ...while completely forgetting about security
| zbentley wrote:
| > fixing the actual problem is just too hard.
|
| I think it's laziness, not difficulty. That's not meant to be
| snide or glib: I think gaining expertise in how to package
| and deploy non-containerized applications isn't difficult or
| unattainable for most engineers; rather, it's tedious and
| specialized work to gain that expertise, and Docker allowed
| much of the field to skip doing it.
|
| That's not good or bad per se, but I do think it's different
| from "pre-container deployment was _hard_ ". Pre-container
| deployment was neglected and not widely recognized as a
| specialty that needed to be cultivated, so most shops sucked
| at it. That's not the same as "hard".
| skydhash wrote:
| It's not even laziness or expertise. A lot of people are
| against learning conventions. They want their way, meaning
| what works on their computer. That's why they like the
| current scope of package managers, docker, flatpack,...
| They can do what they want in the sandbox provided however
| nonsensical and then ship the whole thing. And it will
| break if you look at it the wrong way.
| Bratmon wrote:
| I mean, walking through a door is easier than tearing down a
| wall, walking through it, and rebuilding the wall. That
| doesn't mean the latter is a good idea.
| forrestthewoods wrote:
| Linux user space is an abject disaster of a design. So so so
| bad. Docker should not need to exist. Running computer programs
| need not be so difficult.
| esafak wrote:
| Who does it right?
| whateverboat wrote:
| Windows.
| jjmarr wrote:
| Nix and Guix.
|
| Good luck convincing people to switch!
| abacate wrote:
| Trying to convince people usually makes any resistance
| worse.
|
| Using it, solving problems with it, and building a real
| community around it tend to make a much greater impact in
| the long run.
| NortySpock wrote:
| Yeah, but if the problem you are solving is rare for most
| practitioners, effectively theoretical until it actually
| happens, then people won't switch until they get bit by
| that particular problem.
| zbentley wrote:
| But they're roughly the same paradigm as docker, right?
| My understanding of the Nix approach is that it's still
| reproducing most of a user land/filesystem in a
| captive/separate/sandbox environment. Like, docker is
| using namespaces for more stuff, Nix has a heavier
| emphasis on reproducibility/determinism, but ... they're
| both still throwing in the towel on deploying directly on
| the underlying OS's userland (unless you go all the way
| to nixOS) and shipping what amounts to a filesystem in a
| box, no?
| jjmarr wrote:
| I daily drive NixOS. I don't have a global "userland".
| Packages are shipped from upstream and pull in the
| dependencies they need to function.
|
| That means unlike Gentoo, I've never dealt with a "slot
| conflict" where two packages want conflicting
| dependencies. And unlike Ubuntu, I have new versions of
| everything.
|
| Pick 2: share dependencies, be on the bleeding edge, or
| waste your time resolving conflicts.
| forrestthewoods wrote:
| Windows is an order of magnitude better in this regard.
| vanviegen wrote:
| It used to be, but only in cases where your distro
| doesn't just package whatever software you require.
| Nowadays I prefer Flatpak or AppImage over crappy custom
| Windows installers for those cases. They allow for
| sandboxing and reliable updating/deinstallation.
| skydhash wrote:
| These days, I equate anything that ships via
| docker/flatpak first as built by someone that only care
| about their own computer, especially if the project is
| opensource. As soon as a library or a tool update, they
| usually rush to add a hard condition on it for no reason
| other than to be on the "bleeding edge".
| robmusial wrote:
| And yet I'm constantly getting asked when we'll support
| Windows containers at my office.
| avsm wrote:
| We've given up on native Windows containers in OCaml
| after trying to use them for our CI builds for many
| years. See https://www.tunbury.org/2026/02/19/obuilder-
| hcs/ for our recent switch to HCS instead. Compared to
| Linux containers, they're very much a second-class
| citizen in the Microsoft worldview of Docker.
| forrestthewoods wrote:
| This is because your team doesn't know how to ship
| software without using containers.
|
| If you have adopted a bad tool then people are likely to
| want the bad tool in more places. This is the opposite of
| a virtuous cycle and is a horrible form of tech debt.
| jfjasdfuw wrote:
| Plan9 or Inferno.
| chuckadams wrote:
| It's the ultimate in static linking. Perhaps a question that
| should be asked is why that approach is so compelling?
| blackcatsec wrote:
| I question that as well, it's also why Go is extremely
| popular. Could it just be a pendulum swing back towards
| static linking?
|
| Wonder when some enterprising OSS dev will rebrand dynamic
| linking in the future...
| jfjasdfuw wrote:
| CGO_ENABLED=0 is sigma tier.
|
| I don't care about glibc or compatibility with
| /etc/nsswitch.conf.
|
| look at the hack rust does because it uses libc:
|
| > pub unsafe fn set_var<K: AsRef<OsStr>, V:
| AsRef<OsStr>>(key: K, value: V)
| jcgl wrote:
| > I don't care about glibc or compatibility with
| /etc/nsswitch.conf.
|
| So what do you do when you need to resolve system users?
| I sure hope you don't parse /etc/passwd, since plenty of
| users (me included) use other user databases (e.g. sssd
| or systemd-userdbd).
| cyberax wrote:
| Most software doesn't need to resolve users. You also can
| always shell out to `id` if you need an occasional bit of
| metadata.
| avsm wrote:
| (coauthor of the article here)
|
| Well, before Docker I used to work on Xen and that possible
| future of massive block devices assembled using Vagrant and
| Packer has thankfully been avoided...
|
| One thing that's hard to capture in the article -- but that
| permeated the early Dockercons -- is the (positive) disruption
| Docker had in how IT shops were run. Before that going to
| production was a giant effort, and 'shipping your filesystem'
| quickly was such a change in how people approached their work.
| We had so many people come up to us grateful that they could
| suddenly build services more quickly and get them into the
| hands of users without having to seek permission slips signed
| in triplicate.
|
| We're seeing the another seismic cultural shift now with coding
| agents, but I think Docker had a similar impact back then, and
| it was a really fun community spirit. Less so today with the
| giant hyperscalars all dominating, sadly, but I'll keep my fond
| memories :-)
| talkvoix wrote:
| Great point about coding agents! Back then, Docker gave us
| 'it works on my machine, let's ship the machine'. Now, AI
| agents are giving us 'I have no idea how this works, let's
| ship the prompt'. The early Docker community spirit really
| was legendary though--before every hyperscaler wrapped it in
| 7 layers of proprietary managed services. Thanks for the
| memories and the write-up!
| avsm wrote:
| Thanks for the kind words! I've been prodding
| @justincormack to resurrect the single most fun OS
| unconference I've ever attended -- New Directions in
| Operating Systems (last held back in 2014).
| https://operatingsystems.io
|
| Some of those talks strangely make more sense today (e.g.
| Rump Kernels or unikernels + coding agents seems like a
| really good combination, as the agent could search all the
| way through the kernel layers as well).
| throwawaypath wrote:
| >massive block devices assembled using Vagrant and Packer has
| thankfully been avoided...
|
| Funny comment considering lightweight/micro-VMs built with
| tools like Packer are what some in the industry are moving
| towards.
| avsm wrote:
| And those lightweight VM base images are possible because
| Docker applied a downward pressure on OS base image sizes!
| Alpine Linux doesn't get enough credit for this; in
| addition to being a great base image, it was also the first
| distro to prioritise fast and small image creation (Gentoo
| and Arch were small, but not fast to create).
| kgwgk wrote:
| Maybe in that alternative future of massive block devices
| some downward pressure on image sizes would have been
| applied just the same.
| avsm wrote:
| It's not as easy; a block device has to be bootable and
| so usually bundles a kernel (large). And because the
| filesystem inside is opaque, you can't do layering like
| Docker does easily via overlayfs and friends. libguestfs
| does a heroic job of making VM images easier to
| manipulate from code, but it's an uphill battle...
| curt15 wrote:
| >'then we'll just ship your machine production'
|
| Minus the kernel of course. What is one to do for workloads
| requiring special kernel features or modules?
| avsm wrote:
| Those are global to the machine; generally not an issue and
| seccomp rules can filter out undesirable syscalls to other
| containers. But GPU kernel/userspace driver matching has been
| a huge headache; see https://cacm.acm.org/research/a-decade-
| of-docker-containers/... in the article for how the CDI is
| (sort of) helping standardise this.
| syncsynchalt wrote:
| I see this take a lot but I'd argue what Docker did was to
| entice everyone to capture their build into a repeatable
| process (via a Dockerfile).
|
| "Ship your machine to production" isn't so bad when you have a
| ten-line script to recreate the machine at the push of a
| button.
| lioeters wrote:
| Exactly my feeling. Docker is "works on _this_ machine " with
| an executable recipe to build the machine and the
| application. Newer better solutions like OCI-compliant tools
| will gradually replace Docker, but the paradigm shift has
| provided a lot of lasting value.
| Gigachad wrote:
| Yeah docker codifies what the process to convert a base
| linux distro in to a working platform for the app actually
| is. Every company I've worked at that didn't use docker
| just has this tribal knowledge or an outdated wiki page on
| the steps you need to take to get something to work. Vs a
| dockerfile that exactly documents the process.
| Skywalker13 wrote:
| Oh, thank you... I'm not alone... I'm so tired of seeing crappy
| containers with pseudo service management handled by
| Dockerfiles, used instead of proper and serious packaging like
| that of many venerable Linux distributions.
| hwhshs wrote:
| In 2002 I used to think why cant they package a website. These
| .doc installation instructions are insane! What a waste of
| someones time.
|
| I sort of had the problem in mind. Docker is the answer. Not
| clever enough to have inventer it.
|
| If I did I would probably have invented octopus deploy as I was
| a Microsoft/.NET guy.
| INTPenis wrote:
| I thought it was 2014 when it launched? The article says the
| command line interface hasn't changed since 2013.
| avsm wrote:
| We first submitted the article to the CACM a while ago. The
| review process takes some time and "Twelve years of Docker
| containers" didn't have quite the same vibe.
| bmitch3020 wrote:
| I've seen countless attempts to replace "docker build" and
| Dockerfile. They often want to give tighter control to the build,
| sometimes tightly binding to a package manager. But the
| Dockerfile has continued because of its flexibility. Starting
| from a known filesystem/distribution, copying some files in, and
| then running arbitrary commands within that filesystem mirrored
| so nicely what operations has been doing for a long time. And as
| ugly as that flexibility is, I think it will remain the dominant
| solution for quite a while longer.
| zbentley wrote:
| > the Dockerfile has continued because of its flexibility
|
| I wish we had standardized on something other than shell
| commands, though. Puppet or terraform or something more
| declarative would have been such a better alternative to
| "everyone cargo cults 'RUN apt-get upgrade' onto the top of
| their dockerfiles".
|
| Like, the layer/stage/caching behavior is fine. I just wish the
| actual execution parts had been standardized using something at
| a higher level of abstraction than shell.
| avsm wrote:
| Docker broke out the build layer into a separate component
| called BuildKit (see HN discussion recently
| https://news.ycombinator.com/item?id=47166264).
|
| However, Dockerfiles are so popular because they run shell
| commands and permit 'socially' extending someone else shell
| commands; tacking commands onto the end of someone else's
| shell script is a natural process. /bin/sh is unreasonably
| effective at doing anything you need to a filesystem, and if
| the shell exposes a feature, it has probably been used in a
| Dockerfile somewhere.
|
| Every other solution, especially declarative ones, tend to
| come up short when _layering_ images quickly and easily.
| However, I agree they're good if you control the entire
| declarative spec.
| mihaelm wrote:
| I'd say LLB is the "standard", Dockerfile is just one of
| human-friendly frontends, but you can always make one
| yourself or use an alternative. For example, Dagger uses
| BuildKit directly for building its containers instead of
| going through a Dockerfile.
| bheadmaster wrote:
| > Puppet or terraform or something more declarative would
| have been such a better alternative
|
| Until you need to do something that isn't covered with its
| DSL, and you extend it with an external command execution
| declaration... At which point people will just write bash
| scripts anyway and use your declarative language as a
| glorified exec.
| sofixa wrote:
| If you have 90-95% of everyone's needs (installing
| packages, compiling, putting files) covered in your DSL,
| and it has strong consistency and declarativeness, it's not
| that big of a problem if you need an escape hatch from time
| to time. Terraform, Puppet, Ansible, SaltStack show this
| pretty well, and the vast majority of them that isn't bash
| scripts is better and more maintainable than their
| equivalents in pure bash would be.
| toast0 wrote:
| Oof, not terraform please. If you use foreach and friends,
| dependency calculations are broken, because dependency
| happens before dynamic rules are processed.
|
| I'd get much better results it I used something else to do
| the foreach and gave terraform only static rules.
| esseph wrote:
| The more you try and abstract from the OS, the more problems
| you're going to run into.
| zbentley wrote:
| Bash is pretty darn abstracted from the OS, though. Puppet
| vs Bash is more about abstraction relative to the _goal_.
|
| If your dockerfile says "ensure package X is installed at
| version Y" that's a lot clearer (and also more easy to make
| performant/cached and deterministic) than "apt-get update;
| apt-get install $transitive-at-specific-version; apt-get
| install $the-thing-you-need-atspecific-version". I'm not
| thrilled at how distro-locked the shell version makes you,
| and how easy it is for accidental transitive changes to
| occur too.
|
| But neither of those approaches is at a particularly low
| abstraction level relative to the OS itself; files and
| system calls are more or less hidden away in both package-
| manager-via-bash and puppet/terraform/whatever.
| harrall wrote:
| Declarative methods existed before Docker for years and they
| never caught on.
|
| They sounded nice on paper but the work they replaced was
| somehow more annoying.
|
| I moved over to Docker when it came out _because_ it used
| shell.
| mort96 wrote:
| Dockerfile has the flexibility to do what you want though,
| no? Use a base image with terraform or puppet or opentofu or
| whatever pre-installed, then your Dockerfile can just run the
| right command to apply some declarative config file from the
| build context.
|
| And if you want something weird that's not supported by your
| particular tool of choice, you have the escape hatch of
| running arbitrary commands in the Dockerfile.
|
| What more do you want?
| cpuguy83 wrote:
| Give https://github.com/project-dalec/dalec a look. It is
| more declarative. Has explicit abstractions for packages,
| caching, language level integrations, hermetic builds, source
| packages, system packages, and minimal containers.
|
| Its a Buildkit frontend, so you still use "docker build".
| miladyincontrol wrote:
| The lack of docker registry-like solutions really does seem to
| be the chokepoint for many alternatives.
|
| Personally I love using mkosi and while it has all the
| composability and deployment options I'd care for, its clear
| not everyone wants to build starting only with a blank set of
| OS templates.
| __MatrixMan__ wrote:
| There are some hurdles preventing that flow from achieving
| reproducible builds. As the bad guys get more sophisticated,
| it's going to become more and more important that one party can
| say "we trust this build hash" and a separate party to say "us
| too".
|
| That's not going to work if both parties get different hashes
| when they build the image, which won't happen as long as file
| modification timestamps (and other such hazards) are part of
| what gets hashed.
| bmitch3020 wrote:
| Recent versions of buildkit have added support for
| SOURCE_DATE_EPOC. I've been making the images reproducible
| before that with my own tooling, regctl image mod [1] to
| backdate the timestamps.
|
| It's not just the timestamps you need to worry about. Tar
| needs to be consistent with the uid vs username, gzip
| compression depends on implementations and settings, and the
| json encoding can vary by implementation.
|
| And all this assumes the commands being run are reproducible
| themselves. One issue I encountered there was how alpine
| tracks their package install state from apk, which is a tar
| file that includes timestamps. There are also timestamps in
| logs. Not to mention installing packages needs to pin those
| package versions.
|
| All of this is hard, and the Dockerfile didn't make it easy,
| but it is possible. With the right tools installed,
| reproducing my own images has a documented process [2].
|
| [1]: https://regclient.org/cli/regctl/image/mod/
|
| [2]: https://regclient.org/install/#reproducible-builds
| whateveracct wrote:
| Nix is exceptionally good at making docker containers.
| Spivak wrote:
| Yes but then you're committed to using Nix which doesn't work
| so well the moment you need some software not packaged by
| Nix.
|
| Want to throw a requirements.txt in there? No no, why would
| you even ask that? Meanwhile docker says yeah sure just run
| pip install, why should I care?
| okso wrote:
| LLMs are getting very good at packaging software using Nix.
| CuriouslyC wrote:
| This. I wouldn't have touched Nix when you needed someone
| who was really good at Nix to keep it working, but agents
| make it viable to use in a number of place.
| mort96 wrote:
| Then you're committing to maintaining a package for that
| software.
|
| Like all LLM boosters, you've ignored the fact that the
| largest time sink in many kinds of software is not
| initial development, but perpetual maintenance.
| whateveracct wrote:
| I use software from pretty much every language with Nix.
| And I package it myself too when needed. Including Python
| often :)
| nothrabannosir wrote:
| Nix doesn't make sense if all you're going to use it for is
| building Docker images. It only makes sense if you're all
| in in the first place. Then Docker images are free.
| gnull wrote:
| Packaging for nix is exceptionally easy once you learn it.
| And once something is packaged, it's solved for all, it's
| not going to randomly break.
|
| If you care about getting it to work with minimal effort
| right now more thar about it being sustainable later, then
| sure.
| mikepurvis wrote:
| Especially if you use nix2container to take control over the
| layer construction and caching.
| stabbles wrote:
| Does Nix do one layer per dependency? Does it run into >=128
| layers issues?
|
| In Spack [1] we do one layer per package; it's appealing, but
| I never checked if besides the layer limit it's actually bad
| for performance when doing filesystem operations.
|
| [1] https://spack.readthedocs.io/en/latest/containers.html
| phplovesong wrote:
| You can pretty much replace "docker build" with "go build".
|
| But as long as people want to use scripting languages (like
| php, python etc) i guess docker is the neccessary evil.
| speedgoose wrote:
| It doesn't sound like Golang is going to dominate and replace
| everything else, so Docker is there to stay.
| osigurdson wrote:
| In some situations, yes, others no. For instance if you want
| to control memory or cpu using a container makes sense
| (unless you want to use cgroups directly). Also if running
| Kubernetes a container is needed.
| matrss wrote:
| You have to differentiate container images, and "runtime"
| containers. You can have the former without the latter, and
| vice versa. They are entirely orthogonal things.
|
| E.g. systemd exposes a lot of resource control as well as
| sandboxing options, to the point that I would argue that
| systemd services can be very similar to "traditional"
| runtime containers, without any image involved.
| aobdev wrote:
| Wasn't this the same argument for .jar files?
| garganzol wrote:
| Go is just one language, while Dockerfile gives you access to
| the whole universe with myriads of tools and options from
| early 1970s and up to the future. I don't know how you can
| compare or even "replace" Docker with Go; they belong to
| different categories.
| yunwal wrote:
| > You can pretty much replace "docker build" with "go build".
|
| Interesting. How does go build my python app?
| well_ackshually wrote:
| >You can pretty much replace "docker build" with "go build".
|
| I'll tell that to my CI runner, how easy is it for Go to
| download the Android SDK and to run Gradle? Can I also `go
| sonarqube` and `go run-my-pullrequest-verifications` ? Or are
| you also going to tell me that I can replace that with a
| shitty set of github actions ?
|
| I'll also tell Microsoft they should update the C# definition
| to mark it down as a scripting language. And to actually give
| up on the whole language, why would they do anything when
| they could tell every developer to write if err != nil
| instead
|
| Just because you have an extremely narrow view of the field
| doesn't mean it's the only thing that matters.
| kccqzy wrote:
| > But the Dockerfile has continued because of its flexibility.
|
| The flip side is that the world still hasn't settle on a
| language-neutral build tool that works for all languages.
| Therefore we resort to running arbitrary commands to invoke
| language-specific package managers. In an alternate timeline
| where everyone uses Nix or Bazel or some such, docker build
| would be laughed out of the window.
| brightball wrote:
| Reminds me of the "Electric cars in reverse" video where the
| guy envisions a world where all vehicles are electric and
| tries to make the argument for gas engines.
| anal_reactor wrote:
| Link?
| fittom wrote:
| try searching for 'Rory Sutherland: What If Petrol Cars
| Were Invented In 2025'
| muvlon wrote:
| As a Nix evangelist, I have to say: Nix is really not capable
| of replacing languag-specific package managers.
|
| > running arbitrary commands to invoke language-specific
| package managers.
|
| This is exactly what we do in Nix. You see this everywhere in
| nixpkgs.
|
| What sets apart Nix from docker is not that it works well at
| a finer granularity, i.e. source-file-level, but that it has
| real hermeticity and thus reliable caching. That is, we also
| run arbitrary commands, but they don't get to talk to the
| internet and thus don't get to e.g. `apt update`.
|
| In a Dockerfile, you can `apt update` all you want, and this
| makes the build layer cache a very leaky abstraction. This is
| merely an annoyance when working on an individual container
| build but would be a complete dealbreaker at linux-distro-
| scale, which is what Nix operates at.
| avsm wrote:
| An extremely random fact I noticed when writing the companion
| article [1] to this (an OCaml experience report):
| "Docker, Guix and NixOS (stable) all had their first releases
| during 2013, making that a bumper year for packaging
| aficionados."
|
| Now we get coding agent updates every week, but has there been a
| similar year since 2013 where multiple great projects all came
| out at the same time?
|
| [1]: https://anil.recoil.org/papers/2025-docker-icfp.pdf
| esseph wrote:
| TBH I feel as if only docker belongs in that list. Guix and nix
| have users, sure, but not remotely like docker.
| NewJazz wrote:
| Yeah they are way better than docker for packaging
| brcmthrowaway wrote:
| I dont use Dockerfile. Am i slumming it?
| vvpan wrote:
| Probably? How do you deploy?
| rglover wrote:
| Just pull a tarball from a signed URL, install deps, and run
| from systemd. Rolls out in 30 seconds, remarkably stable.
| Initial bootstrap of deps/paths is maybe 5 minutes.
| user3939382 wrote:
| It solves a practical problem that's obvious. And on one hand the
| practical where-were-at-now is all that matters, that's a
| legitimate perspective.
|
| There's another one, at least IMHO, that this entire stack from
| the bottom up is designed wrong and every day we as a society
| continue marching down this path we're just accumulating more
| technical debt. Pretty much every time you find the solution to
| be, "ok so we'll wrap the whole thing and then..." something is
| deeply wrong and you're borrowing from the future a debt that
| must come due. Energy is not free. We tend to treat compute like
| it is.
|
| Maybe I'm in a big club but I have a vision for a radically
| different architecture that fixes all of this and I wish that got
| 1/2 the attention these bandaids did. Plan 9 is an example of the
| theme if not the particular set of solutions I'm referring to.
| arikrahman wrote:
| I'm hoping the next decade introduces more declarative workflows
| with Nix and work with docker to that end.
| politelemon wrote:
| Somewhere along the line they started prioritising docker desktop
| over docker. It's a bit jarring to see new features coming to
| desktop before it comes to Linux, such as the new sandbox
| features.
|
| Is there any insight into this, I would have thought the opposite
| where developers on the platform that made docker succeed are
| given first preview of features.
| krapht wrote:
| Paying customers use docker desktop.
| brtkwr wrote:
| I realise apple containers haven't quite taken off yet as
| expected but omission from the article stands out. Nice that it
| mentions alternative approaches like podman and kata though.
| avsm wrote:
| > but omission from the article stands out.
|
| (article author here)
|
| Apple containers are basically the same as how Docker for Mac
| works; I wrote about it here:
| https://anil.recoil.org/notes/apple-containerisation
|
| Unfortunately Apple managed to omit the feature we all want
| that only they can implement: namespaces for native macOS!
|
| Instead we got yet another embedded-Linux-VM which (imo) didn't
| really add much to the container ecosystem except a bunch of
| nice Swift libraries (such as the ext2 parsing library, which
| is very handy).
| phplovesong wrote:
| We have shipped unikernels for the last decade. Zero sec issues
| so far. I highly recommend looking into the unikernel space for a
| docker alternative. MirageOS being a good start.
| avsm wrote:
| cool! What services have you shipped as unikernels? Docker
| doesn't have to be an alternative; it can help with the
| build/run pipeline for them too:
| https://www.youtube.com/watch?v=CkfXHBb-M4A (Dockercon 2015!)
| heraldgeezer wrote:
| I still havent learned it being in IT its so embarassing. Yes I
| know about the 2-3h Youtube tutorials but just...
| forrestthewoods wrote:
| I am so thoroughly convinced that Docker is a hacky-but-
| functional solution to an utterly failed userspace design.
|
| Linux user space decided to try and share dependencies. Docker
| obliterates this design goal by shipping dependencies, but
| stuffing them into the filesystem as-if they were shared.
|
| If you're going to do this then a far far far simpler solution is
| to just link statically or ship dependencies adjacent to the
| binary. (Aka what windows does). Replicating a faux "shared"
| filesystem is a gross hack.
|
| This is a distinctly Linux problem. Windows software doesn't
| typically have this issue. Because programs ship their
| dependencies and then work.
|
| Docker is one way to ship dependencies. So it's not the worst
| solution in the world. But I swear it's a bad solution. My blood
| boils with righteous fury anytime anyone on my team mentions they
| have a 15 minute docker build step. And don't you damn dare say
| the fix to Docker being slow is to add more layers of complexity
| with hierarchical Docker images ohmygodiswear. Running a computer
| program does not have to be hard I promise!!
| ahnick wrote:
| Okay, so what's the best solution? What's even just a better
| solution than Docker? I mean really truly lay out all the
| details here or link to a blog post that describes in
| excruciating detail how they shipped a web application and
| maintained it for years and was less work than Docker
| containers. Just saying "a far far simpler solution is to just
| link statically or ship dependencies adjacent to the binary" is
| ignoring huge swaths of the SDLC. Anyone can cast stones, very
| few can actually implement a better solution. Bring the
| receipts.
| forrestthewoods wrote:
| The first half of my career was spent shipping video games.
| There is no such thing as shipping a game in Docker. Not even
| on Linux. You depend on minimum version of glibc and then
| ship your damn dependencies.
|
| The more recent half of my career has been more focused on ML
| and now robotics. Python ML is absolute clusterfuck. It is
| close to getting resolved with UV and Pixi. The trick there
| is to include your damn dependencies... via symlink to a
| shared cache.
|
| Any program or pipeline that relies on whatever arbitrary ass
| version of Python is installed on the system can die in a
| fire.
|
| That's mostly about deploying. We can also talk about build
| systems.
|
| The one true build system path is a monorepo that contains
| your damn dependencies. Anything else is wrong and evil.
|
| I'm also spicy and think that if your build system can't
| crosscompile then it sucks. It's trivial to crosscompile for
| Windows from Linux because Windows doesn't suck (in this
| regard). It _almost_ impossible to crosscompile to Linux from
| Windows because Linux userspace is a bad, broken, failed
| design. However Andrew Kelley is a patron saint and Zig makes
| it feasible.
|
| Use a monorepo, pretend the system environment doesn't exist,
| link statically/ship adjacent so/dll.
|
| Docker clearly addresses a real problem (that Linux userspace
| has failed). But Docker is a bad hack. The concept of trying
| to share libraries at the system level has objectively
| failed. The correct thing to do is to not do that, and don't
| fake a system to do it.
|
| Windows may suck for a lot of reasons. But boy howdy is it a
| whole lot more reliable than Linux at running computer
| programs.
| 1970-01-01 wrote:
| I now wonder if we'll end up switching it all back to VMs so the
| LLMs have enough room to grow and adapt.
| skybrian wrote:
| Maybe, but the install will often be done using a Docker file.
| tzs wrote:
| I've not done serious networking stuff for over two decades, and
| never in as complex an environment as that in the article, so the
| networking part of the article went pretty much over my head.
|
| What I want to do when running a Docker container on Mac is to be
| able to have the container have an IP address separate from the
| Mac's IP address that applications on the Mac see. No port
| mapping: if the container has a web server on port 80 I want to
| access it at container_ip:80, not 127.0.0.1:2000 or something
| that gets mapped to container port 80.
|
| On Linux I'd just used Docker bridged networking and I believe
| that would work, but on Mac that just bridges to the Linux VM
| running under the hypervisor rather than to the Mac.
|
| Is there some officially recommended and supported way to do
| this?
|
| For a while I did it by running WireGuard on the Linux VM to
| tunnel between that and the Mac, with forwarding enabled on the
| Linux VM [1]. That worked great for quite a while, but then
| stopped and I could not figure out why. Then it worked again.
| Then it stopped.
|
| I then switched to this [2] which also uses WireGuard but in a
| much more automated fashion. It worked for quite a while, but
| also then had some problems with Docker updates sometimes
| breaking it.
|
| It would be great if Docker on Mac came with something like this
| built in.
|
| [1] https://news.ycombinator.com/item?id=33665178
|
| [2] https://github.com/chipmk/docker-mac-net-connect
| djs55 wrote:
| (co-author of the article and Docker engineer here) I think
| WireGuard is a good foundation to build this kind of feature.
| Perhaps try the Tailscale extension for Docker Desktop which
| should take care of all the setup for you, see
| https://hub.docker.com/extensions/tailscale/docker-extension
|
| BTW are you trying to avoid port mapping because ports are
| dynamic and not known in advance? If so you could try running
| the container with --net=host and in Docker Desktop Settings
| navigate to Resources / Network and Enable Host Networking.
| This will automatically set up tunnels when applications listen
| on a port in the container.
|
| Thanks for the links, I'll dig into those!
| johanbcn wrote:
| I don't have a Mac environment, but I have researched a bit for
| devex purposes, and I would go with the Colima project as a
| open source solution for containers on mac. Have you tried it?
| callamdelaney wrote:
| The fact that docker still, in 2026, will completely overwrite
| iptables rules silently to expose containers to external requests
| is, frankly, fucking stupid.
| netrem wrote:
| Indeed. I've had even experienced sysadmins be surprised that
| their ufw setup will be ignored.
| pixelmonkey wrote:
| The math of "a decade" seemed wrong to me, since I remembered
| Docker debuting in 2013 at PyCon US Santa Clara.
|
| Then I found an HN comment I wrote a few years ago that confirmed
| this:
|
| "[...] I remember that day pretty clearly because in the same
| lightning talk session, Solomon Hykes introduced the Python
| community to docker, while still working on dotCloud. This is
| what I think might have been the earliest public and recorded
| tech talk on the subject:"
|
| YouTube link: https://youtu.be/1vui-LupKJI?t=1579
|
| Note: starts at t=1579, which is 26:19.
|
| Just being pedantic though. That's about 13 years ago. The
| lightning talk is fun as a bit of computing history.
|
| (Edit: as I was digging through the paper, they do cite this
| YouTube presentation, or a copy of it anyway, in the footnotes.
| And they refer to a 2013 release. Perhaps there was a multi-year
| delay between the paper being submitted to ACM with this title
| and it being published. Again, just being pedantic!)
| FlyingSnake wrote:
| You're right, it was 2014. I was there on HN when docker was
| announced by shykes. It was a godsend because I was getting
| bummed by the alternatives like LXC, juju charms or vagrant.
|
| Here's the announcement from 2013:
|
| https://news.ycombinator.com/item?id=5408002
| avsm wrote:
| From another comment below, it's just a nice short title to
| convey that we're going back in time and not one to set your
| watch by. We first submitted the article to
| the CACM a while ago. The review process takes some
| time and "Twelve years of Docker containers" didn't
| have quite the same vibe.
|
| (The CACM reviewers helped improve our article quite a bit. The
| time spent there was worth it!)
| rando1234 wrote:
| Didn't Vagrant/Vagrantfiles precede Docker? Unclear why that
| would be the key to its success if so.
| netrem wrote:
| With ML and AI now being pushed into everything, images have
| ballooned in size. Just having torch as a dependency is some
| multiple gigabytes. I miss the times of aiming for 30MB images.
|
| Have others found this to be the case? Perhaps we're doing
| something wrong.
| Joe_Cool wrote:
| I have an immutable Alpine Linux running from an ISO that
| includes a few docker containers (mostly ruby and php). All in
| about 750MB.
| tsoukiory wrote:
| I dont no spek anglais
| mberning wrote:
| I remember being pretty skeptical of "dockerizing" applications
| when it first becamee popular. But I've come around to it, if for
| no other reason than it provided an easily understandable concept
| which anyone could understand and more importantly use. The
| onramp to using docker is very gentle.
| benatkin wrote:
| > If you are a developer, our goal is to make Docker an invisible
| companion
|
| I want it not to just be invisible but to be missing. If you have
| kubernetes, including locally with k3s or similar, it won't be
| used to run containers anyway. However it still often is used to
| build OCI images. Podman can fill that gap. It has a
| Containerfile format that is the same syntax but simpler than the
| Docker builds.
___________________________________________________________________
(page generated 2026-03-07 23:00 UTC)