Should we be exorcizing Daemons, or perhaps love them?

Konstantin Gredeskoul
3 min readJan 24, 2021

I am, of course, talking about Ruby Daemons, particularly Puma Web Server’s former daemonization feature…

You may or may not know this, but In version 5.0 of the popular Ruby HTTP server Puma, the developers chose to drop the daemonization support from Puma. They did that because the code wasn’t actively maintained. Other options now exist (such as systemd), not to mention that many people have switched to Kubernetes and Docker, where you generally want to start all of your web servers in the foreground.

And yet, on occasion, it was rather useful and straightforward to use the built-in daemonization feature that was cross-platform and is now gone. Some folks are still using this feature and are therefore stuck with Puma version 4, or must wrap Puma either in the systemd manifest or launchctl plist on Mac OS-X, or a Docker container. Well, not anymore!

I was a bit nostalgic for it, so I wrote a supplemental gem called puma-daemon that brings this feature back!

How to Use

Just type,

gem install puma-daemon -N

Or, add this gem to your Gemfile dependencies, and make a one-line change either in your config/puma.rb file, or use pumad binary to start Puma as per usual, and you can even leave -d flags there (they are ignored when started via pumad, and Puma always goes to the background when started that way).

Here, we show both the puma config file and the daemonization in action.

Note how we switch back to the original puma executable in the second screenshot and set the NO_DAEMON variable to disable daemonization configured in the Puma’s config file.

And we are running in the foreground! So even with puma-daemon gem included, you can still run things in the foreground if you so desire.

Design Decisions

This gem’s original goal was to surgically augment Puma’s source code to restore daemonization by merely requiring puma/daemon.

While this was an admirable goal, it has not been accomplished in the current version. The internals of Puma isn’t very easy to monkey-patch or augment. For example, we couldn’t think of a way to add back the -d flags to the Option Parsing method without having to override the entire method: — which is not a good solution, because — what if Puma developers add a new flag in the future? We would have to keep this overridden method frequently updated and potentially choose a different version depending on what version of Puma you are using. That sounds like a nightmare.

It is why instead, we took an approach that requires you — the user — to make a couple of small changes in your Puma configuration to bring daemonization back, or in your scripts, change puma to pumad, and everything should work. If you run into problems, please submit an issue.

Thanks for reading, and please leave your comments here. If you end up using puma-daemon please give it a ⭐️ :)

Thanks much!

--

--

Konstantin Gredeskoul

Konstantin is an avid ruby expert, and a 4x-CTO. He authored over forty Ruby Gems (18M downloads), speaks at conferences (250K slideshare views). C++/Ruby/BASH.