Skip to content

Conversation

@Deepak-Kesavan
Copy link
Contributor

What

  • Fixed issues with word level confidence

Why

  • Its not working as expected.

How

Can this PR break any existing features. If yes, please list possible items. If no, please explain why. (PS: Admins do not merge the PR without this section filled)

  • No.

Database Migrations

Env Config

Relevant Docs

Related Issues or PRs

Dependencies Versions

Notes on Testing

Screenshots

Checklist

I have read and understood the Contribution Guidelines.

Deepak-Kesavan and others added 13 commits November 21, 2025 03:49
Add word-level confidence feature that extends the existing highlight functionality. This feature allows tracking confidence scores at the word level during extraction.

Key changes:
- Add enable_word_confidence field to CustomTool model
- Add word_confidence_postamble support for custom prompts
- Pass word_confidence flag through extraction and indexing pipelines
- Update SDK to preserve original text for post-processing
- Add dependency check to ensure word confidence requires highlight to be enabled
…ext parameter

- Updated post_process_fn type signature from Callable[[LLMResponseCompat, bool], ...]
  to Callable[[LLMResponseCompat, bool, str], ...] to match the actual call at line 500-502
- Addresses review comment: #1672 (comment)
- The highlight_data plugin's run() method already accepts the third parameter (original_text: str)
- Removed WORD_CONFIDENCE_DATA constant as it's not used in main repo's workflow manager
- The constant is only needed in unstract-cloud repo which has the rule engine
- Prompt studio code uses the string directly, which is appropriate
- Addresses review comment: #1672 (comment)
@coderabbitai
Copy link
Contributor

coderabbitai bot commented Nov 25, 2025

Summary by CodeRabbit

  • New Features

    • Added line-level confidence support for highlighted text extractions.
  • Bug Fixes

    • Improved confidence score calculation with enhanced fallback logic when primary confidence data is unavailable.
    • Enhanced data isolation during batch processing to prevent cross-prompt interference.

✏️ Tip: You can customize this high-level summary in your review settings.

Walkthrough

The changes refactor confidence data handling across frontend, backend, and worker layers. Loop-scoped alias variables prevent cross-prompt data mutations during output processing. Confidence computation adopts a multi-tier fallback strategy (word-level → highlight-derived → explicit), with new LLMWhisperer configuration support for line-level confidence extraction.

Changes

Cohort / File(s) Summary
Backend output processing
backend/prompt_studio/prompt_studio_output_manager_v2/output_manager_helper.py
Introduces loop-scoped alias variables (prompt_context, prompt_highlight_data, prompt_confidence_data, prompt_word_confidence_data, prompt_challenge_data) to isolate per-prompt data extraction and prevent cross-iteration mutations. Updates update_or_create_prompt_output call signatures to pass serialized and isolated prompt-specific data.
Frontend confidence computation
frontend/src/components/custom-tools/prompt-card/DisplayPromptResult.jsx
Adds extractConfidenceFromHighlightData() helper to recursively traverse highlight data and compute average confidence. Introduces getNestedValue() for nested access to word confidence data. Implements three-tier fallback: word-level confidence → highlight-derived average → explicit confidenceData, passed to handleSelectHighlight.
Frontend confidence simplification
frontend/src/components/custom-tools/prompt-card/PromptCard.jsx
Removes extractConfidenceFromHighlightData() helper and confidence averaging logic. Simplifies handleSelectHighlight to directly use confidenceData without fallback derivation.
SDK LLMWhisperer configuration
unstract/sdk1/src/unstract/sdk1/adapters/x2text/llm_whisperer_v2/src/constants.py
Adds new WhispererConfig.INCLUDE_LINE_CONFIDENCE constant to expand line-level confidence configuration options.
SDK LLMWhisperer parameter forwarding
unstract/sdk1/src/unstract/sdk1/adapters/x2text/llm_whisperer_v2/src/helper.py
Adds INCLUDE_LINE_CONFIDENCE entry to params dictionary in get_whisperer_params(), forwarded from extra_params.enable_highlight, enabling line confidence in whisper endpoint calls.
LLM post-processing signature
unstract/sdk1/src/unstract/sdk1/llm.py
Expands post_process_fn signature to accept third parameter (original_text). Updates type hint from Callable[[LLMResponseCompat, bool], ...] to Callable[[LLMResponseCompat, bool, str], ...] to match call sites.
Worker destination confidence extraction
workers/shared/workflow/destination_connector.py
Adds _extract_confidence_from_highlight_data() static helper to recursively extract average confidence from 5-element coordinate arrays. Implements three-tier fallback in _should_handle_hitl: word confidence → highlight-derived average → explicit confidence. Extends wrapped_result.metadata to include highlight_data and extracted_text alongside confidence fields for downstream evaluation.

Sequence Diagram(s)

sequenceDiagram
    participant OMH as Output Manager<br/>(Backend)
    participant DC as Destination<br/>Connector (Worker)
    participant Frontend as Frontend<br/>Component
    
    OMH->>OMH: Extract loop-scoped<br/>variables per prompt
    OMH->>OMH: Serialize context<br/>& challenge data
    OMH->>DC: Call with isolated<br/>prompt data
    
    DC->>DC: Extract confidence<br/>from highlight data
    DC->>DC: Apply 3-tier fallback:<br/>word → highlight → explicit
    DC->>DC: Populate metadata with<br/>all confidence variants
    DC->>Frontend: Return wrapped result
    
    Frontend->>Frontend: Receive confidence
    Frontend->>Frontend: Apply nested word<br/>confidence lookup
    Frontend->>Frontend: Fallback to highlight<br/>or explicit confidence
    Frontend->>Frontend: Pass to<br/>handleSelectHighlight
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~50 minutes

  • workers/shared/workflow/destination_connector.py: New _extract_confidence_from_highlight_data() method and three-tier fallback logic require careful verification of recursion depth, edge cases (null/undefined), and integration with existing metadata flow.
  • frontend/src/components/custom-tools/prompt-card/DisplayPromptResult.jsx: getNestedValue() nested path parsing with array index support and confidence averaging logic need validation across coordinate array structures.
  • backend/prompt_studio/prompt_studio_output_manager_v2/output_manager_helper.py: Loop-scoped variable isolation must be verified to prevent accidental data leakage between prompt iterations and ensure per-prompt serialization correctness.
  • Cross-layer integration: Verify that the multi-tier fallback strategy (word → highlight → explicit) is consistently applied across backend, worker, and frontend layers and that metadata propagation carries all required confidence variants downstream.

Pre-merge checks and finishing touches

❌ Failed checks (2 warnings)
Check name Status Explanation Resolution
Description check ⚠️ Warning The description covers most required sections from the template but is incomplete: 'How' section is empty, and critical details like testing notes, related issues, and changelog information are missing. Complete the 'How' section explaining the specific implementation approach, and add details about testing strategy and any related issue references to ensure reviewers understand the full context.
Docstring Coverage ⚠️ Warning Docstring coverage is 55.56% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
✅ Passed checks (1 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly identifies the specific issue being fixed (word level confidence) and includes the ticket reference (UN-3008), making it concise and directly related to the changeset.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch UN-3008-word-level-confidence

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

🧹 Nitpick comments (3)
workers/shared/workflow/destination_connector.py (1)

224-266: Refactor to reduce cognitive complexity and add recursion protection.

SonarCloud flags cognitive complexity of 28 (allowed: 15). The nested function with multiple conditionals is hard to follow. Additionally, deeply nested highlight data could cause stack overflow.

Consider refactoring to reduce nesting and add a depth limit:

 @staticmethod
-def _extract_confidence_from_highlight_data(data: Any) -> float | None:
+def _extract_confidence_from_highlight_data(
+    data: Any, max_depth: int = 50
+) -> float | None:
     """Extract confidence from 5th element of highlight data coordinate arrays.
-
-    Recursively searches through nested arrays/objects to find coordinate arrays
-    with 5 elements where the 5th element (index 4) is the confidence score.
-
-    Args:
-        data: Highlight data structure (can be nested arrays/dicts)
-
-    Returns:
-        Average confidence score if found, None otherwise
     """
     if not data:
         return None

     confidence_values = []

-    def extract_from_array(arr):
-        if isinstance(arr, list):
-            for item in arr:
-                if isinstance(item, list):
-                    # Check if this is a coordinate array with 5 elements
-                    if len(item) >= 5 and isinstance(item[4], (int, float)):
-                        confidence_values.append(float(item[4]))
-                    else:
-                        # Recursively check nested arrays
-                        extract_from_array(item)
-                elif isinstance(item, dict):
-                    # Recursively check objects
-                    for val in item.values():
-                        extract_from_array(val)
-        elif isinstance(arr, dict):
-            for val in arr.values():
-                extract_from_array(val)
+    def extract_recursive(arr, depth: int = 0):
+        if depth > max_depth:
+            return
+        if isinstance(arr, list):
+            # Check if this is a coordinate array with 5 elements
+            if len(arr) >= 5 and isinstance(arr[4], (int, float)):
+                confidence_values.append(float(arr[4]))
+                return
+            for item in arr:
+                extract_recursive(item, depth + 1)
+        elif isinstance(arr, dict):
+            for val in arr.values():
+                extract_recursive(val, depth + 1)

-    extract_from_array(data)
+    extract_recursive(data)

     if confidence_values:
         return sum(confidence_values) / len(confidence_values)
-
     return None
frontend/src/components/custom-tools/prompt-card/DisplayPromptResult.jsx (2)

138-138: Prefer replaceAll() for clarity.

While replace() with the global flag works, replaceAll() more explicitly conveys the intent to replace all occurrences.

Apply this diff:

-      const normalized = path.replace(/\[(\d+)\]/g, ".$1");
+      const normalized = path.replaceAll(/\[(\d+)\]/g, ".$1");

147-166: Consider adding comments to clarify the multi-tier fallback strategy.

The confidence computation uses a three-tier fallback (word-level → highlight-derived → explicit), but this strategy isn't immediately apparent from the code. Adding inline comments would improve maintainability.

Consider adding clarifying comments:

      let confidence;
+     // Tier 1: Try word-level confidence (most granular)
      if (shouldUseWordConfidence && wordConfidenceData) {
        const wordConfidence = getNestedValue(wordConfidenceData, key);
        if (wordConfidence && typeof wordConfidence === "object") {
          const values = Object.values(wordConfidence).filter(
            (v) => typeof v === "number"
          );
          if (values.length > 0) {
            const sum = values.reduce((acc, val) => acc + val, 0);
            confidence = sum / values.length;
          }
        }
      }

+     // Tier 2: Extract from highlight data coordinate arrays (5th element)
+     // Tier 3: Fall back to explicit confidence data
      if (confidence === undefined) {
        const extractedConfidence = extractConfidenceFromHighlightData(
          highlightData[key]
        );
        confidence = extractedConfidence ?? confidenceData?.[key];
      }
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

Cache: Disabled due to Reviews > Disable Cache setting

Knowledge base: Disabled due to Reviews -> Disable Knowledge Base setting

📥 Commits

Reviewing files that changed from the base of the PR and between df86a79 and 7d16e50.

📒 Files selected for processing (7)
  • backend/prompt_studio/prompt_studio_output_manager_v2/output_manager_helper.py (2 hunks)
  • frontend/src/components/custom-tools/prompt-card/DisplayPromptResult.jsx (2 hunks)
  • frontend/src/components/custom-tools/prompt-card/PromptCard.jsx (1 hunks)
  • unstract/sdk1/src/unstract/sdk1/adapters/x2text/llm_whisperer_v2/src/constants.py (1 hunks)
  • unstract/sdk1/src/unstract/sdk1/adapters/x2text/llm_whisperer_v2/src/helper.py (1 hunks)
  • unstract/sdk1/src/unstract/sdk1/llm.py (1 hunks)
  • workers/shared/workflow/destination_connector.py (2 hunks)
🧰 Additional context used
🧬 Code graph analysis (4)
unstract/sdk1/src/unstract/sdk1/adapters/x2text/llm_whisperer_v2/src/helper.py (1)
unstract/sdk1/src/unstract/sdk1/adapters/x2text/llm_whisperer_v2/src/constants.py (1)
  • WhispererConfig (50-77)
frontend/src/components/custom-tools/prompt-card/DisplayPromptResult.jsx (1)
frontend/src/components/custom-tools/document-manager/DocumentManager.jsx (1)
  • highlightData (108-108)
unstract/sdk1/src/unstract/sdk1/llm.py (1)
unstract/sdk1/src/unstract/sdk1/utils/common.py (1)
  • LLMResponseCompat (120-138)
workers/shared/workflow/destination_connector.py (2)
backend/adapter_processor_v2/models.py (1)
  • metadata (161-171)
backend/api_v2/api_deployment_views.py (1)
  • get (139-189)
🪛 GitHub Check: SonarCloud Code Analysis
frontend/src/components/custom-tools/prompt-card/DisplayPromptResult.jsx

[failure] 89-89: Refactor this function to reduce its Cognitive Complexity from 22 to the 15 allowed.

See more on https://sonarcloud.io/project/issues?id=Zipstack_unstract&issues=AZq5vmfHJLmK1kHiqjA4&open=AZq5vmfHJLmK1kHiqjA4&pullRequest=1681


[warning] 138-138: Prefer String#replaceAll() over String#replace().

See more on https://sonarcloud.io/project/issues?id=Zipstack_unstract&issues=AZq5vmfHJLmK1kHiqjA5&open=AZq5vmfHJLmK1kHiqjA5&pullRequest=1681

workers/shared/workflow/destination_connector.py

[failure] 225-225: Refactor this function to reduce its Cognitive Complexity from 28 to the 15 allowed.

See more on https://sonarcloud.io/project/issues?id=Zipstack_unstract&issues=AZq5vmklJLmK1kHiqjA6&open=AZq5vmklJLmK1kHiqjA6&pullRequest=1681

⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: build
🔇 Additional comments (6)
unstract/sdk1/src/unstract/sdk1/adapters/x2text/llm_whisperer_v2/src/constants.py (1)

75-75: LGTM!

The new configuration key follows the existing naming conventions and integrates well with the other WhispererConfig constants.

unstract/sdk1/src/unstract/sdk1/adapters/x2text/llm_whisperer_v2/src/helper.py (1)

205-206: LGTM!

Coupling INCLUDE_LINE_CONFIDENCE with enable_highlight is consistent with ADD_LINE_NOS and ensures line-level confidence data is available when highlighting features are enabled downstream.

backend/prompt_studio/prompt_studio_output_manager_v2/output_manager_helper.py (1)

147-169: Good refactor: Loop-scoped variables prevent cross-prompt data mutation.

This correctly isolates per-prompt data extraction, ensuring that modifications (like extracting nested keys or adding file_name) don't affect subsequent iterations.

workers/shared/workflow/destination_connector.py (1)

1494-1534: LGTM: 3-tier confidence fallback hierarchy is well-implemented.

The fallback logic correctly prioritizes:

  1. word_confidence_data (most granular)
  2. Extracted average from highlight_data (derived)
  3. Original confidence_data (last resort)

The enriched metadata in wrapped_result now provides comprehensive confidence data for downstream HITL rule evaluation.

unstract/sdk1/src/unstract/sdk1/llm.py (1)

477-478: Verify breaking change impact on external callers

The signature change for post_process_fn from the original 2-parameter to the new 3-parameter callable is confirmed and real. The callback now requires (LLMResponseCompat, bool, str) parameters and is invoked at lines 501-502 with three arguments: response_compat, extract_json, and original_text.

However, no callers of complete() passing post_process_fn were found in the codebase search. Since this parameter is passed via **kwargs and appears undocumented, determine whether:

  • This is a new feature with no existing users (safe to change)
  • Users exist in external code outside this repository (breaking change)
  • Users exist in code paths not covered by the search

Confirm there are no external dependencies relying on the old 2-parameter signature before merging.

frontend/src/components/custom-tools/prompt-card/PromptCard.jsx (1)

235-235: LGTM! Simplified confidence handling.

The change correctly delegates confidence computation to DisplayPromptResult.jsx, removing the averaging logic from this component. This centralizes the multi-tier confidence fallback strategy in one place.

@github-actions
Copy link
Contributor

Test Results

Summary
  • Runner Tests: 11 passed, 0 failed (11 total)
  • SDK1 Tests: 66 passed, 0 failed (66 total)

Runner Tests - Full Report
filepath function $$\textcolor{#23d18b}{\tt{passed}}$$ SUBTOTAL
$$\textcolor{#23d18b}{\tt{runner/src/unstract/runner/clients/test\_docker.py}}$$ $$\textcolor{#23d18b}{\tt{test\_logs}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{runner/src/unstract/runner/clients/test\_docker.py}}$$ $$\textcolor{#23d18b}{\tt{test\_cleanup}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{runner/src/unstract/runner/clients/test\_docker.py}}$$ $$\textcolor{#23d18b}{\tt{test\_cleanup\_skip}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{runner/src/unstract/runner/clients/test\_docker.py}}$$ $$\textcolor{#23d18b}{\tt{test\_client\_init}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{runner/src/unstract/runner/clients/test\_docker.py}}$$ $$\textcolor{#23d18b}{\tt{test\_get\_image\_exists}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{runner/src/unstract/runner/clients/test\_docker.py}}$$ $$\textcolor{#23d18b}{\tt{test\_get\_image}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{runner/src/unstract/runner/clients/test\_docker.py}}$$ $$\textcolor{#23d18b}{\tt{test\_get\_container\_run\_config}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{runner/src/unstract/runner/clients/test\_docker.py}}$$ $$\textcolor{#23d18b}{\tt{test\_get\_container\_run\_config\_without\_mount}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{runner/src/unstract/runner/clients/test\_docker.py}}$$ $$\textcolor{#23d18b}{\tt{test\_run\_container}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{runner/src/unstract/runner/clients/test\_docker.py}}$$ $$\textcolor{#23d18b}{\tt{test\_get\_image\_for\_sidecar}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{runner/src/unstract/runner/clients/test\_docker.py}}$$ $$\textcolor{#23d18b}{\tt{test\_sidecar\_container}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{TOTAL}}$$ $$\textcolor{#23d18b}{\tt{11}}$$ $$\textcolor{#23d18b}{\tt{11}}$$
SDK1 Tests - Full Report
filepath function $$\textcolor{#23d18b}{\tt{passed}}$$ SUBTOTAL
$$\textcolor{#23d18b}{\tt{tests/test\_platform.py}}$$ $$\textcolor{#23d18b}{\tt{TestPlatformHelperRetry.test\_success\_on\_first\_attempt}}$$ $$\textcolor{#23d18b}{\tt{2}}$$ $$\textcolor{#23d18b}{\tt{2}}$$
$$\textcolor{#23d18b}{\tt{tests/test\_platform.py}}$$ $$\textcolor{#23d18b}{\tt{TestPlatformHelperRetry.test\_retry\_on\_connection\_error}}$$ $$\textcolor{#23d18b}{\tt{2}}$$ $$\textcolor{#23d18b}{\tt{2}}$$
$$\textcolor{#23d18b}{\tt{tests/test\_platform.py}}$$ $$\textcolor{#23d18b}{\tt{TestPlatformHelperRetry.test\_non\_retryable\_http\_error}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/test\_platform.py}}$$ $$\textcolor{#23d18b}{\tt{TestPlatformHelperRetry.test\_retryable\_http\_errors}}$$ $$\textcolor{#23d18b}{\tt{3}}$$ $$\textcolor{#23d18b}{\tt{3}}$$
$$\textcolor{#23d18b}{\tt{tests/test\_platform.py}}$$ $$\textcolor{#23d18b}{\tt{TestPlatformHelperRetry.test\_post\_method\_retry}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/test\_platform.py}}$$ $$\textcolor{#23d18b}{\tt{TestPlatformHelperRetry.test\_retry\_logging}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/test\_prompt.py}}$$ $$\textcolor{#23d18b}{\tt{TestPromptToolRetry.test\_success\_on\_first\_attempt}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/test\_prompt.py}}$$ $$\textcolor{#23d18b}{\tt{TestPromptToolRetry.test\_retry\_on\_errors}}$$ $$\textcolor{#23d18b}{\tt{2}}$$ $$\textcolor{#23d18b}{\tt{2}}$$
$$\textcolor{#23d18b}{\tt{tests/test\_prompt.py}}$$ $$\textcolor{#23d18b}{\tt{TestPromptToolRetry.test\_wrapper\_methods\_retry}}$$ $$\textcolor{#23d18b}{\tt{4}}$$ $$\textcolor{#23d18b}{\tt{4}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestIsRetryableError.test\_connection\_error\_is\_retryable}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestIsRetryableError.test\_timeout\_is\_retryable}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestIsRetryableError.test\_http\_error\_retryable\_status\_codes}}$$ $$\textcolor{#23d18b}{\tt{3}}$$ $$\textcolor{#23d18b}{\tt{3}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestIsRetryableError.test\_http\_error\_non\_retryable\_status\_codes}}$$ $$\textcolor{#23d18b}{\tt{5}}$$ $$\textcolor{#23d18b}{\tt{5}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestIsRetryableError.test\_http\_error\_without\_response}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestIsRetryableError.test\_os\_error\_retryable\_errno}}$$ $$\textcolor{#23d18b}{\tt{5}}$$ $$\textcolor{#23d18b}{\tt{5}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestIsRetryableError.test\_os\_error\_non\_retryable\_errno}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestIsRetryableError.test\_other\_exception\_not\_retryable}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestCalculateDelay.test\_exponential\_backoff\_without\_jitter}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestCalculateDelay.test\_exponential\_backoff\_with\_jitter}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestCalculateDelay.test\_max\_delay\_cap}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestCalculateDelay.test\_max\_delay\_cap\_with\_jitter}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestRetryWithExponentialBackoff.test\_successful\_call\_first\_attempt}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestRetryWithExponentialBackoff.test\_retry\_after\_transient\_failure}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestRetryWithExponentialBackoff.test\_max\_retries\_exceeded}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestRetryWithExponentialBackoff.test\_max\_time\_exceeded}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestRetryWithExponentialBackoff.test\_retry\_with\_custom\_predicate}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestRetryWithExponentialBackoff.test\_no\_retry\_with\_predicate\_false}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestRetryWithExponentialBackoff.test\_exception\_not\_in\_tuple\_not\_retried}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestRetryWithExponentialBackoff.test\_delay\_would\_exceed\_max\_time}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestCreateRetryDecorator.test\_default\_configuration}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestCreateRetryDecorator.test\_environment\_variable\_configuration}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestCreateRetryDecorator.test\_invalid\_max\_retries}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestCreateRetryDecorator.test\_invalid\_max\_time}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestCreateRetryDecorator.test\_invalid\_base\_delay}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestCreateRetryDecorator.test\_invalid\_multiplier}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestCreateRetryDecorator.test\_jitter\_values}}$$ $$\textcolor{#23d18b}{\tt{2}}$$ $$\textcolor{#23d18b}{\tt{2}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestCreateRetryDecorator.test\_custom\_exceptions\_only}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestCreateRetryDecorator.test\_custom\_predicate\_only}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestCreateRetryDecorator.test\_both\_exceptions\_and\_predicate}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestCreateRetryDecorator.test\_exceptions\_match\_but\_predicate\_false}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestPreconfiguredDecorators.test\_retry\_platform\_service\_call\_exists}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestPreconfiguredDecorators.test\_retry\_prompt\_service\_call\_exists}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestPreconfiguredDecorators.test\_platform\_service\_decorator\_retries\_on\_connection\_error}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestPreconfiguredDecorators.test\_prompt\_service\_decorator\_retries\_on\_timeout}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestRetryLogging.test\_warning\_logged\_on\_retry}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestRetryLogging.test\_info\_logged\_on\_success\_after\_retry}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{tests/utils/test\_retry\_utils.py}}$$ $$\textcolor{#23d18b}{\tt{TestRetryLogging.test\_exception\_logged\_on\_giving\_up}}$$ $$\textcolor{#23d18b}{\tt{1}}$$ $$\textcolor{#23d18b}{\tt{1}}$$
$$\textcolor{#23d18b}{\tt{TOTAL}}$$ $$\textcolor{#23d18b}{\tt{66}}$$ $$\textcolor{#23d18b}{\tt{66}}$$

@sonarqubecloud
Copy link

@Deepak-Kesavan Deepak-Kesavan merged commit 3512d89 into main Nov 25, 2025
7 checks passed
@Deepak-Kesavan Deepak-Kesavan deleted the UN-3008-word-level-confidence branch November 25, 2025 06:50
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.

5 participants