Skip to content

branch-4.0: [fix](test) fix branch-4.0 P0 regression failures (build #198126) - #64525

Merged
morningman merged 32 commits into
apache:branch-4.0from
morningman:tc-198126-backports
Jun 17, 2026
Merged

branch-4.0: [fix](test) fix branch-4.0 P0 regression failures (build #198126)#64525
morningman merged 32 commits into
apache:branch-4.0from
morningman:tc-198126-backports

Conversation

@morningman

@morningman morningman commented Jun 15, 2026

Copy link
Copy Markdown
Contributor

What problem does this PR solve?

Stabilizes the branch-4.0 P0 / Cloud-P0 regression pipeline. It started from the
failures in regression build #198126 and has since grown to cover additional flaky /
failing suites surfaced by subsequent P0 and Cloud-P0 runs.

Most commits are test-only (deflaking, isolation, session-default pinning, branch-4.0
compatibility, or temporarily skipping cases whose feature is absent / whose backport
is pending). Two are real product fixes backported from master, plus one debug-point
gate change with no production impact.

Product fixes backported from master

  • [fix](load) fix empty statistics for forwarded INSERT #64439 [fix](load) fix empty statistics for forwarded INSERT — a forwarded
    INSERT ... SELECT showed empty JobDetails (ScannedRows=0, LoadBytes=0, …)
    because the regular Coordinator / CloudCoordinator fallback path was built without
    the insert jobId, so LoadManager progress was never initialized/updated. The
    jobId is now preserved on both fallback paths. Fixes load_p0/insert/test_insert_statistic.
  • [fix](ann-index) Fix ANN range search state leakage and incorrect slot index tracking. #63666 [fix](ann-index) Fix ANN range search state leakage and incorrect slot index tracking — ANN range-search execution state was stored on the shared VExpr
    root, so a segment that ran ANN range search could leak state into a segment without an
    ANN index and wrongly drop the common expression; it also mixed schema column indexes
    with storage column ids. State now flows through the evaluation call and slot status is
    keyed by source column index. Adapted to 4.0 (this branch predates enable_result_cache,
    so that parameter is dropped from the ported signatures).

Product change behind a debug point (no production impact)

  • [fix](compaction) let time_series_level2_file_count debug point bypass the level2 freshness gate — the 24h freshness gate skipped freshly-created level1 rowsets before
    the time_series_level2_file_count debug point could collect them, so
    test_time_series_compaction_level2 never forced a level-2 merge (tablet kept 11
    rowsets instead of 2). The debug point now guards the gate; with debug points disabled
    is_enable() returns false, so behavior is unchanged.

Test suites backported from master

  • [test](regression) Add debug point ANN index-only scan test #63859 [test](regression) Add debug point ANN index-only scan test — replaces the
    fragile ScanBytes-profile-based ANN suites (an unreliable index-only proxy) with
    debug-point suites that directly fail if the embedding column is read in index-only
    scenarios. Fixes ann_index_p0/ann_index_only_scan_distance_expr and
    ann_index_p0/ann_index_only_scan_metric_direction.
  • partial [fix](be) Rename CPU time profile counter #64238 — ports only the scanner_profile actualRows regex fix
    (PhysicalOlapScan[<id>] renders the numeric nereids id, not the table name, so the
    old PhysicalOlapScan[scanner_profile] regex could never match). The BE CPU-time
    counter rename in [fix](be) Rename CPU time profile counter #64238 is intentionally NOT backported to a release branch.

Aligned with the enable_insert_strict / enable_strict_cast decoupling (#63794)

  • insert_p0/insert_group_commit_into_max_filter_ratio — cherry-pick from master.
  • external_table_p0/hive/write/test_hive_ctas_to_doris — set enable_strict_cast=true
    so the CTAS casts behave as the expected output was generated under.

Deflaking — asynchronous profile-report races

The BE reports the detailed execution profile to FE after the query result returns;
tests that fetched the profile with a fixed sleep raced that report (empty MergedProfile).

  • query_profile/scanner_profile — poll getProfileByToken (Awaitility) until the scan
    operator lands before asserting MaxScanConcurrency / backfilled actualRows (sits on
    top of the regex fix above; it was the only query_profile test with no wait/retry).
  • query_profile/adaptive_pipeline_task_serial_read_on_limit — same fix: poll until
    MaxScanConcurrency lands instead of Thread.sleep(500).
  • AutoProfileTest (FE UT) — the JMockit result=System.currentTimeMillis() froze the
    begin-time at record time while the duration was measured against the real wall clock,
    leaving only ~101ms of slack. Drop JMockit + both sleeps and set queryBeginTime
    directly (now / now-60s) for a deterministic ~60s margin.

Deflaking — CBO / statistics timing

  • nereids_rules_p0/mv/.../partition_curd_union_rewrite — guard the six post-insert
    mv_rewrite_success checks with is_partition_statistics_ready (matching the suite's
    own pre-mutation calls); new-partition row-count stats are reported asynchronously, so
    within the fixed sleep CBO costed the union plan above the direct plan and emitted
    "not chose".
  • nereids_syntax_p0/distribute/prune_bucket_with_bucket_shuffle_join — pin
    parallel_pipeline_task_num=1 so the bucket-shuffle downgrade heuristic
    (totalBucketNum < backEndNum*paraNum*0.8) doesn't fire on a high-core Cloud-P0 agent
    and downgrade BUCKET_SHUFFLEPARTITIONED.
  • correctness_p0/test_colocate_join_of_column_order — inject column stats (set stats)
    before EXPLAIN so the COLOCATE-vs-PARTITIONED cost choice is deterministic
    (freshly-created tables have rowCountReported=false until the async CloudTabletStatMgr
    tick).

Deflaking — cross-FE system-table semantics

  • query_p0/schema_table/test_sql_block_rule_statusBLOCKS is a cross-FE SUM over
    each FE's non-replicated in-memory counter, so a stray counter on another FE makes the
    sum exceed 1. Set fetch_all_fe_for_system_table=false so the read sees only the local
    FE that ran the blocked query.
  • nereids_p0/cache/parse_sql_from_sql_cache — drop the racy cross-FE assertNoCache:
    the sql-cache result lives on a shared BE chosen by a deterministic hash, so a second FE
    can legitimately serve the same query from cache. Keep the meaningful assertHasCache.

Deflaking — routine-load adaptive timeout (test_routine_load_adaptive_param + RoutineLoadTestUtils)

The adaptive timeout is only recomputed when a task is scheduled with data, and the
converged value can sit on an idle (txnId == -1) task; the old txnId != -1 gate raced
a sub-second live-txn window.

  • RoutineLoadTestUtils.checkTaskTimeout — skip transient txnId == -1 tasks and poll
    until a stable task carries the expected timeout.
  • restore phase — checkTaskTimeoutWithData feeds a small batch each round to force the
    timeout to recompute.
  • increase phase — drive data each round too, and rewrite the txn-timeout check to join on
    the task UUID and read the persisted timeout from the committed transaction
    (SHOW TRANSACTION WHERE label) instead of catching a live txn.

Deflaking — publish / delete visibility & file cache

  • fault_injection_p0/.../test_f_delete_publish_skip_read — replace Thread.sleep(12000)
    with a bounded Awaitility poll until the delete (v4) is actually published and visible
    (k1=2 gone). The storage engine applies the delete correctly; the race was in publish
    timing (the disable_block request could queue behind the in-flight stream load).
  • external_table_p0/cache/test_file_cache_statistics (and test_file_cache_query_limit)
    file_cache_statistics reports one row per (cache_path, metric) and a data file
    hashes to exactly one path, so a bare limit 1 inspected an arbitrary path. Sum each
    metric across paths (SUM(CAST(METRIC_VALUE AS DOUBLE))) and replace fixed sleeps with
    Awaitility.

Determinism — pin fuzzed session defaults / fix drifted expected output

  • check_before_quit — pin the two fuzzed variant session defaults to 0 so the
    CREATE → recreate → show-create round-trip is idempotent for property-less variant columns.
  • variant_p0/.../test_variant_compaction_with_sparse_limit — pin
    default_variant_max_subcolumns_count=2048 (the FE default the .out was generated
    under) so nested paths stay typed subcolumns.
  • audit/test_audit_log_behavior — correct the drifted query_id column to varchar(128)
    (Config.label_regex_length); stmt_type stays varchar(48).

branch-4.0 compatibility — remove unsupported enable_condition_cache variable

enable_condition_cache does not exist on branch-4.0, so set enable_condition_cache=false
fails with "Unknown system variable". Removing the line is a semantic no-op (the branch is
already in the cache-disabled state the tests expect). Applied to the ann_index_only_scan
debug-point cases (from #63859) and the ann_range_search cases (from #63666).

Test isolation

  • backup_restore/test_backup_restore_reset_index_id (+ test_backup_restore_inverted_idx,
    restore_p0/test_validate_restore_inverted_idx) — these three suites mutate the
    process-global restore_reset_index_id FE config; running in parallel, one could flip it
    between another suite's BACKUP and RESTORE (build #198126). They are now in the
    nonConcurrent group so they run serially. The FE reset logic itself is correct; purely
    a test-isolation fix.

Temporarily skipped / disabled

Release note

None

Check List (For Committer)

  • Test

Check List (For Reviewer who provide ASF feature)

  • Performance regression

@hello-stephen

Copy link
Copy Markdown
Contributor

Thank you for your contribution to Apache Doris.
Don't know what should be done next? See How to process your PR.

Please clearly describe your PR:

  1. What problem was fixed (it's best to include specific error reporting information). How it was fixed.
  2. Which behaviors were modified. What was the previous behavior, what is it now, why was it modified, and what possible impacts might there be.
  3. What features were added. Why was this function added?
  4. Which code was refactored and why was this part of the code refactored?
  5. Which functions were optimized and what is the difference before and after the optimization?

@morningman morningman changed the title [fix](test) fix branch-4.0 P0 regression failures (build #198126) branch-4.0: [fix](test) fix branch-4.0 P0 regression failures (build #198126) Jun 15, 2026
@morningman

Copy link
Copy Markdown
Contributor Author

run buildall

sollhui and others added 9 commits June 15, 2026 22:59
### What problem does this PR solve?

When `INSERT INTO ... SELECT` is forwarded from a follower FE to the
master FE, `SHOW LOAD` could show an empty `JobDetails`, such as
`ScannedRows=0`, `LoadBytes=0`, `TaskNumber=0`, and empty backend lists.

The root cause is that the insert load job is registered with a real
`jobId`, but when coordinator creation falls back to the regular
`Coordinator` / `CloudCoordinator` path, that `jobId` was not passed
into the coordinator. Therefore, the coordinator kept the default
`jobId=-1` and did not initialize or update the corresponding
`LoadManager` progress. The load job was still recorded as `FINISHED`,
but its `LoadStatistic` remained empty when `SHOW LOAD` rendered
`JobDetails`.

This PR preserves the insert `jobId` in the regular `Coordinator` and
`CloudCoordinator` fallback paths, so `initJobProgress()` and
`updateJobProgress()` update the same `InsertLoadJob` that is later
recorded and displayed by `SHOW LOAD`.

(cherry picked from commit a53679b)
…3859)

Issue Number: None

Related PR: None

Problem Summary: The previous ANN index-only scan regression coverage
inferred whether source vector columns were skipped by comparing
ScanBytes from query profiles. That made the test hard to review and
could miss cases where both query shapes still read the source column.
Replace that coverage with a dedicated debug-point regression that
directly fails if the embedding column is read in index-only scenarios,
including a remapped reader-schema case where the source slot index
differs from the storage column id. Remove the old profile-based suites
and generated output.

None

- Test: Manual test
    - git diff --cached --check
- Regression test not run per request; an earlier attempt was blocked by
Maven writing to /Users/roanhe/.m2/repository under the sandbox
- Behavior changed: No
- Does this need documentation: No

Issue Number: close #xxx

Related PR: #xxx

Problem Summary:

None

- Test <!-- At least one of them must be included. -->
    - [ ] Regression test
    - [ ] Unit Test
    - [ ] Manual test (add detailed scripts or steps below)
    - [ ] No need to test or manual test. Explain why:
- [ ] This is a refactor/code format and no logic has been changed.
        - [ ] Previous test can cover this change.
        - [ ] No code files have been changed.
        - [ ] Other reason <!-- Add your reason?  -->

- Behavior changed:
    - [ ] No.
    - [ ] Yes. <!-- Explain the behavior change -->

- Does this need documentation?
    - [ ] No.
- [ ] Yes. <!-- Add document PR link here. eg:
apache/doris-website#1214 -->

- [ ] Confirm the release note
- [ ] Confirm test cases
- [ ] Confirm document
- [ ] Add branch pick label <!-- Add branch pick label that this PR
should merge into -->

(cherry picked from commit 6e5198b)
…pache#64238)

The scanner_profile suite asserts that `actualRows` is backfilled onto the
PhysicalOlapScan node, but the regex `PhysicalOlapScan\[scanner_profile\]`
can never match: FE renders the node as `PhysicalOlapScan[<id>] ( table=
scanner_profile, ... actualRows=N )` (the bracket holds the numeric nereids
id, not the table name). matcher.find() is always false regardless of the
backfilled value, so the case fails deterministically.

Upstream apache/doris apache#64238 (952aede) fixes this regex to
`PhysicalOlapScan[^\n]*scanner_profile[^\n]*actualRows=(\d+)`. This is a
minimal port of ONLY that regex change. The rest of apache#64238 (a BE CPU-time
counter rename `MaxFindRecvrTime`->`MaxFindRecvrCpuTime` plus new
`TaskCpuTime`/`ScannerCpuTime` profile assertions and BE unit tests) is an
unrelated cosmetic cleanup; it is intentionally NOT backported to avoid
shipping a BE change and profile-naming assertions to a release branch.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…126)

test_temp_table asserted `3 * replicaNum == show_tablets_result.size()`,
deriving replicaNum by regex-parsing force_olap_table_replication_allocation
with `/:(\d+)/`. That detection is wrong on clusters that force replication=3:
the canonical allocation string `tag.location.default: 3` has a space after
the colon so the regex never matches (replicaNum stuck at 1), and the separate
force_olap_table_replication_num config is never consulted. On the 3-replica
TeamCity cluster SHOW TABLETS returned 9 rows (3 tablets x 3 replicas) while
the test expected 3.

Keep verifying the real replica count (so a wrong/missing replica is still
caught) but fix the detection:
- assert there are exactly 3 distinct tablets (3 partitions x 1 bucket), and
- assert total rows == 3 * replicaNum, where replicaNum is derived robustly and
  mirrors FE precedence (PropertyAnalyzer.analyzeReplicaAllocation): the
  force_olap_table_replication_allocation per-tag counts are summed first with a
  whitespace-tolerant regex `/:\s*(\d+)/`, falling back to
  force_olap_table_replication_num.

Same defect exists on apache/master; forward-port there too.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…dex_id (build #198126)

restore_reset_index_id is a single process-global, master-only, mutable FE
config read at RESTORE execution time (OlapTable.resetIdsForRestore). Three
suites mutate it:
- backup_restore/test_backup_restore_reset_index_id (sets true, then asserts
  the restored index id was reset to a new value)
- backup_restore/test_backup_restore_inverted_idx (sets false / true)
- restore_p0/test_validate_restore_inverted_idx (sets false / true)

Because the regression framework runs NORMAL suites in parallel, one suite can
flip the shared global config between another suite's BACKUP and RESTORE. In
build #198126 a concurrent suite set restore_reset_index_id=false after
test_backup_restore_reset_index_id had set it true, so that suite's RESTORE
took the else-branch, kept the original index id, and the line-142 assertion
failed (old id == new id).

Add these suites to the `nonConcurrent` group so they run serially in the
single-thread SINGLE phase and can no longer race on the shared global config.
The FE reset logic itself is correct; this is purely a test-isolation fix. Same
design exists on apache/master; forward-port there too.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…only_scan debug_point cases

These 3 cases were cherry-picked from master (apache#63859). The session
variable enable_condition_cache (condition cache feature) does not exist
on branch-4.0, so 'set enable_condition_cache=false' fails with
'Unknown system variable'. Since the feature is absent, the branch is
already in the cache-disabled state the test expects, so removing the
line is a semantic no-op and restores the cases on this branch.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
@morningman
morningman force-pushed the tc-198126-backports branch from c2254f3 to d58d717 Compare June 15, 2026 12:59
@morningman

Copy link
Copy Markdown
Contributor Author

run buildall

@hello-stephen

Copy link
Copy Markdown
Contributor

FE UT Coverage Report

Increment line coverage 0.00% (0/7) 🎉
Increment coverage report
Complete coverage report

morningman and others added 5 commits June 16, 2026 07:07
…audit_log_behavior

The audit_log query_id column is createVarchar(Config.label_regex_length)
(default 128), but the expected .out still encoded the old varchar(48).
Updated the single drifted column; stmt_type stays varchar(48) (literal width).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…compaction_with_sparse_limit

The session-variable fuzzer randomized default_variant_max_subcolumns_count to
a small value, which diverts nested field v['b'] into the variant sparse column;
that path reads empty after cumulative compaction on this branch, so sql_33
returned empty. Pin it to 2048 (the FE default the .out was generated under) so
all nested paths stay typed subcolumns and the case is deterministic.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
….checkTaskTimeout

checkTaskTimeout asserted on the first visible task, but a just-scheduled task
(txnId == -1) can still carry the timeout from a previous schedule round before
the adaptive timeout converges, causing a flaky expected:3600/actual:100 race.
Skip transient txnId == -1 tasks and poll until a stable task carries the
expected timeout, failing with a clear message on timeout.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…ound-trip in check_before_quit

A property-less variant column renders bare 'variant' only when
default_variant_max_subcolumns_count == 0 (VariantType.toSql), and the recreate
parser bakes the current session default into the column. The per-connection
fuzzer randomized these defaults, making the CREATE -> recreate -> show-create
round-trip non-idempotent for 7 variant tables. Pin the two fuzzed variant
session defaults to 0 in the check connection.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…s the level2 freshness gate

In TimeSeriesCumulativeCompactionPolicy::pick_input_rowsets the 24h freshness
gate skipped freshly-created level1 rowsets before the time_series_level2_file_count
debug point could collect them, so the debug point (used by
test_time_series_compaction_level2 to force a level-2 merge) never fired and the
tablet kept 11 rowsets instead of 2. Add the debug point as a guard on the
freshness gate. No production impact: with debug points disabled is_enable()
returns false, so the extra condition is always true and behavior is unchanged.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@morningman

Copy link
Copy Markdown
Contributor Author

run buildall

…t index tracking (apache#63666)

Backport of apache#63666 (commit 2ddf97a).

ANN range search execution state was stored on shared VExpr roots.
VExprContext clones share the root expression, so a segment that executed
ANN range search could leak that state into another segment without an ANN
index and incorrectly remove the common expression. ANN range search also
mixed schema column indexes with storage column ids when updating common
expression index status, so remapped schemas failed to mark the source slot
expression as evaluated. This patch returns ANN execution state through the
current evaluation call, stores ANN root bitmap in the current segment
IndexContext, and updates slot index status by source column index.

Adapted to 4.0: this branch predates the enable_result_cache parameter, so
that parameter is omitted from the ported signatures; source paths and test
conventions are adjusted accordingly.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@hello-stephen

Copy link
Copy Markdown
Contributor

BE Regression && UT Coverage Report

Increment line coverage 0.00% (0/2) 🎉

Increment coverage report
Complete coverage report

Category Coverage
Function Coverage 57.72% (20613/35711)
Line Coverage 40.47% (201544/497957)
Region Coverage 37.46% (161746/431834)
Branch Coverage 38.03% (68818/180961)

1 similar comment
@hello-stephen

Copy link
Copy Markdown
Contributor

BE Regression && UT Coverage Report

Increment line coverage 0.00% (0/2) 🎉

Increment coverage report
Complete coverage report

Category Coverage
Function Coverage 57.72% (20613/35711)
Line Coverage 40.47% (201544/497957)
Region Coverage 37.46% (161746/431834)
Branch Coverage 38.03% (68818/180961)

morningman and others added 3 commits June 16, 2026 10:27
…e paths to deflake hit/read count checks

information_schema.file_cache_statistics reports one row per (cache_path,
metric_name): the BE iterates every cache instance and a given data file is
routed to exactly ONE instance via hash(filename) % num_paths. The tests read
each metric with a bare `... limit 1`, so they inspect a single arbitrary path's
counter, which need not be the path the query's data file routed to. With >1
file_cache_path this made total_hit_counts/total_read_counts assertions flaky
(the inspected path never moved while the routed path did), e.g.
test_file_cache_statistics failing with "total_hit_counts did not increase"
(4499 -> 4499) on a 2-path backend.

- test_file_cache_statistics: read every metric via
  SUM(CAST(METRIC_VALUE AS DOUBLE)) across all paths instead of `limit 1`, and
  replace the fixed Thread.sleep loops with Awaitility polling (total_*_counts
  are live bvar reads needing no wait; hits_ratio*/queue-curr are republished by
  the background monitor and are polled up to a couple of intervals). The
  counter-increase check re-runs the just-cached query inside the poll so a
  transient miss/eviction self-heals.
- test_file_cache_query_limit: sum total_hit_counts/total_read_counts across
  paths via a cacheMetricSum helper. Its normal_queue/queryCacheCapacity logic
  is intentionally left per-instance, as file_cache_query_limit_percent is
  derived from a single path's brpc file_cache_capacity.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…oad_adaptive_param restore phase

The restore-phase checkTaskTimeout("100") is flaky and timed out after 60s
(build 970376). Root cause is observability, not a product bug: a routine load
task's adaptive timeout is only (re)computed when the task is actually scheduled
WITH data to consume (updateAdaptiveTimeout runs after the hasMoreDataToConsume
gate in RoutineLoadTaskScheduler). Once a job drains its data it reaches EOF and
the renewed task stays idle with txnId == -1, inheriting the timeout from the
previous schedule round. So when the single restore batch is consumed atomically
by one task that still carries the isEof=false inertia from the debug-on phase
(timeout 3600), the EOF timeout 100 is never computed on any task, and
checkTaskTimeout's "txnId != -1 && timeout == 100" condition can never be met.

Add checkTaskTimeoutWithData, which feeds a small batch each poll round to force
an isEof task to be scheduled and recompute the timeout, and reads the value
without skipping txnId == -1 (after EOF the converged value settles on the idle
task). Use it for the restore phase; leave checkTaskTimeout (increase phase,
where the converged value lives on the running task) untouched.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@morningman

Copy link
Copy Markdown
Contributor Author

run buildall

@hello-stephen

Copy link
Copy Markdown
Contributor

FE UT Coverage Report

Increment line coverage 0.00% (0/7) 🎉
Increment coverage report
Complete coverage report

morningman and others added 2 commits June 16, 2026 15:49
…OCKS count

The BLOCKS column of information_schema.sql_block_rule_status is a SUM
aggregated across all alive FEs (SchemaTable declares it with
SchemaTableAggregateType.SUM and the table is fetch-all-FE), while each FE
keeps its own non-replicated in-memory block counter. A single blocked SELECT
is planned on exactly one FE and increments that FE's counter once, so on a
multi-FE cluster a stray non-zero counter on another FE makes the cross-FE SUM
exceed 1 and fails assertEquals("1", BLOCKS).

Set fetch_all_fe_for_system_table=false before reading the status table so the
scan reads only the local connection FE (the one that ran the blocked query),
making BLOCKS deterministically 1.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
In the testMultiFrontends thread, after fe1 populates the sql cache for
`select * from test_use_plan_cache18`, the thread connected to fe2 and asserted
assertNoCache for the same query. That assumes per-FE cache isolation, but the
sql cache result is held on the shared BE (the FE picks the cache BE by a
deterministic hash of the query), so fe2 can legitimately serve the same query
from cache without having executed it locally -- making the negative assertion
inherently racy (it is also the only assertion in the suite not wrapped in the
CanRetryException retry path).

Remove the fe2 assertNoCache and keep the meaningful check that the cache is
usable from a second FE (select + assertHasCache).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@morningman

Copy link
Copy Markdown
Contributor Author

run buildall

@hello-stephen

Copy link
Copy Markdown
Contributor

BE UT Coverage Report

Increment line coverage 65.96% (31/47) 🎉

Increment coverage report
Complete coverage report

Category Coverage
Function Coverage 53.33% (19454/36478)
Line Coverage 36.46% (181877/498839)
Region Coverage 33.05% (141302/427523)
Branch Coverage 33.92% (61162/180334)

@hello-stephen

Copy link
Copy Markdown
Contributor

BE Regression && UT Coverage Report

Increment line coverage 89.36% (42/47) 🎉

Increment coverage report
Complete coverage report

Category Coverage
Function Coverage 72.97% (26058/35709)
Line Coverage 56.32% (280448/497965)
Region Coverage 54.14% (233800/431841)
Branch Coverage 55.74% (100863/180967)

morningman and others added 5 commits June 16, 2026 18:24
…l_read_on_limit to fix async-report race

The BE reports the detailed execution profile to FE asynchronously, after
the query result has returned to the client and the FE coordinator is torn
down. The fixed Thread.sleep(500) keeps racing the report under CI load:
the profile fetched too early has an empty MergedProfile (no operators), so
MaxScanConcurrency is absent and the assertion fails. Mirror the sibling
scanner_profile fix and poll with Awaitility until MaxScanConcurrency lands
before evaluating.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…istics_ready to deflake partition_curd_union_rewrite

Root cause: after the inserts at lines 193/207 (and the DROP PARTITION at 220),
the six mv_rewrite_success(...) calls hard-asserted the MV was CBO-chosen
('.mv_10086 chose') without the is_partition_statistics_ready guard that the
pre-mutation calls (183-188) and both sibling suites use. The partition-union
rewrite does succeed, but BE per-partition row-count stats are reported
asynchronously; within the fixed sleep the new partition's stats are still 0
(selectedPartitionsRowCount=0.0), so CBO costs the union plan ~0.35 above the
direct plan and emits 'not chose' -> flaky failure (CloudP0 970791, line 212).

Solution: pass is_partition_statistics_ready(db, ["lineitem","orders",mv_name])
to the six post-mutation calls, matching the file's own pre-mutation pattern and
partition_mv_rewrite / union_rewrite_grace_big. When stats are not yet ready the
check degrades to chose-or-not-chose; the following compare_res(...) calls still
verify rewrite correctness, so intent is preserved.

Tests: existing suite is the test (CloudP0 e2e, CI-gated). TEST-only, no product
change.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…n prune_bucket_with_bucket_shuffle_join

Root cause: the second extractFragment asserts RIGHT OUTER JOIN(BUCKET_SHUFFLE)
under the new distribute planner, but the bucket-shuffle downgrade heuristic
ChildrenPropertiesRegulator.isBucketShuffleDownGrade
(totalBucketNum < backEndNum*paraNum*0.8) fires on the CloudP0 agent: the left
side prunes to 1 partition x 10 buckets = 10, backEndNum=1, and with the default
parallel_pipeline_task_num=0 paraNum auto-derives to 16 on the 32-core BE, so
10 < 1*16*0.8 = 12.8 -> downgrade -> PARTITIONED. The join is then labeled
PARTITIONED, never BUCKET_SHUFFLE, so all 120 retries fail (~128s, muted).
This became reachable after apache#56279 (302ba2e) replaced the old
Math.min(10, backEndNum*paraNum) cap with the *0.8 formula; the var is also
fuzzy, an additional flake source.

Solution: set parallel_pipeline_task_num=1 in the second-phase multi_sql so
paraNum=1 and the threshold becomes 10 < 0.8 (false) -> no downgrade ->
BUCKET_SHUFFLE kept deterministically, independent of BE core count and fuzz.
Bucket pruning (tablet<20), exchangeNum==1 and result correctness are unaffected.

Tests: existing suite is the test (CloudP0 e2e, CI-gated). TEST-only, no product
change; apache#56279's formula is intentional and left as-is.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…ge_search pending apache#64082

test_routine_load_adaptive_param: the txn-timeout check raced a live routine-load
transaction (poll SHOW ROUTINE LOAD TASK until txnId != -1, then SHOW TRANSACTION).
A small-batch routine-load txn begins and commits in well under the 1s poll interval,
so the txnId != -1 window is sub-second and the poll consistently sampled the idle gap
(62/62 polls saw txnId == -1 in build 970793, while versions advanced ~1/s -- the
product was healthy). Rewrite checkTxnTimeoutMatchesTaskTimeout (same signature) to
join on the task UUID (SHOW ROUTINE LOAD TASK col[0] == the FE transaction label set
by RoutineLoadTaskInfo.beginTxn) and read the timeout from the committed/visible
transaction via SHOW TRANSACTION WHERE label, whose timeoutMs is persisted and
retained long after commit -- no live-txn race.

ann_range_search_pushdown_regression: disable the case (wrap the body in a block
comment; the suite becomes a no-op). It builds a mixed indexed/non-indexed IVF scan by
inserting rowsets smaller than nlist and relies on the BE skipping ANN index build for
under-sized segments, which comes from PR apache#64082 (not backported to this branch).
Without it the single-row INSERT fails at segment finalize with faiss 'nx >= k'.
Re-enable after backporting apache#64082.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@morningman

Copy link
Copy Markdown
Contributor Author

run buildall

@hello-stephen

Copy link
Copy Markdown
Contributor

FE UT Coverage Report

Increment line coverage 0.00% (0/7) 🎉
Increment coverage report
Complete coverage report

…tead of wall-clock sleep

testAutoProfile mocked getQueryBeginTime() with result=System.currentTimeMillis(),
which JMockit freezes at record time, while Profile.updateSummary computes the query
duration against the real wall clock captured in markQueryFinished(). The first case
slept 899ms against a 1000ms threshold, leaving only ~101ms of slack; under CI load
(sleep oversleep / GC / scheduling) the measured duration reached >=1000ms, so the
profile was kept instead of removed and the line-70 assertNull failed.

Make the duration deterministic: drop JMockit and both Thread.sleep calls and set
queryBeginTime directly via SummaryProfile.setQueryBeginTime() (matching the sibling
ProfileManagerTest.getProfileByOrder pattern). Case 1 begins "now" (duration ~0 <
1000 -> removed); case 2 begins 60s ago (duration ~60s >= 500 -> kept). Both keep a
~60s margin that wall-clock jitter cannot flip while still exercising the real
durationMs < executionProfiles.size()*autoProfileDurationMs branch.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@hello-stephen

Copy link
Copy Markdown
Contributor

BE UT Coverage Report

Increment line coverage 65.96% (31/47) 🎉

Increment coverage report
Complete coverage report

Category Coverage
Function Coverage 53.33% (19454/36478)
Line Coverage 36.46% (181884/498839)
Region Coverage 33.09% (141468/427523)
Branch Coverage 33.92% (61173/180334)

@hello-stephen

Copy link
Copy Markdown
Contributor

BE Regression && UT Coverage Report

Increment line coverage 91.49% (43/47) 🎉

Increment coverage report
Complete coverage report

Category Coverage
Function Coverage 71.56% (25554/35709)
Line Coverage 54.44% (271081/497965)
Region Coverage 52.12% (225067/431841)
Branch Coverage 53.50% (96815/180967)

@morningman

Copy link
Copy Markdown
Contributor Author

run buildall

@hello-stephen

Copy link
Copy Markdown
Contributor

BE UT Coverage Report

Increment line coverage 65.96% (31/47) 🎉

Increment coverage report
Complete coverage report

Category Coverage
Function Coverage 53.33% (19455/36478)
Line Coverage 36.46% (181864/498839)
Region Coverage 33.03% (141214/427523)
Branch Coverage 33.91% (61153/180334)

@hello-stephen

Copy link
Copy Markdown
Contributor

FE UT Coverage Report

Increment line coverage 0.00% (0/7) 🎉
Increment coverage report
Complete coverage report

@hello-stephen

Copy link
Copy Markdown
Contributor

BE Regression && UT Coverage Report

Increment line coverage 91.49% (43/47) 🎉

Increment coverage report
Complete coverage report

Category Coverage
Function Coverage 71.40% (25496/35709)
Line Coverage 54.31% (270452/497965)
Region Coverage 51.99% (224497/431841)
Branch Coverage 53.32% (96492/180967)

@morningman
morningman merged commit 78454d9 into apache:branch-4.0 Jun 17, 2026
28 of 32 checks passed
yiguolei pushed a commit that referenced this pull request Jun 17, 2026
…kport subset of #64525) (#64597)

## What problem does this PR solve?

Stabilizes the **branch-4.1 Cloud-P0** regression pipeline by
back-porting the
relevant, **test-only** subset of branch-4.0 #64525 (which already
stabilized
the 4.0 P0/Cloud-P0 pipeline). These suites are currently
muted-but-still-failing
on 4.1 Cloud-P0; each commit deflakes one case so it can later be
un-muted.

Cases addressed (failure → fix):
- **scanner_profile** — hard-coded `actualRows=9` assert (fails when
tablets prune to <9 rows) → assert `actualRows ∈ [1,9]` via robust
regex, and poll until the async execution profile lands.
- **temp_table** — `assertEquals(show_tablets.size(), 3)` assumed 1
replica; on the 3-replica cloud cluster SHOW TABLETS returns 3×3=9 rows
→ derive replica count robustly (the old `/:(\d+)/` regex missed the
space in `tag.location.default: 3`).
- **insert_group_commit_into_max_filter_ratio** — group-commit async
count race.
- **adaptive_pipeline_task_serial_read_on_limit** — poll until the
async-reported profile is complete.
- **prune_bucket_with_bucket_shuffle_join** — pin
`parallel_pipeline_task_num=1` so bucket-shuffle plan is deterministic.

All changes are under `regression-test/` (no FE/BE code), so no
compilation impact.

## Cherry-picked from branch-4.0 #64525 (with `-x` provenance)
- `[fix](test) fix scanner_profile actualRows regex (partial backport of
#64238)`
- `[fix](test) make test_temp_table replica detection robust`
- `[fix](case) fix insert_group_commit_into_max_filter_ratio`
- `[fix](test) poll for complete profile in scanner_profile`
- `[fix](test) poll for complete profile in
adaptive_pipeline_task_serial_read_on_limit`
- `[fix](test) pin parallel_pipeline_task_num=1 to keep bucket shuffle
in prune_bucket_with_bucket_shuffle_join`

## Deliberately NOT included (follow-up)
- **ANN index-only-scan rework** (#64525 replaces
`ann_index_only_scan*.groovy` with debug-point variants) — needs
confirmation the new debug points exist on 4.1; deferred to a separate
PR.
- **time_series compaction debug-point** — touches BE
(`cumulative_compaction_time_series_policy.cpp`), needs a compile;
deferred.
- **`skip temp_table_p0/test_temp_table.groovy`** — intentionally
omitted; we keep the case running rather than skipping it, to confirm
the robust assert is sufficient on 4.1.

## Release note
None

🤖 Generated with [Claude Code](https://claude.com/claude-code)

---------

Co-authored-by: morningman <yunyou@selectdb.com>
Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Co-authored-by: meiyi <meiyi@selectdb.com>
yiguolei pushed a commit that referenced this pull request Jun 17, 2026
…ug-point tests (backport subset of #64525) (#64603)

## What problem does this PR solve?

Back-ports the **ANN index-only-scan test rework** from branch-4.0
#64525 to
branch-4.1. On 4.1 Cloud-P0 the two ann cases are muted-but-flaky
because they
assert on **profile scan-bytes equality**, which is non-deterministic.

This rework (matching 4.0) **removes the flaky Cloud-P0 cases**
(`ann_index_only_scan`, `ann_index_only_scan_distance_expr`,
`ann_index_only_scan_metric_direction` + its `.out`) and replaces the
coverage
with **deterministic `nonConcurrent` debug-point tests** that force the
index-only path via
`GetDebugPoint().enableDebugPointForAllBEs("segment_iterator._read_columns_by_index",
...)`.

Verified the debug point `segment_iterator._read_columns_by_index`
already
exists on branch-4.1 (`be/src/storage/segment/segment_iterator.cpp`),
and the
ANN range-search product fix (#63965) is already on 4.1, so the new
tests are
runnable here. **Test-only change (no FE/BE code).**

Complements #64597 (the other Cloud-P0 deflake backports).

## Cherry-picked from branch-4.0 #64525 (with `-x` provenance)
- `[test](regression) Add debug point ANN index-only scan test (#63859)`
- `[fix](test) drop unsupported enable_condition_cache var in
ann_index_only_scan debug_point cases`
- `[fix](test) drop unsupported enable_condition_cache var in
ann_range_search cases`

## Not included (separate follow-up)
- `[fix](compaction) let time_series_level2_file_count debug point
bypass …` — touches BE
(`cumulative_compaction_time_series_policy.cpp`, which moved to
`be/src/storage/compaction/`
on 4.1 due to the BE dir refactor #61595), so it needs a manual port + a
remote compile
  verification before submitting; handled separately.

## Release note
None

🤖 Generated with [Claude Code](https://claude.com/claude-code)

---------

Co-authored-by: zhiqiang <seuhezhiqiang@163.com>
Co-authored-by: morningman <yunyou@selectdb.com>
Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
yiguolei pushed a commit that referenced this pull request Jun 17, 2026
…onger maintained, backport of #64525) (#64607)

## What problem does this PR solve?

Back-ports the `skip temp_table_p0/test_temp_table.groovy` decision from
branch-4.0 #64525 to branch-4.1. The temporary-table feature is **no
longer
maintained**, so the suite is skipped (early `return`) rather than kept
as a
chronically-flaky Cloud-P0 case (it is the highest-frequency muted
failure on
branch-4.1 Cloud-P0).

```groovy
suite('test_temp_table', 'p0') {
    if (true) {
        // temp table feature is no longer mantains. skip this case
        return
    }
    ...
```

Test-only change.

## Cherry-picked from branch-4.0 #64525 (with `-x` provenance)
- `skip temp_table_p0/test_temp_table.groovy`

## Note
Supersedes the temp_table replica-detection deflake that is part of
#64597 — once
this lands, that commit in #64597 becomes dead code (unreachable after
the early
return) and can be dropped from #64597.

## Release note
None

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-authored-by: morningman <yunyou@selectdb.com>
yiguolei pushed a commit that referenced this pull request Jun 18, 2026
…/External flaky cases (test-only backport rest of #64525) (#64613)

## What problem does this PR solve?

Back-ports the **remaining test-only** subset of branch-4.0 #64525 to
branch-4.1,
covering the cases still flaky/red across branch-4.1 **Cloud-P0 / P0 /
NonConcurrent /
External** pipelines (the first three subsets are #64597, #64603,
#64607). All changes
are under `regression-test/` — **no FE/BE code, no compile impact**.

Cases addressed (and where they fail today on branch-4.1):
- **query64** (`shape_check.tpcds_sf100/sf1000 .../query64`) — currently
an **un-muted P0 red**; #64525 `ignore`s it.
- **test_colocate_join_of_column_order** — muted on Cloud-P0.
- **test_audit_log_behavior** — muted on NonConcurrent (query_id width).
- **test_routine_load_adaptive_param** + `RoutineLoadTestUtils` — muted
on NonConcurrent/P0 (timeout convergence / drive-data deflakes).
- **parse_sql_from_sql_cache** (drop racy cross-FE assertNoCache),
**test_sql_block_rule_status** (single-FE read) — muted on P0.
- **test_file_cache_statistics** (sum across cache paths),
**test_hive_ctas_to_doris** — muted on External.
- **test_variant_compaction_with_sparse_limit** (pin
`default_variant_max_subcolumns_count` so the session-var fuzzer can't
shrink it), **check_before_quit** (pin variant session defaults) —
variant deflakes.
- **partition_curd_union_rewrite** (guard mv-chosen with
partition-stats-ready), **test_f_delete_publish_skip_read** (wait for
delete visibility), backup/restore `restore_reset_index_id`
serialization.

## Deliberately NOT included
- `[fix](compaction) time_series_level2_file_count debug point` —
touches BE (`cumulative_compaction_time_series_policy.cpp`), needs a
manual port (`olap`→`storage` on 4.1) + remote compile; separate PR.
- `[fix](test) deflake AutoProfileTest` — an FE UT
(`fe/fe-core/src/test/.../AutoProfileTest.java`), separate FE-UT
pipeline; out of scope for this regression-test PR.
- `skip test_parquet_join_runtime_filter` — its stated reason is
**4.0-specific** ("4.0 does not support this feature"); the feature
exists on 4.1 and the test passes there, so skipping it on 4.1 would be
wrong.

## Release note
None

🤖 Generated with [Claude Code](https://claude.com/claude-code)

---------

Co-authored-by: morningman <yunyou@selectdb.com>
Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
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.

6 participants