feat: v1.7.0 -> master#11042
Conversation
|
Claude finished @ovr's task in 59s —— View job Code Review — v1.7.0 release / Elasticsearch driver removalOne-line headline: LGTM — clean removal of the deprecated Elasticsearch driver. 0 high, 0 medium, 1 low. Full review (click to expand)Checklist
SummaryThis PR removes the What I verified
FindingsLow — Removed redirects will now 404 instead of redirecting
Nits
Not reviewed
|
|
Claude finished @ovr's task in 38s —— View job Code Review — v1.7.0 release / Elasticsearch driver removalOne-line headline: LGTM — clean removal of the deprecated Elasticsearch driver. 0 high, 0 medium, 1 low. (Re-affirmed: no new commits since the prior review — HEAD is still Full review (click to expand)Checklist
SummaryThis PR removes the What I verified
FindingsLow — Removed redirects will now 404 instead of redirecting
Nits
Not reviewed
• Branch: |
Codecov Report✅ All modified and coverable lines are covered by tests. Additional details and impacted files@@ Coverage Diff @@
## master #11042 +/- ##
=======================================
Coverage 83.68% 83.68%
=======================================
Files 257 257
Lines 79384 79383 -1
=======================================
+ Hits 66429 66431 +2
+ Misses 12955 12952 -3
Flags with carried forward coverage won't be shown. Click here to find out more. ☔ View full report in Codecov by Harness. 🚀 New features to boost your workflow:
|
BREAKING CHANGE: The Elasticsearch driver has been removed. It was deprecated in v1.6.0. There is no drop-in replacement.
…11044) BREAKING CHANGE: The running_total measure type has been removed. Data models that use `type: running_total` will now fail validation. Replace them with a rolling_window measure using an unbounded trailing window.
…iable (#11048) BREAKING CHANGE: The CUBEJS_SCHEDULED_REFRESH_CONCURRENCY environment variable has been removed. It was deprecated in v1.2.7. Use CUBEJS_SCHEDULED_REFRESH_QUERIES_PER_APP_ID instead.
BREAKING CHANGE: The `renewQuery` parameter of the `/v1/load` REST endpoint and the GraphQL `cube` query has been removed. Use the `cache` parameter instead: `cache: 'must-revalidate'` replaces `renewQuery: true`, and the default `stale-if-slow` replaces `renewQuery: false`.
BREAKING CHANGE: The context_to_roles (contextToRoles) configuration option has been removed. It was deprecated in v1.6.4. Use context_to_groups (contextToGroups) instead.
BREAKING CHANGE: CreateOptions.dbType has been removed. Use driverFactory instead.
Node.js 20 reached EOL on April 30, 2026; Node.js 22 is in maintenance mode since October 21, 2025. The minimal supported version is now 22.
Toolkit has a dependecy on @achrinza/node-ipc that blocks migration for new Node.js everytime. More funny, that it still doesn't support Node.js 26, which I wan to declare in testing matrix. We don't define any .vue files, that's why we can use babel without anything especiall, moreover we build this package outside it folder. We define config in the root directory for rollup bundler # Conflicts: # yarn.lock
…parser babel-eslint has been deprecated since 2020 and was only resolving via hoisting from the legacy vue-cli toolkit until it was dropped. Use the maintained @babel/eslint-parser instead and declare it explicitly in both packages that reference it.
BREAKING CHANGE: Users who install custom Python packages into the Cube image (e.g. for Python/Jinja data models) must target Python 3.13. Packages built for 3.11 will not load.
BREAKING CHANGE: The -jdk image now runs Java 21. JDBC drivers and custom JARs must be compatible with OpenJDK 21.
…fault Tesseract is now the default SQL planner. CUBEJS_TESSERACT_SQL_PLANNER defaults to true (TS env + Rust cubesql config); explicitly disabling it falls back to the legacy planner and emits a one-time deprecation warning, since the legacy planner will be removed in the near future. Tesseract pre-aggregation planning is no longer independently configurable: the CUBEJS_TESSERACT_PRE_AGGREGATIONS env var is dropped, and pre-aggregation planning now follows CUBEJS_TESSERACT_SQL_PLANNER. BaseQuery still honors neverUseSqlPlannerPreaggregation() so CubeStoreQuery stays opted out for correctness (HLL/multi-stage).
In a wrapped SQL-API query, cubesql pushes a grouped CubeScan whose
granularized time-dimension column it references by an explicit alias,
sent via `memberToAlias` keyed `{member}.{granularity}` (e.g.
`orders.created_at.month` -> `datetrunc_utf8__`). Regular dimensions and
measures already honor this override, but `TimeDimensionSymbol` computed
its alias as `{base alias}_{granularity}` (`orders__created_at_month`)
and ignored the override. The wrapper then referenced a column the
CubeScan never emitted -> `column "datetrunc_utf8__" does not exist`.
Look up the `memberToAlias` override for the granularized member in
`compile_time_dimensions` and pass it through a new
`TimeDimensionSymbol::new_with_alias`. When no override is present the
alias is unchanged, so non-pushdown queries are unaffected.
The legacy planner wraps SQL generation in compiler.withQuery() so JS extensions can resolve compiler.contextQuery() during member-SQL evaluation. The Tesseract path (buildSqlAndParamsRust) skipped this, so extensions like Funnels/RefreshKeys hit `contextQuery()` undefined when the native planner calls back into JS.
A masked aggregate measure whose conditional row-level mask filter references a dimension that is in the GROUP BY crashed the native planner with "Measure filter node processor called for wrong node". `MaskedSqlNode::resolve_mask` rendered the mask filter through `self.input` — the measure processor chain (`CaseSqlNode -> MeasureFilterSqlNode -> ...`). When the filter evaluated a dimension reference it reached `MeasureFilterSqlNode`, which only accepts measures and errored. Build a second, kind-dispatching "unmasked" processor tree (a `RootSqlNode` with masking disabled via a new `skip` flag) and render the mask filter through it, so a dimension reference routes through the dimension chain and a filter member that is itself masked does not recurse — mirroring the legacy planner's `skipMasking` behaviour in `conditionalMemberMaskSql`. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
OracleQuery only overrode legacy-planner methods (asSyntaxTable, groupByDimensionLimit, groupByClause), so the native planner fell back to the generic templates and produced invalid Oracle: `AS` before table / subquery aliases, `LIMIT`, and positional `GROUP BY`. Add `sqlTemplates()` overrides so the native planner emits Oracle-compatible SQL: no `AS` before aliases (query_aliased + FROM subquery), expression-based GROUP BY, and `OFFSET ... ROWS FETCH NEXT ... ROWS ONLY`. Update the unit tests for the native planner: drive row limiting via `rowLimit` (the option the planner reads — the native planner applies no default limit), and accept the planner's quoted subquery aliases. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…anner The native (Tesseract) planner — now the default — emits semantically equivalent SQL with different formatting from the legacy planner. Update the expectations accordingly: - single-line SQL with the planner's whitespace (e.g. `FROM t AS "t"`, `ORDER BY 2 ASC`) in base-query syntax-sugar and join tests; - fewer wrapping parens in FILTER_PARAMS / FILTER_GROUP substitutions (`(type = ?)` vs `((type = ?))`); - quoted subquery aliases (`AS "q_0"`); - multi-granularity auto-order emits every granularity column (result- equivalent to the legacy min-granularity-only ordering); - MSSQL rolling-window queries group by the calculated-granularity expression instead of a time-series CTE alias. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…e-agg dates The native planner computes pre-aggregation partition ranges eagerly during matching, calling `inDbTimeZone`. When the query has no timezone this hit `localTimestampToUtc(undefined, ...)` and threw "Unknown timezone: undefined" (the legacy planner is lazy and never reached it). Default to UTC so a timezone-less query can still match/describe partitioned pre-aggregations. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…he pre-agg The native pre-aggregation matcher only rejected multiplied measures when the query itself was multiplied, so a query for an unmultiplied measure (e.g. `orders.total_qty`) wrongly matched a pre-aggregation that multiplies it by grouping on a joined cube's dimension — the stored value differs. This ports the JS planner's #9541 rejection. Add `MultiFactJoinGroups::multiplied_measures()` and reject a match when a used measure is multiplied in the pre-aggregation but not in the query. The query's multiplicativity is computed filter-aware (a multiplying filter, like a multi-stage measure, makes the multiplied pre-agg a legitimate match), matching the JS `hasMultipliedMeasures` gate. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
A rollupLambda UNIONs member rollups that can belong to different cubes
(e.g. `Requests.batch` ∪ `RequestsStream.stream`, `Orders.*` ∪
`RealTimeOrders.AOrdersByCompletedByHour`). The lambda exposes the first
member rollup's symbols, so every member alias is the first cube's
(`requests__tenant_id`, `orders__status`). The physical union builder read
each branch's dimension columns through `dim.alias()` for all branches,
which only holds for same-cube branches — the streaming/real-time branch
stores `requests_stream__tenant_id` / `real_time_orders__status`, so the
per-branch SELECT referenced a missing column and DataFusion rejected it
("No field named requests__tenant_id …").
Carry each union branch's own member symbols on the union item and resolve
every lambda member to that branch's equivalent member, reading through the
branch member's alias while projecting under the lambda's unified alias.
Matching mirrors the legacy planner's `columnsFor`: exact full-name match
first (a dimension from a joined cube is identical across branches, keeping
the previous cross-cube-dimension fix), then the short member name within
the branch's own cube (a cross-cube union member). Applied uniformly to
dimensions, time dimensions and measures; for same-cube branches the read
and output aliases coincide, so behavior there is unchanged. Also fixed the
off-by-one in the lambda symbol-name validation (`i > 1` → `i >= 1`) so the
second member rollup is checked against the first.
Adds a Rust regression test over the cross-cube `lambda_union` fixture
asserting each branch reads its own columns and projects the unified alias.
The native planner identifies a matching pre-aggregation by building the full query SQL. For a rolling-window measure that includes the measure's time series, which requires a date range. The pre-aggregation refresh/metadata path (e.g. the /cubejs-system/v1/pre-aggregations API) builds such a query with no date range, so the native build threw "Date range is required for time series" and the endpoint returned 500. Route that case — cumulative measures with no date range — to the legacy planner, which matches pre-aggregations structurally without building the time series, as it did before Tesseract became the default planner. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
With rolling-window pre-aggregation reads fixed, the postgresql-cubestore suite returns a row per time bucket in the requested range (dense) — null/0 for buckets with no data, including the null-source and google-source rows that exist in the seed. Regenerate the stale sparse snapshots for "Rolling Mixed" and "Rolling Prev Period ratio" so they match the other (already-dense) rolling tests. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
No description provided.