Skip to content

[FLINK-40170][table-planner] Infer update-producing changelog mode for early-fire interval join - #3

Draft
weiqingy wants to merge 1 commit into
FLINK-36953-pr2-targetfrom
FLINK-36953-pr3-changelog
Draft

[FLINK-40170][table-planner] Infer update-producing changelog mode for early-fire interval join#3
weiqingy wants to merge 1 commit into
FLINK-36953-pr2-targetfrom
FLINK-36953-pr3-changelog

Conversation

@weiqingy

@weiqingy weiqingy commented Jul 18, 2026

Copy link
Copy Markdown
Owner

Part of the FLIP-497 stack under umbrella FLINK-36953. Stacked on PR-2. Landing order: PR-1a → PR-1b → PR-2 → PR-3 (this) → PR-4 → PR-5 → PR-6 → PR-7.

What is the purpose of the change

When EARLY_FIRE is set on an outer interval join, the join emits a speculative null-padded row and later corrects it — an updating result. This PR makes the planner infer that update-producing changelog mode and reject an insert-only downstream with a tailored error. Inner joins and negative-window joins remain append-only.

Brief change log

  • Split an interval-join arm in FlinkChangelogModeInferenceProgram (SatisfyModifyKindSetTraitVisitor): early-fire + outer join + non-negative window ⇒ INSERT,UPDATE; otherwise INSERT_ONLY.
  • Add a tailored TableException when such an updating early-fire interval join feeds an insert-only sink.
  • StreamPhysicalIntervalJoin forwards the trait.

Verifying this change

This change added tests and can be verified as follows:

  • Added IntervalJoinTest plan/changelog cases: early-fire outer join is update-producing; insert-only-downstream throws the tailored error; negative-window + early-fire and inner + early-fire stay INSERT_ONLY.

Does this pull request potentially affect one of the following parts:

  • Dependencies (does it add or upgrade a dependency): no
  • The public API, i.e., is any changed class annotated with @Public(Evolving): no
  • The serializers: no
  • The runtime per-record code paths (performance sensitive): no
  • Anything that affects deployment or recovery: no
  • The S3 file system connector: no

Documentation

  • Does this pull request introduce a new feature? no (planner inference for the FLIP-497 hint)
  • If yes, how is the feature documented? not applicable

Was generative AI tooling used to co-author this PR?
  • Yes (please specify the tool below)

Generated-by: Claude Code (Anthropic)

@weiqingy
weiqingy force-pushed the FLINK-36953-pr3-changelog branch from f6163da to 16ae7d2 Compare July 18, 2026 22:12
@weiqingy
weiqingy force-pushed the FLINK-36953-pr2-target branch from 0b76a4b to dc1e210 Compare July 18, 2026 22:12
@weiqingy weiqingy changed the title [FLINK-36953][table-planner] Infer update-producing changelog mode for early-fire interval join [FLINK-40170][table-planner] Infer update-producing changelog mode for early-fire interval join Jul 18, 2026
@weiqingy
weiqingy force-pushed the FLINK-36953-pr3-changelog branch from 16ae7d2 to 17d607b Compare July 21, 2026 02:17
@weiqingy
weiqingy force-pushed the FLINK-36953-pr2-target branch 2 times, most recently from 2d8840b to 8000ad1 Compare July 21, 2026 04:43
@weiqingy
weiqingy force-pushed the FLINK-36953-pr3-changelog branch from 17d607b to 9dbe90d Compare July 21, 2026 04:43
@weiqingy
weiqingy force-pushed the FLINK-36953-pr2-target branch 2 times, most recently from 0ef163a to 3b14d56 Compare August 2, 2026 22:18
…fire interval join

With the EARLY_FIRE hint, an outer interval join speculatively emits a padded
unmatched row after the delay and corrects it when a match later arrives, so it
no longer produces insert-only changes. Teach FlinkChangelogModeInferenceProgram
to reflect this.

Split StreamPhysicalIntervalJoin into its own ModifyKindSet arm: its children
still consume insert-only, but the node provides INSERT and, when the hint makes
it update-producing, UPDATE. A new produceEarlyFireUpdates accessor gates that on
the hint being set, the join being outer, and a non-negative window span, so the
hint stays inert for inner joins and negative-window joins (which only ever emit
inserts). The interval join keeps its place in the UpdateKind and DeleteKind arms.

When such a join feeds an insert-only downstream, planning fails with a tailored
error that names the hint, rather than the generic "doesn't support consuming
update changes" message. Runtime behavior is unchanged; the operator still
ignores the hint.

The compiled-plan round-trip test's sink now declares sink-insert-only=false:
its early-fire outer join produces updates under the new inference, so the
previously insert-only sink no longer accepts the pipeline.
@weiqingy
weiqingy force-pushed the FLINK-36953-pr3-changelog branch from 9dbe90d to 8f7448f Compare August 2, 2026 22:42
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant