Skip to content

ESQL: gate wildcard-to-dataset resolution in FROM behind a feature flag#154987

Open
quackaplop wants to merge 1 commit into
elastic:mainfrom
quackaplop:disable-heterogeneous-from
Open

ESQL: gate wildcard-to-dataset resolution in FROM behind a feature flag#154987
quackaplop wants to merge 1 commit into
elastic:mainfrom
quackaplop:disable-heterogeneous-from

Conversation

@quackaplop

@quackaplop quackaplop commented Jul 24, 2026

Copy link
Copy Markdown
Member

What this is about

FROM currently lets a wildcard pattern resolve to datasets as well as indices, so FROM * (or FROM logs*) pulls in any dataset it happens to match. We want that off in released builds — a wildcard should mean "index-likes," exactly as it did before datasets existed — without disturbing any existing index behaviour.

What this PR does

Adds a feature flag, esql_dataset_wildcards (off by default in released builds, on in snapshot/dev). When it's off, a dataset is reachable only by an exact name:

  • Wildcards resolve to indices only. FROM *, FROM logs*, exclusions, aliases, data streams — all behave exactly as before datasets existed. A dataset a wildcard happened to match is simply dropped; the pattern flows to normal index resolution (which already excludes datasets). Nothing is rejected.
  • Exact names still resolve datasets. FROM my_dataset reads the dataset.
  • Explicit mixes still work. FROM my_dataset, my_index still produces the heterogeneous union — only accidental mixing via a wildcard is prevented, not deliberate explicit mixing.

When the flag is on (snapshot/dev), wildcards match datasets exactly as today.

The restriction lives where dataset names are matched — DatasetRewriter.resolve (filters resolved datasets to exact-named ones) and anyPatternCouldMatchDataset (a wildcard never triggers dataset resolution). So a wildcard never reaches a dataset in the first place, rather than being resolved and then rejected. This also means no dataset schema resolution happens for a wildcard query that resolves to indices only.

Why matching, not a heterogeneity gate

An earlier version gated on "a FROM that resolves to both a dataset and an index." That fundamentally breaks FROM *: the moment a dataset exists in the cluster, a bare FROM * matches it and the query fails — a regression for the most common query. You can't preserve "all index expressions work as today" with a post-hoc gate; the fix has to be in resolution. Treating datasets as name-only (not wildcard-swept), like hidden abstractions, leaves every index expression untouched and removes the need for any mix detection, authorization plumbing, or special data-stream handling.

Does it work?

  • Unit tests in DatasetRewriterTests cover the flag-off paths: a wildcard matching only datasets excludes them (relation untouched); a wildcard spanning an index and a dataset resolves to the index only; a prefix wildcard does not reach a dataset; an exact dataset name still resolves; an explicit dataset + index still unions; and the flag defaults off in release builds. The existing wildcard-matches-datasets tests are pinned to the flag on.
  • The dataset integration suites run with the flag enabled — the same way the datasets feature flag itself is enabled for tests in build.gradle — so the wildcard-dataset path is exercised in both snapshot and release-tests.
  • Green locally: DatasetRewriterTests, the dataset ITs, spotlessJavaCheck, and forbiddenApis (main / test / internalClusterTest).

What's in the diff

  • DatasetRewriter: the flag constant, an exact-name filter in resolve, a flag-aware anyPatternCouldMatchDataset, and a package-private rewriteUnsecured overload threading the flag for tests.
  • EsqlResolveDatasetAction / DatasetResolver: read the flag and pass it into resolution.
  • build.gradle: enable the flag for the esql test tasks.

No wire/transport-version change.

To be backported to 9.5.

@quackaplop quackaplop added :Analytics/ES|QL AKA ESQL Team:Analytics Meta label for analytical engine team (ESQL/Aggs/Geo) >non-issue labels Jul 24, 2026
@elasticsearchmachine

Copy link
Copy Markdown
Collaborator

Pinging @elastic/es-analytical-engine (Team:Analytics)

@quackaplop quackaplop added >feature v9.5.1 auto-backport Automatically create backport pull requests when merged and removed >non-issue labels Jul 24, 2026
@quackaplop
quackaplop force-pushed the disable-heterogeneous-from branch from 7db2bab to 29c91e4 Compare July 24, 2026 17:10
@github-actions

github-actions Bot commented Jul 24, 2026

Copy link
Copy Markdown
Contributor

🔍 Preview links for changed docs

⏳ Building and deploying preview... View progress

This comment will be updated with preview links when the build is complete.

@github-actions

Copy link
Copy Markdown
Contributor

ℹ️ Important: Docs version tagging

👋 Thanks for updating the docs! Just a friendly reminder that our docs are now cumulative. This means all 9.x versions are documented on the same page and published off of the main branch, instead of creating separate pages for each minor version.

We use applies_to tags to mark version-specific features and changes.

Expand for a quick overview

When to use applies_to tags:

✅ At the page level to indicate which products/deployments the content applies to (mandatory)
✅ When features change state (e.g. preview, ga) in a specific version
✅ When availability differs across deployments and environments

What NOT to do:

❌ Don't remove or replace information that applies to an older version
❌ Don't add new information that applies to a specific version without an applies_to tag
❌ Don't forget that applies_to tags can be used at the page, section, and inline level

🤔 Need help?

@julian-elastic julian-elastic left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good

@quackaplop
quackaplop enabled auto-merge (squash) July 24, 2026 17:26
@quackaplop
quackaplop disabled auto-merge July 24, 2026 17:33
@quackaplop
quackaplop force-pushed the disable-heterogeneous-from branch from 29c91e4 to 33ebd3d Compare July 24, 2026 18:10
@quackaplop
quackaplop force-pushed the disable-heterogeneous-from branch from 33ebd3d to 7dbf1ca Compare July 24, 2026 18:30
@quackaplop
quackaplop force-pushed the disable-heterogeneous-from branch from 7dbf1ca to 89d3e29 Compare July 24, 2026 18:43
@quackaplop
quackaplop force-pushed the disable-heterogeneous-from branch from 89d3e29 to 421c0d9 Compare July 24, 2026 19:02
@quackaplop
quackaplop force-pushed the disable-heterogeneous-from branch from 2e893c2 to bdd1696 Compare July 26, 2026 08:54
@quackaplop quackaplop changed the title ESQL: gate heterogeneous FROM behind a feature flag ESQL: gate wildcard-to-dataset resolution in FROM behind a feature flag Jul 26, 2026
@quackaplop
quackaplop force-pushed the disable-heterogeneous-from branch from bdd1696 to 82d3237 Compare July 26, 2026 09:17
Add the esql_dataset_wildcards feature flag (off in release builds). When
it is off, a dataset is reachable only by an exact name: a wildcard FROM
pattern resolves to indices only, exactly as it did before datasets
existed, so no existing index expression changes behaviour. An explicit
dataset named alongside an index still produces the heterogeneous union;
only accidental wildcard mixing is prevented.

The restriction lives in dataset name matching (DatasetRewriter.resolve
and anyPatternCouldMatchDataset), so a wildcard never reaches a dataset
rather than being rejected after the fact. The flag is enabled for the
esql test tasks so the wildcard-dataset path runs in release-tests.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

:Analytics/ES|QL AKA ESQL auto-backport Automatically create backport pull requests when merged >feature Team:Analytics Meta label for analytical engine team (ESQL/Aggs/Geo) v9.5.1 v9.6.0

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants