This is an old debate surely? My first awareness of it was probably related to Django's settings.py back around 2007 but I got the feeling from discussions then that it was a discussion that had been bouncing around for a long time before that.
The counter-argument is that declarative configs inevevitably sprout programming-like features - and if they don't someone will write code to generate them.
(disclaimer - in true HN fashion I haven't properly RTFA'd - dinner is nearly ready and I'm feeling bold)
The counter-argument is that declarative configs inevevitably sprout programming-like features - and if they don't someone will write code to generate them.
Yep the idea of declarative winning out over imperative is nothing new. Yet for some reason, most deployment systems make you go through an imperative flow if you want to orchestrate releases.
Because "burn it all down and rebuild everything" is by far the easiest orchestration to create from a declarative config. And is almost certainly not what any technician is going to want to happen to their production system.
The clients and network have state. If you kill every service, and set everything up from scratch, your users are probably seeing an error message. Their connections all died and the retries failed while you were spinning up the new version of things.
Not when your infrastructure includes your data store, though. Or if it includes such things as your application endpoint. You may want to stand up the new endpoints and then drain over traffic, as an example. Not take an outage for a deployment.
Right, yes - sorry, I should have clarified that I didn't mean "tear down then set up", but rather "set up (new), cut over, then tear down (old)". But still - the service should be "created from scratch"!
I mean, you aren't wrong. But I am challenged to think of a service that doesn't store state somewhere.
And you ignore the other situation. Even a fully "stateless" service that literally just responds to things probably doesn't want an outage just to deploy a new version.
That's true. The way we solve it is by splitting our infrastructure deployments in two parts: a volatile part and a persistent part; the volatile part is versioned by buildnumber, so each deployment is side-by-side with the previous one. The drain/switchover is a manual process for now as we have a user acceptance step in the middle.
It gives us more confidence when deploying the stateless part, but sadly it also means that the persistent deployments don't get as much exercise as the stateless part and are somewhat more prone to bitrot.
Comments
This is an old debate surely? My first awareness of it was probably related to Django's settings.py back around 2007 but I got the feeling from discussions then that it was a discussion that had been bouncing around for a long time before that.
The counter-argument is that declarative configs inevevitably sprout programming-like features - and if they don't someone will write code to generate them.
(disclaimer - in true HN fashion I haven't properly RTFA'd - dinner is nearly ready and I'm feeling bold)
Ha! See the make manual for examples.
Background reading: https://stackoverflow.com/questions/3480950/are-makefiles-tu...
Yep the idea of declarative winning out over imperative is nothing new. Yet for some reason, most deployment systems make you go through an imperative flow if you want to orchestrate releases.
Because "burn it all down and rebuild everything" is by far the easiest orchestration to create from a declarative config. And is almost certainly not what any technician is going to want to happen to their production system.
Sort-of a nitpick, but for stateless services that's _precisely_ what you want to happen!
The clients and network have state. If you kill every service, and set everything up from scratch, your users are probably seeing an error message. Their connections all died and the retries failed while you were spinning up the new version of things.
Right, which is why you set up the new versions of the service _first_ and cutover to them before tearing down.
Not when your infrastructure includes your data store, though. Or if it includes such things as your application endpoint. You may want to stand up the new endpoints and then drain over traffic, as an example. Not take an outage for a deployment.
Right, yes - sorry, I should have clarified that I didn't mean "tear down then set up", but rather "set up (new), cut over, then tear down (old)". But still - the service should be "created from scratch"!
Not when your infrastructure includes your data store, though
Then the service is no longer stateless.
I mean, you aren't wrong. But I am challenged to think of a service that doesn't store state somewhere.
And you ignore the other situation. Even a fully "stateless" service that literally just responds to things probably doesn't want an outage just to deploy a new version.
That's true. The way we solve it is by splitting our infrastructure deployments in two parts: a volatile part and a persistent part; the volatile part is versioned by buildnumber, so each deployment is side-by-side with the previous one. The drain/switchover is a manual process for now as we have a user acceptance step in the middle.
It gives us more confidence when deploying the stateless part, but sadly it also means that the persistent deployments don't get as much exercise as the stateless part and are somewhat more prone to bitrot.
The whole article is an ad.