Some say docker is the new "curl|bash" ;)
If you manage to tell me what's in /etc/os-release on the machine (not inside the container), I'll eat my lunch.
It's also the fact that it generally doesn't do anything to integrate well with your system, and just pull all its dependencies in a folder and never update it afterward.
The other solution is to implement a totally different mechanism ( ACL + some other thing, Capabilities ) but then you lose retrocompatibility.
A process has supplemental group membership. If you were only limited to the above, then, yes, you would need to share resources through world or utilize a special broker if you wanted multiple privilege domains for a service.
But with supplemental groups you can be as fine-grained as you want. Just create a group for each domain with a unique membership set and make that a supplemental group for each user with access to that domain. When you want to share a file, just chown and chmod appropriately.
To see how this works in practice, look at BSDAuth (OpenBSD's alternative to PAM). Rather than using dynamically loadable modules for authentication methods--which effectively means that any program that wants to use authentication services needs root permissions--BSDAuth uses setuid and setgid helpers in /usr/libexec/auth.
$ ls -lhd /usr/libexec/auth/
drwxr-x--- 2 root auth 512B Mar 24 13:23 /usr/libexec/auth/
$ doas ls -lh /usr/libexec/auth/
total 372
-r-xr-sr-x 4 root _token 21.3K Mar 24 13:23 login_activ
-r-sr-xr-x 1 root auth 9.0K Mar 24 13:23 login_chpass
-r-xr-sr-x 4 root _token 21.3K Mar 24 13:23 login_crypto
-r-sr-xr-x 1 root auth 17.2K Mar 24 13:23 login_lchpass
-r-sr-xr-x 1 root auth 9.0K Mar 24 13:23 login_passwd
-r-xr-sr-x 1 root _radius 17.1K Mar 24 13:23 login_radius
-r-xr-xr-x 1 root auth 9.0K Mar 24 13:23 login_reject
-r-xr-sr-x 1 root auth 9.0K Mar 24 13:23 login_skey
-r-xr-sr-x 4 root _token 21.3K Mar 24 13:23 login_snk
-r-xr-sr-x 4 root _token 21.3K Mar 24 13:23 login_token
-r-xr-sr-x 1 root auth 21.0K Mar 24 13:23 login_yubikey
In this scheme, for any user who you want to grant permission to test basic system authentication you add the auth group to their supplemental group. Et voila, they can now use the framework, but without root permissions. For mechanisms that you may want to grant separately you use a separate group (e.g. _radius).Like many bad ideas, Docker basically won because you can use it to isolate and package pre-existing, broken software. And because it's easier to find examples of how to [abuse] Docker for sharing files across security domains than on how to use supplemental groups to do this.
On BSD when you create a file the group owner is set to the group owner of the directory. From the BSD open(2) manual page:
When a new file is created it is given the group of the
directory which contains it.
But on Linux the [default] behavior is to set the group owner to the creating process' effective group. From the Linux open(2) man page: The group ownership (group ID) is set either to the
effective group ID of the process or to the group ID of the
parent directory (depending on file system type and
mount options, and the mode of the parent directory, see
the mount options bsdgroups and sysvgroups described in
mount(8)).
The BSD behavior is more convenient when it comes to using shared supplemental groups because you can often invoke existing programs with a umask of 0002 or 0007 and files they create (without subsequently modifying permissions) will usually have the desirable permissions--specifically, writable by any process which has a supplemental group of the directory they're located in. For example, with BSD semantics Git technically wouldn't have needed a special core.sharedRepository setting. But because of SysV semantics on Linux Git had to be modified to explicitly read the group of the parent directory and explicitly change the group owner of newly created files.To me that's what other technologies like rkt seem to miss or at least choose not to focus on.
They're not much different from nix expressions, or brew formulas or such.
Unlike nix expressions (or rpm specfiles or various other technologies), the dockerfile format never concerned itself with clearly defining the hashes of inputs and dependencies, reproducibility, working without network access on build farms, etc etc,
Sure, it ended up being popular and usable, but at the cost of taking the art of describing how software is installed back in time.
Could it be that these things are mutually exclusive?
Anecdotally, I've tried to learn Nix for several years. I learned to write Dockerfiles in hours.
Don't confuse expedience with usability.
Out of interest, what did you find difficult? I ask because I spent last weekend setting up NixOS, and the only things I found difficult were discoverability and documentation (I spent a lot of time just reading through the source code).
Edit: Thinking about it it's very possible that this is just a case of me not knowing what I don't know, since I'm not currently trying to do anything particularly complex.
The language is not too bad, but how it should be used is the missing part. Like a cookbook or a properly populated Stack Overflow site.
When I was on Linux, I liked to distro hop few times a year. Whenever I got back to NixOS, I felt that I had to relearn everything, and that there was nothing to grasp on to. I always take that as a bad smell.