Back to Blog
Linux16 September 2025Michael Hettwer5 min read

Debian 13 Trixie: how our upgrade run across our own servers went

Debian 13 Trixie rolled across our own servers: what the jump from Debian 12 surfaced and what we pushed back into Ansible.

The Debian project released version 13, code name Trixie, on 2025-08-09. Rather than reading about the upgrade, we rolled it across our own machines in the five weeks since, from the small services box to the machines that host our container workloads, and wrote down what the jump from Debian 12 surfaced. This is that field report: practical, first hand, and free of release-news enthusiasm.

What the jump surfaced

The upgrades behaved as Debian upgrades traditionally do: uneventful until they were not, with every surprise already visible in advance to anyone who reads. The recurring friction points were the usual suspects. One third-party repository did not have Trixie packages on day one, which turned into a two-week wait that cost nothing except impatience. Two locally patched configuration files triggered the package manager's conffile questions, which is exactly what a snapshot beforehand is for: we answered with "take ours", reviewed the diff afterward, and moved the two changes from local patches into a maintained form. One service had changed a default between versions, and testing with a real request rather than a health check caught it.

The machines that came through most smoothly were the ones whose state lived in configuration management beforehand. That is not a compliment to Trixie but an observation about pre-existing discipline: the fewer undocumented local deviations, the less the dist-upgrade had to discover.

One habit transferred from earlier releases without a single change: the written log per machine. Each host's upgrade notes went into the same document, timestamped, with the decisions written above the commands they justified. Re-reading the notes afterward, they read as a question list whose answers were already standing on the machines; pushing those answers back into configuration management turned them from a memory aid into property of the fleet.

The order we kept

Our run followed the same order as in earlier years, and it has not failed us yet: full backup and snapshot first, verified as restorable before anything else moves; then one low-risk machine as the canary, with a written log of every deviation from the release notes path; then one representative per role; then the rest in small batches. Each batch ended with the same verification: services answer their real requests, monitoring is quiet and truthful, logs have no new recurring errors.

A small extra paid its way in the batches: before each window we cleared a defined set of caches and package-managed temporary state, so the actual package operations ran under clean conditions. Nothing in the release notes demanded it; it simply shortened the windows and made the failures that did appear easier to attribute.

Worth repeating, because the release notes say it and it remains true: reading the release notes before running the first command is the cheapest part of the whole exercise. Every surprise we hit was already documented there.

What we pushed back into Ansible afterwards

The upgrade itself is a one-time event, but it leaves a residue of decisions that should not stay local. Everything surfaced by the run went back into our Ansible repository. The conffile verdicts became explicit tasks: where the package default is now right, the local override was dropped; where our behavior is intentional, the override is declared and documented. The changed service default became part of the role rather than a local edit, and the new third-party repository is pinned and versioned like the rest.

The Ansible work after a release also settles a question the notes keep asking: which of these decisions are Trixie-specific and which are just ours? The split is explicit in our repository now: release-driven changes are tagged as such, personal preferences carry their own comment, and the next release will not have to rediscover the difference.

The reason we push this residue back after every release is simple: the next upgrade is cheaper to the exact degree that this one leaves nothing undocumented behind. Server operation is a chain of such releases, and the compounding works in both directions.

What Trixie changes for the way we plan

Two facts from the release shape our planning. Trixie is supported for five years, with long-term support running until June 2030, so there is no reason to rush a cautious fleet. Our practical division for the fleet, straight from this experience: new machines start directly on Trixie, existing systems move in their next scheduled maintenance window with the snapshot discipline above, and nothing moves without a verified rollback path. The habit outlives this release: rollback first, schedule second.

If you plan a Debian upgrade for an environment you would rather not babysit in person: the support services on this site include exactly this kind of accompanied migration, and our earlier posts on restore drills, small-cluster Kubernetes upgrades, and structured Ansible operations describe the same discipline from other angles.

Sources

  • Debian project: "Debian 13 trixie released", https://www.debian.org/News/2025/20250809 (accessed 2026-11-03)
  • Debian: "Debian “trixie” Release Information" (initial release 2025-08-09, support until 2030-06-30), https://www.debian.org/releases/trixie/index.en.html (accessed 2026-11-03)