Skip to content

Fix missing chatStorage config in AICommandExecutor during AI evals#1501

Open
yasithrashan wants to merge 1 commit intowso2:mainfrom
yasithrashan:fix-evals
Open

Fix missing chatStorage config in AICommandExecutor during AI evals#1501
yasithrashan wants to merge 1 commit intowso2:mainfrom
yasithrashan:fix-evals

Conversation

@yasithrashan
Copy link
Contributor

@yasithrashan yasithrashan commented Feb 19, 2026

Purpose

Resolves a crash when running the Ballerina Extension AI evals (AI Test suite). chatStorage is not configured in the eval environment, causing AICommandExecutor to throw a TypeError during initialization and preventing all eval test cases from running.

Error:

TypeError: Cannot destructure property 'workspaceId' of 'this.config.chatStorage' as it is undefined.

Goals

Make chatStorage optional in AICommandExecutor so AI evals can run successfully without requiring chat storage to be configured.

Approach

Added null-guard checks in initializeWorkspaceThread, getChatHistory, and addGeneration. Each method now returns a safe default (void, [], or null) if this.config.chatStorage is undefined, instead of attempting to destructure it.

Summary by CodeRabbit

Bug Fixes

  • Improved stability of AI chat features by adding graceful handling for scenarios where chat storage is unavailable. The system now manages these situations without disruption instead of potential failures.

@coderabbitai
Copy link
Contributor

coderabbitai bot commented Feb 19, 2026

📝 Walkthrough

Walkthrough

This change adds defensive guards to the AICommandExecutor class to handle cases where the optional chatStorage parameter may be absent, returning early or providing default values instead of accessing undefined storage.

Changes

Cohort / File(s) Summary
Optional chatStorage Guards
workspaces/ballerina/ballerina-extension/src/features/ai/executors/base/AICommandExecutor.ts
Added null-safety checks in three methods: initializeWorkspaceThread logs and returns early if chatStorage is absent, getChatHistory returns an empty array, and addGeneration returns null. Prevents undefined storage access without altering public signatures.

Estimated code review effort

🎯 2 (Simple) | ⏱️ ~5 minutes

Poem

A rabbit checked the storage state,
Found guards preventing crashes late,
With early returns and empty arrays,
Optional paths now safe from worries! 🐰✨

🚥 Pre-merge checks | ✅ 3
✅ Passed checks (3 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly and specifically summarizes the main change: adding missing chatStorage config handling in AICommandExecutor for AI eval tests.
Description check ✅ Passed The description covers the three key template sections (Purpose, Goals, Approach) with clear problem statement, solution, and implementation details.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment

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.

🧹 Nitpick comments (1)
workspaces/ballerina/ballerina-extension/src/features/ai/executors/base/AICommandExecutor.ts (1)

42-46: enabled field is declared but never evaluated — consider honoring it in the guards.

The chatStorage config exposes an enabled: boolean flag, but all three guards (and the fallback in run()) only check for undefined. A caller supplying chatStorage: { workspaceId, threadId, enabled: false } would bypass the early-return path and still invoke chat storage operations, which is likely unintentional.

♻️ Suggested: unify the presence + enabled check into a single helper
+    /** Returns true when chat storage is present and enabled */
+    private hasChatStorage(): boolean {
+        return !!this.config.chatStorage?.enabled;
+    }

Then replace every guard:

-        if (!this.config.chatStorage) {
+        if (!this.hasChatStorage()) {

This keeps the three call-sites identical and makes the semantics explicit without changing behavior for callers that currently omit chatStorage entirely.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In
`@workspaces/ballerina/ballerina-extension/src/features/ai/executors/base/AICommandExecutor.ts`
around lines 42 - 46, The guards and fallback in AICommandExecutor.ts currently
only check chatStorage for undefined and ignore its enabled flag, so callers
with chatStorage.enabled === false still trigger storage flows; add a helper
(e.g., isChatStorageEnabled(chatStorage)) that returns false if chatStorage is
undefined or chatStorage.enabled is false and replace the three existing
undefined checks plus the run() fallback to call this helper (update references
to chatStorage in AICommandExecutor methods to use the helper to short-circuit
when disabled).
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Nitpick comments:
In
`@workspaces/ballerina/ballerina-extension/src/features/ai/executors/base/AICommandExecutor.ts`:
- Around line 42-46: The guards and fallback in AICommandExecutor.ts currently
only check chatStorage for undefined and ignore its enabled flag, so callers
with chatStorage.enabled === false still trigger storage flows; add a helper
(e.g., isChatStorageEnabled(chatStorage)) that returns false if chatStorage is
undefined or chatStorage.enabled is false and replace the three existing
undefined checks plus the run() fallback to call this helper (update references
to chatStorage in AICommandExecutor methods to use the helper to short-circuit
when disabled).

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant