Packaging Caddy

So, I’ve mentioned this a few times in a few places, but we have a forum now! \o/

I’ve introduced a fair few people to Caddy, and some of them were disappointed that there wasn’t a package for Caddy in their OS’s package manager, so… Let’s rectify that!

I suggest we target Debian first, because Debian is the server OS of choice (imo).


My issue with this is that plugins make it suck. You either package with no plugins and a lot of stuff won’t be available, or you package with all and have a larger package to push and update.

Caddy comes packaged. Why do we need distro-specific packages?


Less friction for some users. Automatically configuring Caddy as a systemd service for those users who otherwise wouldn’t know where to start.

If Caddy’s goal is to be a very easy to use webserver, I can’t think of an easier way to get up and running than sudo apt-get install caddy and then writing a quick caddyfile.

The reason I’m invested in the idea: it’d also make automatically updating Caddy easier, because it’d be no different to the automatic updates anywhere else on my servers.


Because we haven’t yet decided on one universal package manager :wink:


What about curl | bash? And you can choose precisely which plugins you want with the -s flag. Seems as easy to me, with total flexibility. Works for all platforms too. And for upgrading.

1 Like

That works (it’s how I installed Caddy!), minus stuff that is distro-specific(-ish) like daemonising Caddy, etc.

I’ve got some free time Monday afternoon, I’ll throw together a (very sketchy, but proof of concept nonetheless) Debian package then.

Not really. We have automated patching infrastructure built around yum updates. If something doesn’t publish a yum repo, we have to build our own and push it to our internal repo. Much more convenient if it is done upstream.


Hmm, but then you can’t choose your plugins. Is that really convenient?

No, which again is why I’m hesitant to call them “plugins” and more “build-time addons”, but that’s an issue of semantics more than anything.

I guess I’m proposing two things:

  1. Package Caddy for the major server distros
  2. Possibly figure out some way of making plugins run-time pluggable, instead of build-time, but I’m not familiar enough with the codebase to figure out of this is feasible or a good idea.

Go is currently really bad at “runtime” plugins. There are only three strategies I know of that may work:

  1. Launch separate processes for each plugin and use ipc to communicate. Potentially slow, and a lot could go wrong.
  2. Some kind of cgo based plugin system that runs dynamicly linked go libs and uses a cgo shim on both sides for compatibility. Introduces build complexity and makes cross-compiling harder.
  3. Some kind of dynamic language interpreter: there are native go javascript and lua interpreters, but using those for plugins seems pretty crazy,

Until the go authors implement better support for runtime plugins, I think we are stuck with built-time.

Ew, right. I wasn’t aware.

… Let’s wait till then!

I’m not sure there’s going to be a “then”

1 Like

The Caddy philosophy is don’t build your production tools in production. (Ironically, that’s what the build server does, sitting behind the download page. But it does it for you before you use it.) Build/compile/whatever then ship static resources to your server. Works great, you don’t encounter any dynamic linking issues where it really hurts if you do.

What this means for distro packages is that you probably just want to pick your plugins, compile that into a “package” (a single binary), then use that with yum.


Plugins are also the bottleneck for official docker image. We were advised to include them in the default image but we prefer not to.

Apart from size (which is minor in my view), plugins are contributed and maintained by third parties. I don’t think it would be ideal to default to including them all.

1 Like

Perhaps we should be more proactive at including plugins in the core after they reach certain criteria or something though.


Makes perfect sense. In that case, I suggest we (okay, I) write up some guides for setting up “production-ready” Caddy on various Linux distributions, to give a jumping-off point for the more skittish users out there.

when caddy would become more modular we could manage it like:

  • caddy → Installs caddy server without any plugins
  • caddy-plugin-hugo → adds Hugo Plugin to caddy and restarts caddy after successful install
  • caddy-plugin-git → adds Git Plugin to caddy and restarts caddy after successful install

and so on


@Bitti09 Ehh, could end up being a bit convoluted, and IMO doesn’t line up with the Caddy philosophy.

Interesting idea.

When Caddy gets a REST API this will be possible with a simple HTTP request.

It does if another machine does the build, and the “working” Caddy process doesn’t stop until the new one is working fine (we already have this logic in current reloads).


another machine does the build

I feel I’m going to end up hacking together a script that generates .deb packages based on the plugins you want…

1 Like