Skip to content

test(search): surface the real cause behind ranking-IT poll timeouts - #30250

Merged
mohityadav766 merged 3 commits into
mainfrom
fix/search-ranking-token-entropy
Jul 21, 2026
Merged

test(search): surface the real cause behind ranking-IT poll timeouts#30250
mohityadav766 merged 3 commits into
mainfrom
fix/search-ranking-token-entropy

Conversation

@mohityadav766

@mohityadav766 mohityadav766 commented Jul 20, 2026

Copy link
Copy Markdown
Member

Describe your changes:

Scope narrowed after rebasing on latest main. When this PR was opened it also rewrote RankingSupport.uniqueTerm() to be collision-free. Since then #30120 ("Stabilize integration-test CI") landed a complementary fix for the same ranking-tie flakiness — it makes the filler values in seeded entity names use a disjoint alphabet (EntitySeeder.tokenFreeValue = "aa"+hex) so they can't ngram-match the "zz"+[g-v] query token. That supersedes the token rewrite here, so I merged main and resolved to #30120's approach, dropping the now-redundant uniqueTerm change and its unit test. What remains is the one piece #30120 did not touch.

Surface the real cause behind SearchEntityRankingIT poll timeouts.

RankingSupport.awaitTrue reports every timeout as a flat "not indexed in time". ignoreExceptions() is correct while a document is still being indexed, but discarding the exception makes a condition that throws on every poll — a 4xx, a bad index name, a deserialization error — indistinguishable from genuine indexing lag. Both surface only as "not indexed in time", which is exactly the message dominating several ranking failures in the collate CI runs that prompted this.

awaitOrReason() keeps the transient-error tolerance but retains and reports the last polling error alongside the timeout; SearchEntityRankingIT's two call sites now include it in their failure text. awaitTrue() is retained unchanged for the settings tests that legitimately want a boolean skip.

Net change over main: +awaitOrReason in RankingSupport, and awaitTrue → awaitOrReason at the two SearchEntityRankingIT sites. Nothing else.

How I tested

Type of change:

  • Bug fix

Checklist:

  • I have read the CONTRIBUTING document.
  • I have commented on my code, particularly in hard-to-understand areas.

Greptile Summary

This PR improves timeout diagnostics in search ranking integration tests. The main changes are:

  • Adds a polling helper that preserves the last exception.
  • Includes the timeout reason in ranking test failures.
  • Keeps the existing boolean polling helper for settings tests.

Confidence Score: 5/5

This looks safe to merge.

  • The latest changes are limited to integration-test failure diagnostics.
  • No blocking issues were found in the changed code.

Important Files Changed

Filename Overview
openmetadata-integration-tests/src/test/java/org/openmetadata/it/tests/search/RankingSupport.java Adds an Awaitility helper that returns timeout details and the last polling exception.
openmetadata-integration-tests/src/test/java/org/openmetadata/it/tests/search/SearchEntityRankingIT.java Uses the new helper at both ranking poll sites to produce more informative failures.

Reviews (3): Last reviewed commit: "Merge remote-tracking branch 'origin/mai..." | Re-trigger Greptile

…poll errors

SearchEntityRankingIT's "Tier1 > untagged on a text tie" case seeds two
documents with an identical displayName so their text scores are equal, then
asserts the Tier.Tier1 global term boost breaks the tie. The tie was not
actually exact.

RankingSupport.uniqueTerm() derived its token from TestNamespace.uniqueShortId(),
which is RUN_ID.substring(0,8) + methodHash + 4 random chars — only 4 of 16
characters vary within a test method. Every token minted for one test therefore
shared a 14-character prefix, and EntitySeeder.nameFor() places a sibling token
in each entity's name, so the query ngram-matched both documents' names by
differing amounts. That leaked a variable name.ngram / displayName.ngram
contribution into scores the case requires to be equal.

Measured against 1.13 (Tier1 boost 0.05, multiplier 1.05x): 3/25 inversions.
The noise ratio is bounded by roughly 1.17 because the ngram terms sit in the
"max plus 0.3 times others" bucket while displayName.keyword dominates, so
main's post-#29903 boost of 0.5 (1.5x) sits above the noise and never inverts
— the defect is present on main too, just out of range. Drawing the token from
its own full-entropy source removes the overlap at source rather than relying
on a boost margin to outweigh it.

Also stop reporting every awaitTrue timeout as "not indexed in time".
ignoreExceptions() is correct while polling a document that is still being
indexed, but discarding the exception made a condition that threw on every
poll indistinguishable from genuine indexing lag. awaitOrReason() keeps the
tolerance and reports the last error alongside the timeout.

RankingSupportTest covers both collision properties; it fails with a 14-char
shared prefix against the previous implementation.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Copilot AI review requested due to automatic review settings July 20, 2026 19:39

Copilot AI 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.

Copilot was unable to review this pull request because the user who requested the review has reached their quota limit.

@github-actions

Copy link
Copy Markdown
Contributor

❌ PR checklist incomplete

This PR cannot be merged until the following are addressed on its linked issue:

  • No GitHub issue is linked. Link an issue in the Development section of the PR (or add Fixes #12345 to the description). For a same-org cross-repo issue, add Fixes open-metadata/<repo>#123 to the description.

The fields live on the linked issue in the Shipping project (open the issue → right sidebar → Projects). After you set them, re-run this check (or push a commit) — issue/project changes do not re-trigger it automatically.

Maintainers can bypass this check by adding the skip-pr-checks label.

@github-actions

github-actions Bot commented Jul 20, 2026

Copy link
Copy Markdown
Contributor

🟡 Playwright Results — all passed (21 flaky)

✅ 4531 passed · ❌ 0 failed · 🟡 21 flaky · ⏭️ 95 skipped

Shard Passed Failed Flaky Skipped
🟡 Shard 1 434 0 6 16
✅ Shard 2 11 0 0 0
🟡 Shard 3 822 0 6 8
🟡 Shard 4 817 0 1 18
🟡 Shard 5 830 0 1 5
🟡 Shard 6 834 0 1 46
🟡 Shard 7 783 0 6 2
🟡 21 flaky test(s) (passed on retry)
  • Features/DataAssetRulesEnabled.spec.ts › Verify the Chart Entity Action items after rules is Enabled (shard 1, 1 retry)
  • Flow/TestConnectionModal.spec.ts › success state shows Done button and hides Edit Connection and Retry Test (shard 1, 1 retry)
  • Pages/Lineage/LineageRightPanel.spec.ts › Verify custom properties tab IS visible for supported type: chart (shard 1, 1 retry)
  • Pages/SearchSettings.spec.ts › Latest preview config wins when a superseded request resolves late (shard 1, 1 retry)
  • Pages/UserCreationWithPersona.spec.ts › Create user with persona and verify on profile (shard 1, 1 retry)
  • Flow/SearchRBAC.spec.ts › a fully denied user sees neither asset type when browsing (shard 1, 1 retry)
  • Features/ColumnBulkOperations.spec.ts › should clear individual filter and update URL (shard 3, 1 retry)
  • Features/ContextCenterArticles.spec.ts › Article listing search filters, clears, and shows empty state (shard 3, 1 retry)
  • Features/ContextCenterArticles.spec.ts › description: switching articles does not bleed unsaved content into next article (shard 3, 1 retry)
  • Features/ContextCenterMemories.spec.ts › clearing search restores the unfiltered list (shard 3, 1 retry)
  • Features/ContextCenterMemories.spec.ts › adding a linked asset in edit mode shows entity badge on the row (shard 3, 1 retry)
  • Features/ContextCenterMemories.spec.ts › typing the linked table name in the asset search returns it as a result (shard 3, 1 retry)
  • Features/SearchExport.spec.ts › Export queues a background job and downloads from the jobs tray (shard 4, 1 retry)
  • Flow/PersonaFlow.spec.ts › Set default persona for team should work properly (shard 5, 1 retry)
  • Pages/Entity.spec.ts › Domain Propagation (shard 6, 1 retry)
  • Pages/Glossary.spec.ts › Verify Glossary Term Deny Permission (shard 7, 1 retry)
  • Pages/Lineage/LineageFilters.spec.ts › Verify Impact Analysis service filter selection (shard 7, 1 retry)
  • Pages/Lineage/LineageRightPanel.spec.ts › Verify custom properties tab is NOT visible for pipelineService in platform lineage (shard 7, 1 retry)
  • Pages/Lineage/LineageRightPanel.spec.ts › Verify custom properties tab is NOT visible for apiService in platform lineage (shard 7, 1 retry)
  • Pages/TaskFormSettings.spec.ts › creates and updates a task form schema from settings (shard 7, 1 retry)
  • Pages/Users.spec.ts › Create and Delete user (shard 7, 1 retry)

📦 Download artifacts

How to debug locally
# Download playwright-test-results-<shard> artifact and unzip
npx playwright show-trace path/to/trace.zip    # view trace

pmbrull
pmbrull previously approved these changes Jul 21, 2026
#30120 ("Stabilize integration-test CI") landed a complementary fix for the same
ranking-tie flakiness this branch targeted: it makes the filler values in seeded
entity names use a disjoint alphabet (EntitySeeder.tokenFreeValue = "aa"+hex) so
they cannot ngram-match the "zz"+[g-v] query token. That supersedes this branch's
uniqueTerm() full-entropy change, so the merge resolves to #30120's token approach
(theirs) and drops the now-redundant uniqueTerm rewrite and RankingSupportTest.

What remains from this branch is the piece #30120 did not touch: awaitOrReason(),
which surfaces the last polling error instead of reporting every awaitTrue timeout
as a flat "not indexed in time". awaitTrue() is retained for the settings tests.
Copilot AI review requested due to automatic review settings July 21, 2026 06:05

Copilot AI 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.

Copilot was unable to review this pull request because the user who requested the review has reached their quota limit.

@mohityadav766 mohityadav766 changed the title test(search): make ranking tokens collision-free and stop swallowing poll errors test(search): surface the real cause behind ranking-IT poll timeouts Jul 21, 2026
@@ -110,14 +110,14 @@ private void evaluateCase(
String term = RankingSupport.uniqueTerm(ns);

@gitar-bot gitar-bot Bot Jul 21, 2026

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

⚠️ Bug: Merge reverts the entropy fix — token collision reintroduced

The merge commit (9f26c7d, the commit under review) reverted uniqueTerm from the branch's full-entropy source (UUID.randomUUID()) back to ns.uniqueShortId() and deleted its guarding test RankingSupportTest.java. Per the PR's own analysis, uniqueShortId() = RUN_ID.substring(0,8) + methodHash + 4 random chars, so within a single test method only 4 of 16 characters vary and every minted token shares a ~14-char prefix. Since seeders place a sibling uniqueTerm in each entity's displayName/name, a query for one case's token ngram-matches another case's document, leaking a variable displayName.ngram/name.ngram contribution into scores the tie-break case requires to be exactly equal — the exact ~12% inversion flakiness this PR set out to eliminate. The merge message claims main's #30120 token approach makes the rewrite "redundant", but TestNamespace.uniqueShortId() at HEAD still only varies in its last 4 chars, so the collision persists and no test remains to catch it. Restore the full-entropy token (and ideally the collision-property test).

Restore the full-entropy, method-independent token source so sibling tokens minted in the same test method no longer share a long prefix. Revert the callers in SearchEntityRankingIT to uniqueTerm() (no ns arg), re-add the UUID import and TERM_HEX_LENGTH constant, and consider restoring RankingSupportTest.:

static String uniqueTerm() {
    String hex = UUID.randomUUID().toString().replace("-", "").substring(0, 16);
    StringBuilder term = new StringBuilder("zz");
    for (int i = 0; i < hex.length(); i++) {
      term.append((char) ('g' + Character.digit(hex.charAt(i), 16)));
    }
    return term.toString();
}

Was this helpful? React with 👍 / 👎

Copilot AI review requested due to automatic review settings July 21, 2026 09:38

Copilot AI 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.

Copilot was unable to review this pull request because the user who requested the review has reached their quota limit.

@mohityadav766
mohityadav766 merged commit f67fbc0 into main Jul 21, 2026
80 of 83 checks passed
@mohityadav766
mohityadav766 deleted the fix/search-ranking-token-entropy branch July 21, 2026 13:07
@gitar-bot

gitar-bot Bot commented Jul 21, 2026

Copy link
Copy Markdown
Code Review ⚠️ Changes requested 0 resolved / 1 findings

Reintroduces token collisions by reverting the entropy fix in the merge commit, effectively breaking the ranking test stability. The integration tests now rely on insufficient random tokens instead of the intended UUID-derived source.

⚠️ Bug: Merge reverts the entropy fix — token collision reintroduced

📄 openmetadata-integration-tests/src/test/java/org/openmetadata/it/tests/search/RankingSupport.java:161-168 📄 openmetadata-integration-tests/src/test/java/org/openmetadata/it/tests/search/SearchEntityRankingIT.java:110 📄 openmetadata-integration-tests/src/test/java/org/openmetadata/it/tests/search/SearchEntityRankingIT.java:151

The merge commit (9f26c7d, the commit under review) reverted uniqueTerm from the branch's full-entropy source (UUID.randomUUID()) back to ns.uniqueShortId() and deleted its guarding test RankingSupportTest.java. Per the PR's own analysis, uniqueShortId() = RUN_ID.substring(0,8) + methodHash + 4 random chars, so within a single test method only 4 of 16 characters vary and every minted token shares a ~14-char prefix. Since seeders place a sibling uniqueTerm in each entity's displayName/name, a query for one case's token ngram-matches another case's document, leaking a variable displayName.ngram/name.ngram contribution into scores the tie-break case requires to be exactly equal — the exact ~12% inversion flakiness this PR set out to eliminate. The merge message claims main's #30120 token approach makes the rewrite "redundant", but TestNamespace.uniqueShortId() at HEAD still only varies in its last 4 chars, so the collision persists and no test remains to catch it. Restore the full-entropy token (and ideally the collision-property test).

Restore the full-entropy, method-independent token source so sibling tokens minted in the same test method no longer share a long prefix. Revert the callers in SearchEntityRankingIT to uniqueTerm() (no ns arg), re-add the UUID import and TERM_HEX_LENGTH constant, and consider restoring RankingSupportTest.
static String uniqueTerm() {
    String hex = UUID.randomUUID().toString().replace("-", "").substring(0, 16);
    StringBuilder term = new StringBuilder("zz");
    for (int i = 0; i < hex.length(); i++) {
      term.append((char) ('g' + Character.digit(hex.charAt(i), 16)));
    }
    return term.toString();
}
🤖 Prompt for agents
Code Review: Reintroduces token collisions by reverting the entropy fix in the merge commit, effectively breaking the ranking test stability. The integration tests now rely on insufficient random tokens instead of the intended UUID-derived source.

1. ⚠️ Bug: Merge reverts the entropy fix — token collision reintroduced
   Files: openmetadata-integration-tests/src/test/java/org/openmetadata/it/tests/search/RankingSupport.java:161-168, openmetadata-integration-tests/src/test/java/org/openmetadata/it/tests/search/SearchEntityRankingIT.java:110, openmetadata-integration-tests/src/test/java/org/openmetadata/it/tests/search/SearchEntityRankingIT.java:151

   The merge commit (9f26c7d6, the commit under review) reverted `uniqueTerm` from the branch's full-entropy source (`UUID.randomUUID()`) back to `ns.uniqueShortId()` and deleted its guarding test `RankingSupportTest.java`. Per the PR's own analysis, `uniqueShortId()` = `RUN_ID.substring(0,8)` + methodHash + 4 random chars, so within a single test method only 4 of 16 characters vary and every minted token shares a ~14-char prefix. Since seeders place a sibling `uniqueTerm` in each entity's displayName/name, a query for one case's token ngram-matches another case's document, leaking a variable `displayName.ngram`/`name.ngram` contribution into scores the tie-break case requires to be exactly equal — the exact ~12% inversion flakiness this PR set out to eliminate. The merge message claims main's #30120 token approach makes the rewrite "redundant", but `TestNamespace.uniqueShortId()` at HEAD still only varies in its last 4 chars, so the collision persists and no test remains to catch it. Restore the full-entropy token (and ideally the collision-property test).

   Fix (Restore the full-entropy, method-independent token source so sibling tokens minted in the same test method no longer share a long prefix. Revert the callers in SearchEntityRankingIT to uniqueTerm() (no ns arg), re-add the UUID import and TERM_HEX_LENGTH constant, and consider restoring RankingSupportTest.):
   static String uniqueTerm() {
       String hex = UUID.randomUUID().toString().replace("-", "").substring(0, 16);
       StringBuilder term = new StringBuilder("zz");
       for (int i = 0; i < hex.length(); i++) {
         term.append((char) ('g' + Character.digit(hex.charAt(i), 16)));
       }
       return term.toString();
   }

Options

Display: compact → Showing less information.

Comment with these commands to change the behavior for this request:

Compact
gitar display:verbose         

Was this helpful? React with 👍 / 👎 | Gitar

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

backend safe to test Add this label to run secure Github workflows on PRs

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants