# 0.31.0

Terreno packages move in lockstep. Nothing in this release removes or renames a public
export, so most apps upgrade by bumping the `@terreno/*` versions and running:

- `bun run compile` and `bun run lint` at the repo root
- `cd <your frontend> && bun run sdk` after any `@terreno/api` route or model surface change

## Mongoose 9 is now supported (Mongoose 8 still works)

Every published package that talks to Mongoose (`api`, `test`, `admin-backend`, `ai`,
`feature-flags`) widened its peer dependency to `^8.0.0 || ^9.0.0`. Terreno itself
develops against Mongoose 9.7.4.

You can stay on Mongoose 8 with no changes. If you upgrade your app to Mongoose 9, the
changes that mattered inside Terreno will most likely matter in your code too:

```typescript
// Before (Mongoose 8)
await Model.findOneAndUpdate(filter, update, {new: true});

// After (Mongoose 9)
await Model.findOneAndUpdate(filter, update, {returnDocument: "after"});
```

- Aggregation-pipeline updates must pass `updatePipeline: true` to `updateMany`.
- Query middleware no longer takes the legacy `next()` callback — use the async form.
- Array schema paths expose `getEmbeddedSchemaType()`; the private `caster` property is gone.
- Mongoose 9 ships its own types, so `@types/mongodb` and
  `@types/passport-local-mongoose` should be removed from your dev dependencies.
- Pin `bson` to `7.2.0` if your lockfile resolves an older copy alongside Mongoose 9.

Mongoose 9 requires Node >= 20.19.0. Terreno's root `package.json` now declares that
engine range for local development.

## `@terreno/api` type changes

Both changes widen or relax types; they are source-compatible for normal usage, but
explicit annotations may need updating:

- `modelRouter` now accepts `Model<T, any, any, any, any, any>` instead of `Model<T>`,
  so models with custom query helpers, methods, or virtuals no longer need a cast.
- `findOneOrNoneFor(model, query)` takes `ModelQuery<T>` (a partial record keyed by the
  document fields) instead of Mongoose's `FilterQuery<T>`. If you were building a
  `FilterQuery<T>` value to pass in, it still works; if you were annotating the variable
  as `FilterQuery<T>` and relying on operator typing, switch to `ModelQuery<T>`.

## `@terreno/admin-backend` array field metadata

`GET /admin/config` derives array item metadata (`itemType`, `itemRef`, `itemEnum`) from
Mongoose's public `getEmbeddedSchemaType()` when available, falling back to the Mongoose 8
`caster` shape. `itemEnum` is only emitted when the embedded enum is an array, so an enum
declared as an object map no longer produces a malformed `itemEnum`. Admin clients that
read `itemEnum` should treat it as optional.

## License changed from Apache-2.0 to MIT

All published `@terreno/*` packages are now MIT licensed and ship a `LICENSE` file in the
package tarball. No code change is required; update any license inventory or attribution
list that pinned Terreno as Apache-2.0.
