Saturday, April 18, 2026
๐Ÿ›ก๏ธ
Adaptive Perspectives, 7-day Insights
Technology

Cloud Apps Are Not Deploy-and-Forget

Today's fifteen-minute Node 24 upgrade is a reminder that cloud applications carry a maintenance calendar whether you planned for one or not.

Cloud Apps Are Not Deploy-and-Forget

As part of my job, I built a small HIPAA-covered application on AWS serverless primitives a while back. Today I spent about fifteen minutes upgrading it from Node.js 20 to Node.js 24. The work was a single configuration change replicated across a handful of Lambda functions. Zero code changes. Zero downtime. Done before lunch.

If I hadn’t done it, nothing would have broken โ€” tomorrow, or next week, or even next month. Amazon doesn’t switch off your functions the day a runtime hits end-of-support. They just stop patching it. For a workload that touches protected health information, that’s not a tradeoff I’m willing to make.

The upgrade itself was easy. What’s harder is getting across the idea that the day you deploy something to the cloud is not the end of the job. It’s the beginning. The ribbon-cutting isn’t also the retirement party. Every cloud dependency carries a clock, and that clock starts the day you ship.

The AWS deprecation calendar

Amazon publishes a schedule for every managed runtime. For Node.js 20 on Lambda, it looks like this:

MilestoneDate
End of security patchesApril 30, 2026
Block function creationAugust 31, 2026
Block function updatesSeptember 30, 2026

Note what’s missing: a date when invocations stop. AWS never blocks invocations of a deprecated runtime. Your function will keep running, possibly for years. It just won’t receive security patches, won’t appear in the console dropdown, and eventually you won’t be able to change a line of code without first upgrading the runtime.

For regulated workloads, the real deadline is the first row โ€” the day the patches stop. Unpatched code handling PHI is not a position I want to defend in an audit.

Node.js 22 on Lambda hits the same milestones in 2027. Node.js 24 in 2028. Upgrading to 22 would have bought me twelve months of support. Upgrading to 24 buys twenty-four. I took the longer runway.

What else needs upkeep

A runtime upgrade is one of the more visible items on the maintenance calendar. It is not the only one. A cloud application, even a small one, sits on top of a stack of dependencies that all have their own clocks:

  • TLS certificates. ACM handles renewal automatically if your setup is right. If it isn’t โ€” if you bolted on a certificate manually, or if DNS validation broke because someone changed a record โ€” you find out when a browser starts warning your customers.
  • Database engine versions. RDS and Aurora roll minor versions on their own cadence. Major versions occasionally force-migrate. If you’re on PostgreSQL 14 and AWS announces it’s leaving extended support, you’re on a schedule whether you planned for one or not.
  • Dependency CVEs. Your package.json is a list of other people’s code running in your environment. When one of them publishes a security advisory, you’re on the hook for the patch.
  • AWS SDK versions. AWS SDK v2 is on a deprecation glide path. Staying current on v3 isn’t optional if you want to keep getting features and fixes.
  • IAM policies. AWS deprecates actions and introduces new ones that should be scoped tighter than the old wildcard someone wrote in 2019. Those policies don’t audit themselves.
  • Container base images. If you’re on Fargate or EKS, the base image your team picked two years ago is almost certainly out of support.
  • DNS and domain renewals. Route 53 auto-renews. Many third-party registrars don’t by default.

None of this is dramatic. None of it makes a good war story. But collectively, it’s why a “small” application I haven’t added features to in months has still seen a steady trickle of small changes over the last several months โ€” almost all of them driven by the ecosystem around the code rather than the code itself.

Make the maintenance cheap

The question isn’t whether you’ll do maintenance on a cloud app. You will. The question is whether you’ve made it a fifteen-minute job or a fifteen-day project.

A few things that kept today’s upgrade in the fifteen-minute category:

  1. Single-responsibility functions. Each Lambda does one thing. Auditing one of them for Node 24 compatibility took a few minutes. Auditing the whole set took under half an hour.
  2. Lean dependencies. The heaviest function imports three AWS SDK clients. No ORM, no framework, nothing compiled from C++. Every package you don’t install is one you never have to audit.
  3. Reproducible commands, not runbooks. The upgrade was a bash loop against the AWS CLI, not a multi-step checklist executed by hand. Every time I’ve written a runbook instead of a script, I’ve regretted it six months later when I couldn’t remember what order to run the steps in.
  4. Observability that was already there. CloudWatch logs confirmed the runtime swap in real time. I didn’t have to add instrumentation to know the upgrade worked โ€” I just had to read the logs that were already being written.
  5. Documentation that actually tracks decisions. When I came back to this repo cold today, every prior change โ€” every patch, every version bump, every deprecation I’d dealt with before โ€” was in the README. Nothing is worse than doing the same audit twice because you didn’t write down what you learned the first time.

The cost of those habits is front-loaded. You pay for them the first time you build the thing. You get that cost back every time the ecosystem shifts around you โ€” and in cloud, the ecosystem is always shifting.

Maintenance isn’t the tax you pay for shipping. Maintenance is shipping.