Hacker News new | ask | show | jobs
by lacampbell 3432 days ago
I'm just a guy that wants to deploy web apps. Is docker overkill for me? Basically, I want to be able to test something on my local machine under the same conditions it will be running on my server. Containerisation seems like the only way to do this that doesn't involve keeping packages and system configurations in sync in two or more systems.
11 comments

Docker may be overkill to start but it's relatively low cost to implement and it will definitely pay dividends over time:

    * You can be sure that what you're running locally 
      is exactly what you'll be running on the server
    * Your deployment experience will be the same 
      regardless of which tech stack you're using for the 
      web application
    * There are many places you can deploy docker 
      containers (Google GCE, Amazon ECS, Amazon EB, etc.)
    * A web application is often composed of several 
      services (e.g. the web app, a database, redis etc.) 
      and docker compose makes it easy to fire all of 
      those up in development e.g. if a new 
      developer joins, they only need to install 
      docker rather than web app framework + 
      database + redis
    * Docker sets you up quite well to grow into a 
      more complex deployment (e.g. using Kubernetes)
> it's relatively low cost to implement

Running Docker in production takes a huge amount of effort to get right and is not easily done.

I dont believe that's an accurate assessment. If the grandparent wants to run a one off container with reproducible results, something like docker-compose is perfect. If he wants to run a multi-node microservices architecture then the story gets more complicated.
i run a lot of small projects with docker-compose on a single host and it makes deploying my changes very easy. Maybe there is a low cost setting it up, but i think eve with a small project it pays it divides pretty fast.
I could have been clearer. I meant that setting up docker for his use case i.e. a single 'standard' web application, is relatively easy. Especially if you're using something like Amazon Elastic Beanstalk. At least, that's been my experience.

You're right that docker can become very complex e.g. dockerizing and orchestrating mariadb with galera for high availability was not pleasant.

I agree that its actually ok for that use case. But then you don't have a big initial pain to solve, anyway - people using Docker in production usually have few other choices due to the scale they are operating at, and Nomad+Ansible doesn't cut it because there are complex dependencies.
Docker is very well suited for local development and testing, particularly since the launch of Docker for Mac and Windows. It makes utilities like MAMP less necessary.

But apart from local development, I'd say that depends on your needs. If you want more ease-of-use, and you run a single-server hosting environment with multiple projects, it may be easier to keep doing that without adding Docker. But if you want increased security and better isolation between your projects, Docker is likely a better solution.

In any case, I would strongly recommend that you familiarize yourself with Docker, at least locally. After a while, you can decide if you want to take the leap and use it on your server as well.

Docker for local development for us been a pain in the butt. - We've hit performance problems with the filesystem, - Problem with caching things like yarn and npm install - The need to constantly rebuild the images for changes to be picked up. - Dificulty dealing with single docker file for prod and testing, making us want to montain 2 docker files.

Probably some bad setup of our part, but we've been using on production with kubernetes and none of those problems.

We're still using the compose to bootstrap database, caching, etc.

I don't understand how kubernetes solved your base image issue. That's a clustering system, so by default it can't help.

It sounds as though your setup doesn't work with the immutable filesystems introduced by docker. That's not an issue with docker at all - just something to learn.

I can't imagine dev or deployment without docker any more - all of my tests, yarn installs, dev workflow and prod runs through it.

My experience has been that it's great for local develoment, if your app is reasonably complex (ie Docker doesn't make sense if you only have an app worker and SQLite database), but I don't love it for production. In order for Docker to work well on production, you need something like Kubernetes, and that's a huge hassle for a small app.
I don't think that Kubernetes is the most important thing on prod. Some colleagues from another team at $WORK use plain Docker and "orchestrate" their containers with simple systemd units that run `docker stop|start`. If the app is only a single container, that should do it. (Actually, in that case, I think that `rkt run` would be better since the process runs below the same cgroup, and systemd can detect crashes and restart the container.)

Anyway, Kubernetes is not so important for small deployments, but what I've found really helpful is CoreOS: an auto-updating base OS that gets out of the way and (more importantly) ships a combination of Linux kernel + Docker that usually works really well.

Recent versions of systemd-nspawn can directly download a docker image and run it in a service unit.
What about docker-compose? We've recently started using it, and we don't see any problems; did your colleagues evaluate it?
docker-compose is really straightforward to get running, even moreso with docker-machine, and it gives you dev/prod parity, but the downside is that there's not a built in way to do zero downtime deploys.
Actually with the new docker-compose version 3 you can do rolling updates[1]. 1. https://docs.docker.com/compose/compose-file/#/deploy
That doesn't suggest zero downtime though, no? Still needs an LB to know to stop routing to that host for a moment.
That's how I do deployments, but they take a while to start/stop. Whereas, with uwsgi, for example, deployments are zero-downtime, since uwsgi loads a new interpreter and uses that for new connections from that point on, without interrupting any old connections.
For your use case, containers aren't overkill, but a full orchestration system probably is. Just letting some simple outside process just handle starting them up is fine, and Swarm seems to have improved enough that you can use that for single computer "keep my app running with x instances" stuff with no overhead.
I'll go against the grain here, and say that Vagrant + Ansible (or your favorite config management tool) will be easier to handle. It's well understood, simple, and you can try out any config changes in your local Vagrant environment before running the same changes on production.

At least in my mind, it's much more simple to say "OK, I installed these packages, let me add that to Ansible" than it is to get a production-ready Docker setup going.

You can try rkt[1] instead. Its from a container framework from coreos which makes a lot of things easier than docker.

Running it in a simple production setup is simply writing a systemd/initd job which starts the container. No container management daemon or orchestration framework involved.

[1] https://github.com/coreos/rkt

>Containerisation seems like the only way to do this that doesn't involve keeping packages and system configurations in sync in two or more systems.

In a nutshell, this is why I'm now hooked on docker. I can reproducibly build things on my macbook without tearing up the system packages, and I can deploy them to my small datacenter without thinking twice.

I'd suggest you at least try it out.

For single-node applications, I develop on a LXC setup with a base template of the distribution that will run a production VM. This combination provides maximum dev/prod parity, the benefits of lightweight virtualization for development, and a boring, battle-tested production environment. The setup and deployment is written once for the choice distribution.
> Containerisation seems like the only way to do this that doesn't involve keeping packages and system configurations in sync in two or more systems.

Virtual machines will also work.

Docker serves as a lightweight virtualization that will provide the same experience, assuming you are willing to keep to the kernel and Docker version "in sync" between prod and local.

Lately I've been sending a bunch of patches upstream to the runv project (https://github.com/hyperhq/runv). Turns out that wrapping the docker interface with full VM isolation is a model I very much like.
If you only care about controlling the software configuration and versions, nix (nixos.org/nix/) will do this far more elegantly than docker.
Does your web app have a database?