Security issue: node is run as root
mtparet opened this issue · 19 comments
In case of security flaw in the application run and in docker.
cf:
http://blog.zeltser.com/post/104976675349/security-risks-and-benefits-of-docker-application
http://thenewstack.io/docker-addresses-more-security-issues-and-outlines-plugin-approach/
http://www.slideshare.net/jpetazzo/docker-linux-containers-lxc-and-security
https://blog.xenproject.org/2014/06/23/the-docker-exploit-and-the-security-of-containers/
Thanks, we'll look at ways to address this in a future release.
If you come up with a good way to actually solve this nicely at the language stack level, please share so we can make sure all the stacks get updated. We've been trying to think through this problem for a while, and there's not really an easy "works for everyone" way to do this without knowing the specifics of the application being Dockerized (in our experience).
TL;DR this might be more of a docs problem (ie, update the documentation to show best practices for running your application as non-root)
Sure :)
For now though, you are right, it really is a docs problem
Thanks for answers.
Closing this out, since it's more of a Docs/best practice issue at this point.
since it's more of a Docs/best practice
I disagree it should be a default behavior.
It's a bad practice of running software as root although they do not need root rights.
What about needing to bind to port 80 or other similar scenarios?
As Docker can handle binding container port to host port, it should not be an issue ? (We should be able to bind the 8080 port on the container to the 80 port on the host)
True, but I guess that means possibly breaking things for anyone using the current image, right?
Yes this will be a breaking change...
"Isn't the port to bind on specified in the application itself?"
What do you mean ?
Yes the application itself inside the container will specified its port but we should be able to bind it to any port on the host when running the container (with the option -p
), no ?
Yes of course. It's fine to let the application binding the port it wants to.
But this does not imply giving root right to this one by default as it should not be needed for a web server. (If they need to bind the port 80, they should change this or if not possible use possible workaground http://stackoverflow.com/questions/413807/is-there-a-way-for-non-root-processes-to-bind-to-privileged-ports-1024-on-l#414258)
Docker's official stance on this seems clear to me:
If a service can run without privileges, use USER to change to a non-root user.
We're not in compliance. If someone wants to run the Node process as root (e.g., to bind to port 80), then the burden should be on them to write a custom Dockerfile.
This isn't the Dockerfile for a "service", but a base Dockerfile for services, some of which may be able to run as root and some of which won't.
I personally the consider the part after what @NodeGuy quoted just as important in determining whether a Docker image should use USER
:
Note: Users and groups in an image get a non-deterministic UID/GID in that the “next” UID/GID gets assigned regardless of image rebuilds. So, if it’s critical, you should assign an explicit UID/GID.
For a base image like node
where you have no idea what people will or will not want to mount into their container as volumes, you're going to frequently run into user support issues where your "node" user (or whatever the in-container user would be called) either doesn't have access to files that someone has bind-mounted into the container at all or doesn't have the appropriate UID for being able to write files to the mount. Debugging this in the presence of things like boot2docker mounts using VirtualBox shared folders gets even harder to explain.
Just my two cents on why changing to USER node
isn't necessarily cut and dry.
I agree with your point @md5 but currently most of the application using the base image as run as root although there are no need. https://github.com/search?utf8=%E2%9C%93&q=FROM+node%3A0.10-onbuild&type=Code&ref=searchresults
So if we can't make it a default it should be very clear in the documentation...
Agree that doing the right thing by default would be really nice.
Documentation landed in #122