Skip to content

fix(wren-ai-service): Settings Loading and Multi-Pipeline Component Mechanism for Evaluation Framework - #1198

Merged
cyyeh merged 18 commits into
mainfrom
fix/evaluation-framework
Jan 21, 2025
Merged

cyyeh merged 18 commits into
mainfrom
fix/evaluation-framework

Conversation

@paopa

@paopa paopa commented Jan 20, 2025 •

Copy link
Copy Markdown

Overview

This Pull Request introduces significant updates to the evaluation framework, focusing on transitioning to a new settings loading mechanism and implementing a multi-pipeline component structure. Additionally, it includes modifications to accommodate changes in the deepeval interface.

Key Changes

  1. Settings Management:

    • Removed settings related to LANGFUSE_PROJECT_ID, OPENAI_API_KEY, WREN_IBIS_ENDPOINT, WREN_ENGINE_ENDPOINT, WREN_IBIS_TIMEOUT, BATCH_SIZE, BATCH_INTERVAL, DATA_SOURCE, bigquery.project-id, bigquery.dataset-id, and bigquery.credentials-key from the .env.example file.
    • Introduced a new EvalSettings class in the __init__.py file to manage settings such as langfuse project ID, batch size, batch interval, datasource, config path, and langfuse URL.
  2. Multi-Pipeline Component Mechanism:

    • Refactored the deployment of models in pipelines to utilize the new settings and components.
    • Updated retrieval and generation pipelines to align with the new architecture.
  3. Interface Changes:

    • Updated the deepeval interface to reflect the new settings and multi-pipeline component mechanism.
  4. Metric Classes Updates:

    • Modified the AccuracyMetric, AnswerRelevancyMetric, ContextualRecallMetric, and FaithfulnessMetric classes to use engine_info instead of engine_config.
    • Updated method calls to reflect these changes.
  5. Code Cleanup:

    • Removed unused imports and classes to streamline the codebase.

Summary by CodeRabbit

  • Configuration Changes

    • Removed .env.example file with environment variable configurations.
    • Updated .gitignore to include config.yaml and deepeval_telemtry.txt.
  • Dependency Updates

    • Moved deepeval from dev dependencies to evaluation dependencies.
    • Added streamlit-tags to evaluation dependencies.
  • Evaluation Improvements

    • Introduced new EvalSettings class for centralized configuration management.
    • Updated metrics and pipeline classes to use new configuration approach.
    • Simplified environment variable and provider initialization processes.
  • Code Refactoring

    • Renamed configuration-related parameters from engine_config to engine_info.
    • Streamlined initialization of pipeline components.
    • Updated string formatting across utility functions.
    • Enhanced configurability in the data curation application.

@coderabbitai

coderabbitai Bot commented Jan 20, 2025 •

Copy link
Copy Markdown
Contributor

Walkthrough

This pull request introduces significant refactoring of the Wren AI service's evaluation module, focusing on configuration management and code structure. The changes involve removing the .env.example file, which contained environment variable placeholders, and replacing environment variable-based configurations with a centralized EvalSettings class. Various utility and metric classes have been updated to utilize this new configuration approach, streamlining the process and enhancing the modularity of the evaluation pipeline.

Changes

File Change Summary
eval/.env.example Deleted configuration file with environment variable placeholders
eval/.gitignore Added config.yaml to ignored files
eval/__init__.py Introduced EvalSettings class extending Settings
eval/evaluation.py Removed environment variable loading, updated evaluation logic
eval/metrics/* Renamed engine_config to engine_info across accuracy, answer relevancy, context recall, and faithfulness metrics
eval/pipelines.py Integrated EvalSettings, updated pipeline component initialization
eval/prediction.py Replaced provider-based configuration with EvalSettings
eval/utils.py Updated string formatting, modified engine_config function
pyproject.toml Moved deepeval dependency, added streamlit-tags
eval/data_curation/app.py Enhanced configurability by using EvalSettings for API key retrieval
.gitignore Added .deepeval_telemtry.txt to ignored files

Sequence Diagram

sequenceDiagram
    participant User
    participant EvalSettings
    participant Providers
    participant Pipelines
    participant Metrics

    User->>EvalSettings: Initialize with configuration
    EvalSettings-->>Providers: Generate components
    Providers-->>Pipelines: Provide configured components
    Pipelines->>Metrics: Pass engine_info
    Metrics->>Metrics: Calculate evaluation metrics
    Metrics-->>Pipelines: Return results
Loading

Possibly related PRs

Poem

🐰 A config revolution, clean and bright,
Settings dancing with newfound might
Environment vars, now tucked away
EvalSettings leads the way today!
Code refactored, smooth and light 🌟

✨ Finishing Touches
  • 📝 Generate Docstrings (Beta)

Thank you for using CodeRabbit. We offer it for free to the OSS community and would appreciate your support in helping us grow. If you find it useful, would you consider giving us a shout-out on your favorite social media?

❤️ Share
🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

  • Review comments: Directly reply to a review comment made by CodeRabbit. Example:
    • I pushed a fix in commit <commit_id>, please review it.
    • Generate unit testing code for this file.
    • Open a follow-up GitHub issue for this discussion.
  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query. Examples:
    • @coderabbitai generate unit testing code for this file.
    • @coderabbitai modularize this function.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read src/utils.ts and generate unit testing code.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.
    • @coderabbitai help me debug CodeRabbit configuration file.

Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments.

CodeRabbit Commands (Invoked using PR comments)

  • @coderabbitai pause to pause the reviews on a PR.
  • @coderabbitai resume to resume the paused reviews.
  • @coderabbitai review to trigger an incremental review. This is useful when automatic reviews are disabled for the repository.
  • @coderabbitai full review to do a full review from scratch and review all the files again.
  • @coderabbitai summary to regenerate the summary of the PR.
  • @coderabbitai generate docstrings to generate docstrings for this PR. (Beta)
  • @coderabbitai resolve resolve all the CodeRabbit review comments.
  • @coderabbitai configuration to show the current CodeRabbit configuration for the repository.
  • @coderabbitai help to get help.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai anywhere in the PR title to generate the title automatically.

CodeRabbit Configuration File (.coderabbit.yaml)

  • You can programmatically configure CodeRabbit by adding a .coderabbit.yaml file to the root of your repository.
  • Please see the configuration documentation for more information.
  • If your editor has YAML language server enabled, you can add the path at the top of this file to enable auto-completion and validation: # yaml-language-server: $schema=https://coderabbit.ai/integrations/schema.v2.json

Documentation and Community

  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

@paopa paopa added module/ai-service ai-service related ci/ai-service ai-service related labels Jan 20, 2025
@paopa
paopa marked this pull request as ready for review January 20, 2025 10:16

@coderabbitai coderabbitai Bot 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.

Actionable comments posted: 7

🧹 Nitpick comments (5)
wren-ai-service/eval/pipelines.py (2)

115-115: Confirm usage of ellipsis in abstract method

The use of ... as the method body for _process in the Eval class is acceptable in Python 3.5 and above for abstract methods. Ensure that the Python version used in the project supports this syntax. Alternatively, consider using pass for clarity.

Apply this diff if you prefer using pass:

-    def _process(self, prediction: dict, **_) -> dict: ...
+    def _process(self, prediction: dict, **_) -> dict:
+        pass

368-377: Update parameter names in init function

In the init function, consider renaming the parameter components to pipe_components for consistency with the rest of the codebase, as seen in the classes where pipe_components is used. This enhances readability and reduces confusion.

Apply this diff:

-def init(
    name: Literal["retrieval", "generation", "ask"],
    meta: dict,
    mdl: dict,
    components: Dict[str, Any],
    settings: EvalSettings,
) -> Eval:
    args = {
        "meta": meta,
        "mdl": mdl,
-       "components": components,
+       "pipe_components": components,
        "settings": settings,
    }

Ensure that all calls to init and usage of args within the function are updated accordingly.

wren-ai-service/eval/metrics/faithfulness.py (2)

10-13: Consider maintaining private attribute convention.

The removal of the underscore prefix from _engine_config suggests this is now intended to be a public attribute. If this is meant to be an implementation detail, consider keeping it as a private attribute with the underscore prefix.

-        self.engine_info = engine_info
+        self._engine_info = engine_info

20-20: Update attribute reference to match constructor.

If keeping the private attribute convention, update the attribute reference here as well.

-            sql=test_case.actual_output, **self.engine_info
+            sql=test_case.actual_output, **self._engine_info
wren-ai-service/eval/evaluation.py (1)

85-85: Consider adding error details to the result.

The error handling could be improved by including error details in the test result.

-                result = evaluate([test_case], self._metrics, ignore_errors=True).test_results[0]
+                try:
+                    result = evaluate([test_case], self._metrics, ignore_errors=True).test_results[0]
+                except Exception as e:
+                    result = TestResult(test_case=test_case, error=str(e))
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 3d1eb8c and 71e57c9.

⛔ Files ignored due to path filters (1)
  • wren-ai-service/poetry.lock is excluded by !**/*.lock
📒 Files selected for processing (12)
  • wren-ai-service/eval/.env.example (0 hunks)
  • wren-ai-service/eval/.gitignore (1 hunks)
  • wren-ai-service/eval/__init__.py (1 hunks)
  • wren-ai-service/eval/evaluation.py (3 hunks)
  • wren-ai-service/eval/metrics/accuracy.py (3 hunks)
  • wren-ai-service/eval/metrics/answer_relevancy.py (1 hunks)
  • wren-ai-service/eval/metrics/context_recall.py (1 hunks)
  • wren-ai-service/eval/metrics/faithfulness.py (1 hunks)
  • wren-ai-service/eval/pipelines.py (11 hunks)
  • wren-ai-service/eval/prediction.py (3 hunks)
  • wren-ai-service/eval/utils.py (8 hunks)
  • wren-ai-service/pyproject.toml (1 hunks)
💤 Files with no reviewable changes (1)
  • wren-ai-service/eval/.env.example
✅ Files skipped from review due to trivial changes (1)
  • wren-ai-service/eval/.gitignore
🔇 Additional comments (18)
wren-ai-service/eval/prediction.py (3)

16-16: Ensure correct import path for EvalSettings

The import statement from eval import EvalSettings might not resolve if the eval module is not correctly recognized as a package. If EvalSettings is defined in the __init__.py file within the eval directory, ensure that the eval directory has an __init__.py file to make it a package. Alternatively, adjust the import statement to reflect the correct module structure.


24-25: Update calls to generate_meta to match new parameter

The generate_meta function has been updated to accept settings: EvalSettings instead of llm_provider and embedder_provider. Ensure that all calls to this function are updated accordingly to pass the settings parameter. This change centralizes configuration management but requires careful updates to all function invocations.


28-43: ⚠️ Potential issue

Verify that all settings attributes exist in EvalSettings

The code accesses several attributes from settings, such as:

  • settings.langfuse_url
  • settings.column_indexing_batch_size
  • settings.table_retrieval_size
  • settings.table_column_retrieval_size
  • settings.batch_size
  • settings.batch_interval
  • settings.datasource

Ensure that all these attributes are defined within the EvalSettings class or inherited from the base Settings class. Missing attributes will result in an AttributeError at runtime.

Run the following script to verify the existence of these attributes:

✅ Verification successful

All required settings attributes are properly defined

The code correctly accesses all required attributes:

  • Direct attributes in EvalSettings: batch_size, batch_interval, datasource
  • Property in EvalSettings: langfuse_url
  • Inherited from base Settings class: column_indexing_batch_size, table_retrieval_size, table_column_retrieval_size
🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify that all required attributes exist in EvalSettings.

# Test: List all attributes of EvalSettings and check for the required ones.
ast-grep --pattern $'class EvalSettings(Settings) {
  $$$
}' wren-ai-service/eval/__init__.py | grep -E 'langfuse_url|column_indexing_batch_size|table_retrieval_size|table_column_retrieval_size|batch_size|batch_interval|datasource'

Length of output: 232


Script:

#!/bin/bash
# Find the relevant Python files
echo "=== Finding relevant files ==="
fd -e py "settings|__init__" eval

# View the content of files in eval directory that might contain settings
echo -e "\n=== Checking content of potential settings files ==="
for f in $(fd -e py "settings|__init__" eval); do
  echo -e "\n=== Content of $f ===";
  cat "$f";
done

# Search for the attributes across all Python files in eval
echo -e "\n=== Searching for settings attributes ==="
rg -A 1 "class .*Settings" eval/
rg "(langfuse_url|column_indexing_batch_size|table_retrieval_size|table_column_retrieval_size|batch_size|batch_interval|datasource)\s*[:=]" eval/

Length of output: 822


Script:

#!/bin/bash
# Check settings class definitions
echo "=== Settings Class Definitions ==="
rg -A 5 "class .*Settings" wren-ai-service/

# Check settings attributes
echo -e "\n=== Settings Attributes ==="
rg "(langfuse_url|column_indexing_batch_size|table_retrieval_size|table_column_retrieval_size|batch_size|batch_interval|datasource)\s*[=:]" wren-ai-service/

# View the specific settings file content
echo -e "\n=== Settings File Content ==="
find wren-ai-service -type f -name "settings.py" -o -name "__init__.py" | while read -r file; do
  echo -e "\n--- $file ---"
  cat "$file"
done

Length of output: 69957

wren-ai-service/eval/pipelines.py (3)

15-15: Verify correct import of EvalSettings

Similar to prediction.py, ensure that the import from eval import EvalSettings correctly locates the EvalSettings class. Confirm that the eval package is properly recognized, and adjust the import path if necessary.


33-33: Update parameter type in deploy_model function

The deploy_model function's parameter pipe has changed from indexing.Indexing to indexing.DBSchema. Ensure that the DBSchema class provides all the methods and attributes used within deploy_model. This change should be verified to prevent any unexpected behavior.


172-188: ⚠️ Potential issue

Ensure all settings attributes are defined and used correctly

Within the RetrievalPipeline class, several attributes from settings are used:

  • settings.column_indexing_batch_size
  • settings.table_retrieval_size
  • settings.table_column_retrieval_size
  • settings.allow_using_db_schemas_without_pruning

Verify that these attributes are defined in EvalSettings or inherited from Settings. Missing attributes will cause runtime errors.

wren-ai-service/eval/__init__.py (2)

5-9: ⚠️ Potential issue

Ensure all required settings are included in EvalSettings

The EvalSettings class defines several attributes. Confirm that all required settings used throughout the codebase are included here or in the base Settings class, including:

  • column_indexing_batch_size
  • table_retrieval_size
  • table_column_retrieval_size
  • allow_using_db_schemas_without_pruning

If these attributes are missing, accessing them will result in AttributeError.


12-15: ⚠️ Potential issue

Verify the existence of langfuse_host in EvalSettings

The property langfuse_url uses self.langfuse_host, but langfuse_host is not defined within EvalSettings. Ensure that langfuse_host is defined in the base Settings class or add it to EvalSettings.

wren-ai-service/eval/metrics/context_recall.py (1)

10-13: Same changes as in FaithfulnessMetric.

The changes mirror those in FaithfulnessMetric. Consider applying the same private attribute convention here.

Also applies to: 20-20

wren-ai-service/eval/metrics/answer_relevancy.py (1)

10-13: Same changes as in other metric classes.

The changes mirror those in other metric classes. Consider applying the same private attribute convention here.

Also applies to: 20-20, 24-24

wren-ai-service/eval/evaluation.py (4)

16-18: LGTM! Clean import changes.

The imports reflect the transition to the new settings loading mechanism and provider structure.


146-148: LGTM! Clean settings initialization.

The initialization of settings and components aligns with the new architecture.


155-156: LGTM! Consistent use of engine_info.

The use of engine_info is consistent with the changes in metric classes.


160-172: Remove or update commented code.

The commented-out code related to the training dataset functionality should either be:

  1. Removed if it's no longer needed
  2. Updated to use the new settings mechanism
  3. Tracked as a TODO item if it needs to be addressed later

Let's check if this code is referenced elsewhere:

wren-ai-service/eval/metrics/accuracy.py (2)

15-15: LGTM! Constructor parameter and instance variable names improved.

The renaming from engine_config to engine_info and removal of underscore prefixes improves naming consistency and clarity while maintaining the same functionality.

Also applies to: 18-19


20-20: Verify semantics comparison behavior remains unchanged.

The semantics comparison logic has been updated to use the new variable name. While the changes look correct, please ensure that all test cases for semantic comparison still pass.

Also applies to: 148-148

✅ Verification successful

Semantics comparison behavior verified to be unchanged

The semantics comparison remains an optional feature that acts as a fallback mechanism in accuracy metrics, only triggering when exact matches fail. The variable rename is consistent across the codebase and maintains the same behavior pattern.

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Search for existing tests that cover semantics comparison
rg -l "enable_semantics_comparison.*True" -g "test_*.py"

Length of output: 58


Script:

#!/bin/bash
# Find test files related to accuracy and semantics
echo "=== Test files with 'accuracy' ==="
fd "test.*accuracy.*\.py$"

echo -e "\n=== Any usage of semantics comparison in tests ==="
rg "semantics" -g "test_*.py" -A 2 -B 2

echo -e "\n=== Implementation of semantics comparison ==="
rg "enable_semantics_comparison" -A 5 -B 5

Length of output: 18892

wren-ai-service/eval/utils.py (1)

217-219: Verify engine attributes are always set.

The code assumes _source, _endpoint, and _connection_info attributes exist on the engine object. Add validation to prevent potential AttributeErrors.

wren-ai-service/pyproject.toml (1)

59-60: LGTM! Dependencies properly organized.

Moving deepeval to eval dependencies and adding streamlit-tags aligns with the evaluation framework's scope. The versions are pinned appropriately.

Comment thread wren-ai-service/eval/prediction.py
Comment thread wren-ai-service/eval/prediction.py
Comment thread wren-ai-service/eval/pipelines.py Outdated
Comment thread wren-ai-service/eval/pipelines.py Outdated
Comment thread wren-ai-service/eval/pipelines.py Outdated
Comment thread wren-ai-service/eval/pipelines.py Outdated
Comment thread wren-ai-service/eval/utils.py Outdated
@paopa
paopa requested a review from cyyeh January 21, 2025 02:23
@paopa
paopa force-pushed the fix/evaluation-framework branch from 71e57c9 to 4a0d2be Compare January 21, 2025 03:36

@coderabbitai coderabbitai Bot 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.

Actionable comments posted: 1

🧹 Nitpick comments (3)
wren-ai-service/eval/prediction.py (1)

113-118: Consider adding type hints for pipe_components.

While the code is functional, adding type hints for pipe_components would improve code maintainability and IDE support.

-        components=pipe_components,
+        components: Dict[str, Any]=pipe_components,
wren-ai-service/eval/evaluation.py (1)

159-172: Document the reason for commenting out training dataset code.

The code block for handling training datasets has been commented out. Consider adding a TODO comment explaining why this functionality is temporarily disabled and when it will be re-enabled.

-    # if args.training_dataset:
+    # TODO(TICKET-123): Training dataset functionality temporarily disabled pending dspy integration
+    # if args.training_dataset:
wren-ai-service/eval/pipelines.py (1)

178-180: Consider extracting configuration constants.

The column_batch_size configuration could be moved to a constants file for better maintainability.

+# In constants.py
+DEFAULT_COLUMN_BATCH_SIZE = 100
+
+# In current file
 _indexing = indexing.DBSchema(
     **pipe_components["db_schema_indexing"],
-    column_batch_size=settings.column_indexing_batch_size,
+    column_batch_size=settings.column_indexing_batch_size or DEFAULT_COLUMN_BATCH_SIZE,
 )
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 71e57c9 and 4a0d2be.

⛔ Files ignored due to path filters (1)
  • wren-ai-service/poetry.lock is excluded by !**/*.lock
📒 Files selected for processing (12)
  • wren-ai-service/eval/.env.example (0 hunks)
  • wren-ai-service/eval/.gitignore (1 hunks)
  • wren-ai-service/eval/__init__.py (1 hunks)
  • wren-ai-service/eval/evaluation.py (3 hunks)
  • wren-ai-service/eval/metrics/accuracy.py (3 hunks)
  • wren-ai-service/eval/metrics/answer_relevancy.py (1 hunks)
  • wren-ai-service/eval/metrics/context_recall.py (1 hunks)
  • wren-ai-service/eval/metrics/faithfulness.py (1 hunks)
  • wren-ai-service/eval/pipelines.py (11 hunks)
  • wren-ai-service/eval/prediction.py (4 hunks)
  • wren-ai-service/eval/utils.py (8 hunks)
  • wren-ai-service/pyproject.toml (1 hunks)
💤 Files with no reviewable changes (1)
  • wren-ai-service/eval/.env.example
🚧 Files skipped from review as they are similar to previous changes (8)
  • wren-ai-service/eval/.gitignore
  • wren-ai-service/eval/init.py
  • wren-ai-service/eval/metrics/context_recall.py
  • wren-ai-service/eval/metrics/answer_relevancy.py
  • wren-ai-service/eval/metrics/faithfulness.py
  • wren-ai-service/pyproject.toml
  • wren-ai-service/eval/utils.py
  • wren-ai-service/eval/metrics/accuracy.py
⏰ Context from checks skipped due to timeout of 90000ms (3)
  • GitHub Check: pytest
  • GitHub Check: Analyze (javascript-typescript)
  • GitHub Check: Analyze (go)
🔇 Additional comments (5)
wren-ai-service/eval/prediction.py (2)

111-111: LGTM! Clean parameter update.

The generate_meta call has been correctly updated to use the settings parameter.


104-107: Verify error handling for settings initialization.

The code initializes settings and generates components without any error handling. Consider adding try-catch blocks to handle potential initialization failures gracefully.

wren-ai-service/eval/evaluation.py (2)

146-148: LGTM! Clean initialization sequence.

The settings initialization and langfuse setup follow a logical order.


155-156: LGTM! Proper configuration update.

The engine configuration has been correctly updated to use pipe_components.

wren-ai-service/eval/pipelines.py (1)

185-188: LGTM! Comprehensive retrieval configuration.

The retrieval configuration properly includes all necessary parameters from settings.

Comment on lines +291 to +293
_indexing = indexing.DBSchema(
**pipe_components["db_schema_indexing"],
column_batch_size=settings.column_indexing_batch_size,

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.

🛠️ Refactor suggestion

Code duplication in pipeline initialization.

The initialization code in AskPipeline duplicates the pattern from RetrievalPipeline. Consider extracting this common initialization logic into a base class or utility function.

def init_db_schema(components: Dict[str, Any], settings: EvalSettings) -> indexing.DBSchema:
    return indexing.DBSchema(
        **components["db_schema_indexing"],
        column_batch_size=settings.column_indexing_batch_size,
    )

def init_retrieval(components: Dict[str, Any], settings: EvalSettings) -> retrieval.Retrieval:
    return retrieval.Retrieval(
        **components["db_schema_retrieval"],
        table_retrieval_size=settings.table_retrieval_size,
        table_column_retrieval_size=settings.table_column_retrieval_size,
        allow_using_db_schemas_without_pruning=settings.allow_using_db_schemas_without_pruning,
    )

Also applies to: 298-301

@paopa
paopa force-pushed the fix/evaluation-framework branch from 4a0d2be to cfb1d7e Compare January 21, 2025 03:59

@coderabbitai coderabbitai Bot 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.

Actionable comments posted: 1

🔭 Outside diff range comments (1)
wren-ai-service/eval/evaluation.py (1)

Add test coverage for EvalSettings and its integration

The codebase lacks test coverage for the EvalSettings class and its integration with the evaluation pipeline. While the base Settings class has tests, you should add tests for:

  • EvalSettings configuration validation
  • Settings integration with component initialization
  • Error handling for invalid settings
🔗 Analysis chain

Line range hint 1-177: Verify test coverage for the new settings mechanism.

The changes look good overall, but ensure there are unit tests covering:

  1. The new settings loading mechanism
  2. Component initialization failures
  3. Various evaluation scenarios with the new pipeline structure

Let's check for existing test coverage:

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Search for related test files
fd -e py "test.*evaluation" .
# Check for EvalSettings tests
rg -i "class.*test.*evalsettings" .

Length of output: 69


Script:

#!/bin/bash
# Look for any test files in common test directories
fd -e py . tests/ test/ unit_tests/ integration_tests/ 2>/dev/null

# Search for any test files containing 'eval' or 'settings'
rg -l "class.*Test" -g "*.py" | rg -i "eval|settings"

# Search for imports or usage of EvalSettings
rg "EvalSettings" -A 3 -B 3

Length of output: 4240


Script:

#!/bin/bash
# Check for tests of the parent Settings class
rg "class.*Test.*Settings" -g "*.py"

# Look for any test files importing Settings
rg "from src.config import Settings" -g "*test*.py"

# Check the base Settings class implementation
rg "class Settings" -A 5 -B 5

Length of output: 835

🧹 Nitpick comments (3)
wren-ai-service/eval/evaluation.py (1)

146-148: Consider adding error handling for component initialization.

The new initialization sequence using EvalSettings and component generation looks good, but consider adding error handling for cases where component initialization fails.

 settings = EvalSettings()
+try:
     pipe_components = provider.generate_components(settings.components)
     utils.init_langfuse(settings)
+except Exception as e:
+    print(f"Failed to initialize components: {e}")
+    sys.exit(1)

Also applies to: 155-156

wren-ai-service/eval/pipelines.py (2)

178-180: Extract common initialization logic.

The initialization pattern is duplicated across pipeline classes. Consider extracting this into utility functions.

def init_db_schema(components: Dict[str, Any], settings: EvalSettings) -> indexing.DBSchema:
    return indexing.DBSchema(
        **components["db_schema_indexing"],
        column_batch_size=settings.column_indexing_batch_size,
    )

def init_retrieval(components: Dict[str, Any], settings: EvalSettings) -> retrieval.Retrieval:
    return retrieval.Retrieval(
        **components["db_schema_retrieval"],
        table_retrieval_size=settings.table_retrieval_size,
        table_column_retrieval_size=settings.table_column_retrieval_size,
        allow_using_db_schemas_without_pruning=settings.allow_using_db_schemas_without_pruning,
    )

Also applies to: 185-188


390-392: Add type hints for engine_info parameter.

The engine_info parameter lacks type hints in the metrics_initiator function.

-    engine_info: dict,
+    engine_info: Dict[str, Any],

Also applies to: 396-396, 398-398, 400-400

📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 4a0d2be and cfb1d7e.

⛔ Files ignored due to path filters (1)
  • wren-ai-service/poetry.lock is excluded by !**/*.lock
📒 Files selected for processing (12)
  • wren-ai-service/eval/.env.example (0 hunks)
  • wren-ai-service/eval/.gitignore (1 hunks)
  • wren-ai-service/eval/__init__.py (1 hunks)
  • wren-ai-service/eval/evaluation.py (3 hunks)
  • wren-ai-service/eval/metrics/accuracy.py (3 hunks)
  • wren-ai-service/eval/metrics/answer_relevancy.py (1 hunks)
  • wren-ai-service/eval/metrics/context_recall.py (1 hunks)
  • wren-ai-service/eval/metrics/faithfulness.py (1 hunks)
  • wren-ai-service/eval/pipelines.py (11 hunks)
  • wren-ai-service/eval/prediction.py (4 hunks)
  • wren-ai-service/eval/utils.py (8 hunks)
  • wren-ai-service/pyproject.toml (1 hunks)
💤 Files with no reviewable changes (1)
  • wren-ai-service/eval/.env.example
🚧 Files skipped from review as they are similar to previous changes (8)
  • wren-ai-service/eval/.gitignore
  • wren-ai-service/pyproject.toml
  • wren-ai-service/eval/init.py
  • wren-ai-service/eval/metrics/answer_relevancy.py
  • wren-ai-service/eval/metrics/faithfulness.py
  • wren-ai-service/eval/metrics/context_recall.py
  • wren-ai-service/eval/utils.py
  • wren-ai-service/eval/metrics/accuracy.py
⏰ Context from checks skipped due to timeout of 90000ms (4)
  • GitHub Check: Analyze (python)
  • GitHub Check: pytest
  • GitHub Check: Analyze (javascript-typescript)
  • GitHub Check: Analyze (go)
🔇 Additional comments (7)
wren-ai-service/eval/evaluation.py (3)

16-17: LGTM! Import changes align with the new settings mechanism.

The transition from environment variables to the new EvalSettings class is reflected in these import changes.


85-87: LGTM! Improved result handling with better object-oriented approach.

The change to access test_results attribute instead of direct index access is more robust and maintainable.


160-172: 🛠️ Refactor suggestion

Remove commented-out code and track it properly.

Large blocks of commented code can lead to maintenance issues and confusion. Instead:

  1. If this is temporary, create a ticket to track the re-implementation of the dspy functionality
  2. If this code is no longer needed, remove it entirely
  3. If this is for reference, move it to documentation

Let's check if this dspy-related code is referenced elsewhere:

wren-ai-service/eval/prediction.py (2)

24-24: LGTM! Improved configuration management.

The refactoring of generate_meta to use EvalSettings centralizes configuration management and improves code maintainability.

Also applies to: 28-43


111-111: LGTM! Clean pipeline initialization.

The pipeline initialization is now more streamlined with the new settings-based approach.

Also applies to: 113-118

wren-ai-service/eval/pipelines.py (2)

371-377: LGTM! Clean argument packaging.

The argument packaging for pipeline initialization is clean and maintainable.


224-225: Consider validating component configuration.

The generation component initialization lacks validation for required configuration keys.

Also applies to: 228-229

Comment on lines +104 to +107
settings = EvalSettings()
# todo: handle duckdb as datasource
pipe_components = provider.generate_components(settings.components)
utils.init_langfuse(settings)

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.

🛠️ Refactor suggestion

Verify error handling for settings initialization.

The settings initialization and component generation lack error handling. Consider adding try-catch blocks to handle potential configuration errors gracefully.

-    settings = EvalSettings()
-    # todo: handle duckdb as datasource
-    pipe_components = provider.generate_components(settings.components)
-    utils.init_langfuse(settings)
+    try:
+        settings = EvalSettings()
+        pipe_components = provider.generate_components(settings.components)
+        utils.init_langfuse(settings)
+    except Exception as e:
+        print(f"Failed to initialize settings: {e}")
+        sys.exit(1)

Committable suggestion skipped: line range outside the PR's diff.

@coderabbitai coderabbitai Bot 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.

Actionable comments posted: 1

🧹 Nitpick comments (4)
wren-ai-service/eval/__init__.py (1)

8-9: Add validation for batch processing parameters.

Consider adding validation to ensure batch_size and batch_interval are within reasonable bounds to prevent performance issues.

-    batch_size: int = 4
-    batch_interval: int = 1
+    batch_size: int = Field(default=4, gt=0, le=10)
+    batch_interval: int = Field(default=1, gt=0, le=5)
wren-ai-service/eval/data_curation/app.py (3)

70-72: Improve error message for model mismatch.

The assertion error message could be more helpful by including the actual model details.

-    assert doc["mdl"] == st.session_state["mdl_json"], (
-        "The model in the uploaded dataset is different from the deployed model"
-    )
+    assert doc["mdl"] == st.session_state["mdl_json"], (
+        f"Model mismatch - Uploaded: {doc['mdl'].get('name', 'unknown')} "
+        f"Deployed: {st.session_state['mdl_json'].get('name', 'unknown')}"
+    )

345-345: Standardize error message formatting.

The error messages in the UI should follow a consistent format. Currently, some use f-strings directly while others use get() with default values.

Standardize the error handling:

-                            f"SQL is invalid: {st.session_state['llm_question_sql_pairs'][i]['error']}"
+                            f"SQL is invalid: {st.session_state['llm_question_sql_pairs'][i].get('error', 'Unknown error')}"

Also applies to: 424-424


482-482: Use UTC for timestamp in filename.

When generating filenames with timestamps, it's better to use UTC to avoid timezone-related issues.

-                f"eval_dataset_{datetime.today().strftime('%Y_%m_%d')}.toml",
+                f"eval_dataset_{datetime.utcnow().strftime('%Y_%m_%d')}.toml",
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between cfb1d7e and bb940a0.

📒 Files selected for processing (2)
  • wren-ai-service/eval/__init__.py (1 hunks)
  • wren-ai-service/eval/data_curation/app.py (8 hunks)
⏰ Context from checks skipped due to timeout of 90000ms (4)
  • GitHub Check: pytest
  • GitHub Check: Analyze (python)
  • GitHub Check: Analyze (javascript-typescript)
  • GitHub Check: Analyze (go)
🔇 Additional comments (3)
wren-ai-service/eval/__init__.py (2)

12-12: LGTM! Secure handling of API key.

Good use of SecretStr for the API key and proper implementation of the getter method.

Also applies to: 20-21


7-7: Consider validation for langfuse_project_id.

The empty string default for langfuse_project_id combined with the silent failure in langfuse_url might mask configuration issues. Consider adding validation or logging when the project ID is missing.

Also applies to: 16-18

wren-ai-service/eval/data_curation/app.py (1)

42-43: LGTM! Proper initialization of settings and client.

Good integration of the new EvalSettings class for managing the OpenAI API key.

Comment on lines +16 to +17
sys.path.append(f"{Path().parent.resolve()}")
from eval import EvalSettings

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.

🛠️ Refactor suggestion

Avoid modifying sys.path.

Modifying sys.path directly is not recommended. Consider restructuring the project to use proper Python packaging.

Consider one of these alternatives:

  1. Add an empty init.py in the parent directory to make it a package
  2. Install the package in development mode using pip
  3. Use PYTHONPATH environment variable instead

@cyyeh cyyeh left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

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

LGTM

@cyyeh
cyyeh merged commit cfd8367 into main Jan 21, 2025
@cyyeh
cyyeh deleted the fix/evaluation-framework branch January 21, 2025 08:31

@coderabbitai coderabbitai Bot 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.

Actionable comments posted: 0

🧹 Nitpick comments (2)
wren-ai-service/eval/pipelines.py (2)

178-180: Extract common initialization logic to reduce duplication.

The initialization of DBSchema is duplicated between RetrievalPipeline and AskPipeline. Consider extracting this into a utility function:

def init_db_schema(components: Dict[str, Any], settings: EvalSettings) -> indexing.DBSchema:
    return indexing.DBSchema(
        **components["db_schema_indexing"],
        column_batch_size=settings.column_indexing_batch_size,
    )

Also applies to: 291-293


185-188: Extract retrieval initialization logic to reduce duplication.

Similar to the DBSchema initialization, the Retrieval initialization is also duplicated. Consider extracting this into a utility function:

def init_retrieval(components: Dict[str, Any], settings: EvalSettings) -> retrieval.Retrieval:
    return retrieval.Retrieval(
        **components["db_schema_retrieval"],
        table_retrieval_size=settings.table_retrieval_size,
        table_column_retrieval_size=settings.table_column_retrieval_size,
        allow_using_db_schemas_without_pruning=settings.allow_using_db_schemas_without_pruning,
    )

Also applies to: 298-301

📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between bb940a0 and 81532e2.

📒 Files selected for processing (2)
  • .gitignore (1 hunks)
  • wren-ai-service/eval/pipelines.py (11 hunks)
✅ Files skipped from review due to trivial changes (1)
  • .gitignore
🔇 Additional comments (4)
wren-ai-service/eval/pipelines.py (4)

15-30: LGTM! Clean import organization.

The imports are well-organized and properly reflect the transition to the new settings loading mechanism.


204-210: LGTM! Consistent metrics implementation.

The metrics implementation is now more consistent across all pipeline classes, using engine_info uniformly. The commented-out metrics for the spider dataset are properly documented.

Also applies to: 266-274, 344-358


371-377: LGTM! Clean initialization structure.

The common initialization structure using a dictionary of arguments is clean and maintainable.


321-322: Verify the impact of empty SQL samples.

The sql_samples parameter is passed as an empty list. Verify if this is intentional and whether it affects the generation quality.

✅ Verification successful

Empty SQL samples list is acceptable in evaluation context

The empty SQL samples list is intentionally used in the evaluation pipeline and the codebase is designed to handle this case properly. The generation pipelines accept this parameter as optional and include proper conditional handling in their templates.

🏁 Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Search for other usages of sql_samples to understand the expected values
rg -A 2 "sql_samples" 

Length of output: 4058

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

Labels

ci/ai-service ai-service related module/ai-service ai-service related

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants