Skip to main content
Version: 2026.8.0

Versioning and breaking changes

An update should add capability without asking you to migrate your data by hand or reinstall anything. That is a design rule with teeth, and here is how it is kept.

Migrations are additive first​

  • Every schema change ships as a numbered SQL migration that runs on the api's first boot after the update.
  • Each migration runs inside its own transaction, so it either applies fully or not at all: a partial change is never left behind.
  • The rule the migrations follow is add, don't rewrite. A new feature adds a column or a table, and it does not drop or rename one out from under the running app.
  • An older image keeps working against a newer schema (the extra column it does not know about is simply ignored), which is what makes stepping back to a previous version safe. See Rollback.
How a removal ships without breaking a running version

When a change does have to remove something, it is split across releases: an earlier release adds the new shape and writes to both old and new, a later one switches reads over, and only a release after that drops the old column.

Renaming a field never moves your data​

  • Renaming a field changes the label, not the storage key. Fields are stored by a stable internal name, and the label you see is a presentation layer resolved when a form loads, so the values stay exactly where they were.
  • There is no data migration on a rename, ever. The same holds for hiding, reordering, or recoloring a field.

Self-heal, not reinstall​

  • When a shape does change, the fix runs itself. On boot the api reconciles each workspace against the current code: a module that added a migration after a workspace enabled it gets caught up automatically, and a workspace that predates a newer structure is brought forward in place.
  • You are never asked to uninstall and reinstall a module or a workspace to pick up a change. If an update ever did require that, it would be a bug, not a procedure.

What "breaking" means in practice​

  • The change that hurts a self-hoster is one that requires manual work or loses data on the way up. The discipline above is aimed squarely at removing both.
  • Pin COBBLR_VERSION if you want to read each release's notes before moving, rather than always taking the latest.
  • A one-time action is called out when a release needs one, and the default assumption is that docker compose pull && up -d is all an update takes.