Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 4 additions & 3 deletions content/docs/deployment/cli.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -763,7 +763,7 @@ diverges from the live schema, and the physical column wins at write time.
|---------|-------------|
| `os migrate plan` | Dry-run: show how the database has drifted from metadata, categorised safe / needs-confirm / destructive (no changes applied) |
| `os migrate apply` | Reconcile the database to metadata. Applies loosening changes; destructive ones require `--allow-destructive` |
| `os migrate multi-value-columns` | Migrate a stale `varchar`/`text` column to `json` where the field declares `multiple: true` — one of two drift ops `apply` never reconciles for you. Dry run by default; `--apply` runs the statement the finding prints |
| `os migrate multi-value-columns` | Migrate a stale `varchar`/`text` column to `json` where the field declares `multiple: true` — one of three drift ops `apply` never reconciles for you. Dry run by default; `--apply` runs the statement the finding prints |

```bash
os migrate plan # Preview drift (no changes)
Expand Down Expand Up @@ -852,7 +852,7 @@ occupancy on its own.
| Category | Examples | Applied by |
|----------|----------|------------|
| `safe` | relax `NOT NULL` → nullable, widen a `varchar`, create a declared index (a `UNIQUE` one only when its duplicate pre-flight comes back clean), replace a legacy installation-wide unique with its per-organization composite | `os migrate apply` (and dev auto-reconcile) |
| `needs_confirm` | non-narrowing type change, rebuild a non-unique index whose columns changed | `os migrate apply` — except `manual_widen_varchar_to_text`, which nothing applies |
| `needs_confirm` | non-narrowing type change, rebuild a non-unique index whose columns changed | `os migrate apply` — except `manual_column_type_change` (only `os migrate multi-value-columns --apply` runs it), and `manual_widen_varchar_to_text` and `unbuildable_index`, which nothing applies |
| `destructive` | drop an orphaned column or index, tighten `NOT NULL`, narrow a type, rebuild an index as `UNIQUE`, create a `UNIQUE` index existing rows already violate | `os migrate apply --allow-destructive` |

#### Index drift
Expand All @@ -865,6 +865,7 @@ occupancy on its own.
| `replace_unique_index` | A field's `unique` used to be enforced installation-wide, but metadata now scopes it per organization — the legacy single-column index is swapped for the NULL-safe `(COALESCE(organization_id, '__global__'), field)` composite. A pure relaxation: it creates before it drops, and cannot fail |
| `recreate_index` | An index exists under the declared name but with different columns/uniqueness. The additive sync skips it by name, so it must be dropped and rebuilt. This is also how a per-organization unique becomes NULL-safe: a **tightening**, so it runs a duplicate pre-flight probe first — rows the old NULL-distinct index wrongly admitted **block** the op with a report instead of failing a boot, and the old index stays in place until they are resolved |
| `drop_index` | An index carrying ObjectStack's generated naming (`uniq_…` / `idx_…`) that metadata no longer declares |
| `unbuildable_index` | Metadata declares an index whose key column can never exist: the name is not a field of the object (a misspelling), or it is a virtual `formula` field. Report-only, category `needs_confirm`: severity `error` for a `UNIQUE` index (the declared uniqueness is not enforced), `warning` for a plain one. `os migrate apply` never performs it — it reports the entry `skipped`. Fix the metadata: make every column in the index's `fields` a stored field, or remove the index. A column that is merely not added yet is pending `add_columns` work and is not reported |

Orphan detection is deliberately limited to indexes ObjectStack itself
generated. A hand-rolled covering index you added in `psql` is never reported as
Expand All @@ -887,7 +888,7 @@ it reconciles via a table rebuild (copy → swap) that preserves your data.

#### `os migrate multi-value-columns`

`os migrate apply` will **never** apply this drift op — and it isn't the only one: `manual_widen_varchar_to_text` (an unbounded text-family field left on a pre-existing `varchar` column) is also never applied, but has no `os migrate` subcommand of its own. This section covers the op that does.
`os migrate apply` will **never** apply this drift op — and it isn't the only one: `manual_widen_varchar_to_text` (an unbounded text-family field left on a pre-existing `varchar` column) and `unbuildable_index` (see [Index drift](#index-drift)) are also never applied, and have no `os migrate` subcommand of their own. This section covers `manual_column_type_change`, the op that does.

A field that gains `multiple: true` over a database that already exists keeps
its old `varchar` / `text` column: the additive sync adds columns, and never
Expand Down
Loading