Skip to content

Commit 5141487

Browse files
committed
chore(changeset): @objectstack/lint minor, BREAKING: a cube measure is judged on every row of the table
Claude-Session: https://claude.ai/code/session_01UtnxvdiN376GF3sgXwAw4d Co-authored-by: Claude <noreply@anthropic.com>
1 parent 123989f commit 5141487

1 file changed

Lines changed: 17 additions & 0 deletions

File tree

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
---
2+
"@objectstack/lint": minor
3+
---
4+
5+
fix(lint)!: `os validate`, `os build` and `os lint` refuse an `analyticsCubes` measure whose aggregate the aggregate × field-type table refuses for its column, which the analytics door already refuses at query time
6+
7+
Clause-②: no (narrowing)
8+
9+
<!-- adr-0087: not-required (no-migration-prescription) a refusal at authoring of cube measure pairs the analytics door already refuses with 400 INVALID_FIELD at query time: an analyticsCubes measure whose type is sum, avg, min or max over a column whose declared type that row of AGGREGATE_FIELD_TYPE_COMPATIBILITY does not accept. The table is not edited, and no authorable key, spelling, export or stored shape moves: CubeSchema keeps parsing every measure, no stored row is read or rewritten, and which numeric field an author meant to add up, average or order by is not something a ledger entry can rewrite. The other categories are closed on facts: the package publishes (not unpublished); the dataset-measure-aggregate-field-type-refused and dataset-measure-selecting-aggregate-field-type-refused entries describe DatasetMeasureSchema rows, and this rule's existing cube leg declared this same category on that ground (not already-registered); and the change is a rule verdict, not a declaration (not runtime-interface-only or type-surface-only). -->
10+
11+
**BREAKING**: metadata that passed `os validate`, `os build` and `os lint` can now fail. A cube measure's `type` is its aggregate, and the analytics door judges every cube measure against `AGGREGATE_FIELD_TYPE_COMPATIBILITY` before any SQL is built: a pair the table refuses is answered `400 INVALID_FIELD`. The authoring check judged only a cube's `count_distinct` measures, so a cube `sum` over a `text` column, for one, passed every command and was refused on its first query. The `measure-aggregate-field-type-refused` id (gating, `error`) now judges every cube measure exactly as it judges a dataset measure. It ships as `minor` under the launch-window convention for accept-set narrowings. No export is added or removed.
12+
13+
**What is refused.** On a cube whose `sql` names an object the stack defines: a `measures` entry of `type` `sum`, `avg`, `min` or `max` whose `sql` column is declared with a type outside that aggregate's row of `AGGREGATE_FIELD_TYPE_COMPATIBILITY` (`@objectstack/spec/data`). The four rows accept the numeric and boolean types, `min` and `max` the temporal types too, and `sum` does not accept `percent`; so a text, option, reference, file or structured-JSON column, among others, is refused under all four, and a `date`, `datetime` or `time` column under `sum` and `avg`. The column is the measure's `sql`: a column of the cube's object, or a relationship path read on the object its last hop reaches (the join the cube declares for that hop, else the lookup field's `reference`).
14+
15+
**What an author sees now.** The finding names the cube, the measure, the column, the object that declares it and its type, the types the aggregate accepts and the aggregates the column's type accepts, and says the analytics door refuses the pair with `400 INVALID_FIELD`. It is located at `analyticsCubes[N].measures.KEY.type`, where `KEY` is the measure's key. A quantity that must be added up, averaged or ordered has to be stored as a numeric or temporal field and aggregated as one; `count` accepts every column.
16+
17+
**Unchanged.** Every dataset finding and every cube dimension finding; a cube `count` measure over any column; a cube `count_distinct` measure, judged as before; a measure of an expression type (`number`, `string`, `boolean`); the row wildcard `'*'`; a measure whose column does not resolve or declares no type; a cube whose `sql` names no object this stack defines. The runtime metadata write door: no authoring rule is dispatched for an `analytics_cube` save.

0 commit comments

Comments
 (0)