Skip to content

refactor: update type definitions and improve scope handling across files#310

Merged
frontegg-david merged 13 commits intorelease/1.0.xfrom
refactor-code
Mar 27, 2026
Merged

refactor: update type definitions and improve scope handling across files#310
frontegg-david merged 13 commits intorelease/1.0.xfrom
refactor-code

Conversation

@frontegg-david
Copy link
Contributor

@frontegg-david frontegg-david commented Mar 26, 2026

Summary by CodeRabbit

  • Bug Fixes

    • More robust handling when elicitation/persistence layers are unavailable, with clearer error paths.
    • Explicit validation and clearer failures when transport services are missing.
  • Refactor

    • Simplified registry and entry typing by moving to concrete registry types.
    • Streamlined scope and service access patterns across components.
    • Removed unused marker interfaces and cleaned up internal typings.

@coderabbitai
Copy link
Contributor

coderabbitai bot commented Mar 26, 2026

📝 Walkthrough

Walkthrough

Refactors SDK typing and scope plumbing: removes empty marker interfaces, replaces interface-based registry types with concrete registry classes, migrates many Scope usages to ScopeEntry, switches hook access to scope.hooks, and adds runtime guards/errors for missing transport/elicitation services.

Changes

Cohort / File(s) Summary
Gitignore
/.gitignore
Added .claude/planning/ to ignore list.
Interface removals & generic relaxations
libs/sdk/src/common/interfaces/app.interface.ts, libs/sdk/src/common/interfaces/plugin.interface.ts, libs/sdk/src/common/interfaces/provider.interface.ts, libs/sdk/src/common/interfaces/scope.interface.ts
Deleted empty marker interfaces and changed generic defaults/constraints to unknown.
Registry type consolidation
libs/sdk/src/common/interfaces/internal/registry.interface.ts
Removed registry *Interface types and replaced public RegistryType entries with type-only imports of concrete registry classes.
Entry type updates
libs/sdk/src/common/entries/app.entry.ts, libs/sdk/src/common/entries/plugin.entry.ts, libs/sdk/src/common/entries/provider.entry.ts, libs/sdk/src/common/entries/scope.entry.ts
Changed BaseEntry generic middle parameter to unknown, swapped registry getter return types to concrete registry classes, and added new abstract getters/method runFlowForOutput on ScopeEntry.
Scope → ScopeEntry migrations
libs/sdk/src/agent/agent.instance.ts, libs/sdk/src/agent/agent.scope.ts, libs/sdk/src/flows/flow.instance.ts, libs/sdk/src/job/job.instance.ts, libs/sdk/src/plugin/plugin.registry.ts, libs/sdk/src/prompt/prompt.instance.ts, libs/sdk/src/resource/resource.instance.ts, libs/sdk/src/skill/skill.instance.ts, libs/sdk/src/skill/skill.registry.ts, libs/sdk/src/tool/tool.instance.ts, libs/sdk/src/workflow/workflow.instance.ts
Replaced Scope types with ScopeEntry and added delegated getters on agent scope entries where applicable.
Hook registry access changes
libs/sdk/src/agent/agent.instance.ts, libs/sdk/src/flows/flow.instance.ts, libs/sdk/src/job/job.instance.ts, libs/sdk/src/prompt/prompt.instance.ts, libs/sdk/src/resource/resource.instance.ts, libs/sdk/src/tool/tool.instance.ts, libs/sdk/src/workflow/workflow.instance.ts
Init hooks via this.scope.hooks instead of scope.providers.getHooksRegistry().
Removed implements from registry classes
libs/sdk/src/auth/auth.registry.ts, libs/sdk/src/hooks/hook.registry.ts, libs/sdk/src/resource/resource.registry.ts, libs/sdk/src/tool/tool.registry.ts, libs/sdk/src/prompt/prompt.registry.ts
Removed explicit implements ...Interface clauses from registry class declarations.
Elicitation store access & guards
libs/sdk/src/elicitation/flows/elicitation-request.flow.ts, libs/sdk/src/elicitation/flows/elicitation-result.flow.ts, libs/sdk/src/elicitation/helpers/fallback.helper.ts, libs/sdk/src/elicitation/send-elicitation-result.tool.ts, libs/sdk/src/transport/adapters/transport.local.adapter.ts, libs/sdk/src/transport/adapters/transport.sse.adapter.ts, libs/sdk/src/transport/adapters/transport.streamable-http.adapter.ts
Use this.scope.elicitationStore (guarded/optional), add runtime guards/errors, introduce requireElicitStore() helper in adapters.
Transport guards & new error
libs/sdk/src/transport/flows/handle.sse.flow.ts, libs/sdk/src/transport/flows/handle.stateless-http.flow.ts, libs/sdk/src/transport/flows/handle.streamable-http.flow.ts, libs/sdk/src/errors/transport.errors.ts, libs/sdk/src/errors/index.ts
Read this.scope.transportService directly and throw TransportServiceNotAvailableError when missing; added the new error export.
Cast elimination & direct property access
libs/sdk/src/agent/flows/call-agent.flow.ts, libs/sdk/src/provider/provider.registry.ts, libs/sdk/src/resource/flows/read-resource.flow.ts, libs/sdk/src/scope/flows/http.request.flow.ts, libs/sdk/src/skill/flows/http/skills-api.flow.ts, libs/sdk/src/skill/flows/load-skill.flow.ts, libs/sdk/src/tool/flows/call-tool.flow.ts, libs/sdk/src/tool/flows/tools-list.flow.ts
Removed (this.scope as Scope) casts and use direct this.scope properties (rateLimitManager, toolUI, notifications, etc.).
Tool registry type updates
libs/sdk/src/skill/skill-http.utils.ts, libs/sdk/src/skill/skill-storage.factory.ts, libs/sdk/src/skill/skill-validator.ts, libs/sdk/src/skill/tools/load-skills.tool.ts, tests
Replaced ToolRegistryInterface usages with concrete ToolRegistry type imports and updated signatures/casts.
App instance getter return type tightening
libs/sdk/src/app/instances/app.esm.instance.ts, libs/sdk/src/app/instances/app.local.instance.ts, libs/sdk/src/app/instances/app.remote.instance.ts
Changed tools, resources, prompts getters to return concrete registry classes instead of interface types.
Tests & fixtures
libs/sdk/src/__test-utils__/fixtures/plugin.fixtures.ts, libs/sdk/src/__test-utils__/fixtures/provider.fixtures.ts, libs/sdk/src/plugin/__tests__/*, libs/sdk/src/skill/__tests__/*
Removed implements ...Interface from test fixture classes and updated test type imports to concrete types or type-only imports.
Transport adapters & flow updates
libs/sdk/src/transport/adapters/*, libs/sdk/src/transport/flows/*
Centralized elicit/store access into local guarded variables; added explicit guards and adapted cleanup paths to use the guarded store.

Sequence Diagram(s)

sequenceDiagram
    participant Flow as Flow/Tool/Prompt
    participant ScopeEntry as ScopeEntry
    participant Hooks as HookRegistry
    participant Provider as ProviderRegistry

    Flow->>ScopeEntry: read scope.hooks
    ScopeEntry->>Hooks: return HookRegistry
    Flow->>Hooks: register/emit hooks
    Flow->>ScopeEntry: (when needed) call runFlowForOutput(...)
    ScopeEntry->>Provider: resolve additional deps (optional)
    Provider->>Flow: provide dependencies
Loading
sequenceDiagram
    participant Flow as Transport Flow
    participant ScopeEntry as ScopeEntry
    participant Transport as TransportService
    participant Store as ElicitationStore

    Flow->>ScopeEntry: access transportService
    alt transportService present
        ScopeEntry->>Transport: return instance
        Flow->>Transport: proceed with send/handle
    else transportService missing
        ScopeEntry->>Flow: undefined
        Flow->>Flow: throw TransportServiceNotAvailableError
    end

    Flow->>ScopeEntry: access elicitationStore
    alt elicitationStore present
        ScopeEntry->>Store: return store
        Flow->>Store: setPending / subscribeResult / cleanup
    else elicitationStore missing
        ScopeEntry->>Flow: undefined
        Flow->>Flow: throw or reject (ElicitationStoreNotInitializedError / InternalMcpError)
    end
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~60 minutes

Possibly related PRs

Poem

🐰
I nibble at interfaces thin,
Concrete registries hop right in.
Scopes stretch out their brand-new ears,
Guards stand watch through transport fears.
A joyful hop — the build compiles again!

🚥 Pre-merge checks | ✅ 3
✅ Passed checks (3 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title accurately summarizes the main refactoring changes: removing interface constraints and updating scope type usage across the codebase.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 65.00%.

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

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch refactor-code

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

@github-actions
Copy link
Contributor

github-actions bot commented Mar 26, 2026

Performance Test Results

Status: ✅ All tests passed

Summary

Project Tests Passed Warnings Failed Leaks
✅ demo-e2e-agents 4 4 0 0 0
✅ demo-e2e-cache 11 11 0 0 0
✅ demo-e2e-codecall 4 4 0 0 0
✅ demo-e2e-config 4 4 0 0 0
✅ demo-e2e-direct 3 3 0 0 0
✅ demo-e2e-elicitation 1 1 0 0 0
✅ demo-e2e-errors 4 4 0 0 0
✅ demo-e2e-hooks 3 3 0 0 0
✅ demo-e2e-multiapp 4 4 0 0 0
✅ demo-e2e-notifications 3 3 0 0 0
✅ demo-e2e-openapi 2 2 0 0 0
✅ demo-e2e-providers 4 4 0 0 0
✅ demo-e2e-public 4 4 0 0 0
✅ demo-e2e-redis 15 15 0 0 0
✅ demo-e2e-remember 4 4 0 0 0
✅ demo-e2e-remote 5 5 0 0 0
✅ demo-e2e-serverless 2 2 0 0 0
✅ demo-e2e-skills 15 15 0 0 0
✅ demo-e2e-standalone 2 2 0 0 0
✅ demo-e2e-transport-recreation 3 3 0 0 0
✅ demo-e2e-ui 4 4 0 0 0

Total: 101 tests across 21 projects

📊 View full report in workflow run


Generated at: 2026-03-27T01:46:14.802Z
Commit: b4a28f16

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: 9

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
libs/sdk/src/transport/flows/handle.sse.flow.ts (1)

17-17: ⚠️ Potential issue | 🟡 Minor

Remove unused Scope import from line 17.

The Scope class is imported but never used in this file. Removing it eliminates unnecessary dead code.

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

In `@libs/sdk/src/transport/flows/handle.sse.flow.ts` at line 17, Remove the
unused import of Scope from the top-level imports in handle.sse.flow.ts: locate
the import statement "import { Scope } from '../../scope';" and delete it so
there is no dead/unused import remaining; ensure remaining imports still satisfy
lint rules and build.
🧹 Nitpick comments (5)
libs/sdk/src/elicitation/flows/elicitation-result.flow.ts (1)

14-14: Remove unused import.

The Scope type import appears to be unused after the refactor to ScopeEntry-based access. This should be cleaned up.

🧹 Suggested fix
-import type { Scope } from '../../scope';
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@libs/sdk/src/elicitation/flows/elicitation-result.flow.ts` at line 14, The
import "Scope" is no longer used after switching to ScopeEntry-based access;
remove the unused type import (the `Scope` identifier) from the import statement
so only needed symbols (e.g., ScopeEntry) remain and eliminate the dead import
in elicitation-result.flow.ts where `import type { Scope } from '../../scope';`
currently appears.
libs/sdk/src/common/interfaces/app.interface.ts (1)

6-8: Consider using unknown instead of any for the type parameter default.

While the comment provides justification for any ("broad compatibility with untyped app classes"), the coding guidelines prefer unknown over any for generic type defaults. Using unknown would provide better type safety while still allowing broad compatibility through explicit type narrowing.

If this change would cause breaking changes for existing consumers, the current approach with the eslint-disable comment is acceptable.

♻️ Suggested change
 // Using 'unknown' default for type safety with generic app classes
-// eslint-disable-next-line `@typescript-eslint/no-explicit-any`
-export type AppType<T = any> = Type<T> | AppValueType<T> | RemoteAppMetadata;
+export type AppType<T = unknown> = Type<T> | AppValueType<T> | RemoteAppMetadata;
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@libs/sdk/src/common/interfaces/app.interface.ts` around lines 6 - 8, Replace
the generic default from `any` to `unknown` in the `AppType` alias (i.e., change
`export type AppType<T = any>` to `export type AppType<T = unknown>`), remove
the `// eslint-disable-next-line `@typescript-eslint/no-explicit-any`` line, and
update the preceding comment to reflect the use of `unknown` for broader safety
while preserving compatibility via explicit narrowing; ensure references to
`Type<T>`, `AppValueType<T>`, and `RemoteAppMetadata` remain unchanged.
libs/sdk/src/agent/flows/call-agent.flow.ts (1)

16-16: Remove unused Scope import.

The Scope import on line 16 is not used anywhere in this file and should be removed.

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

In `@libs/sdk/src/agent/flows/call-agent.flow.ts` at line 16, Remove the unused
import Scope from the top of the file: delete the import token "Scope" from the
import statement that currently reads "import { Scope } from '../../scope';" so
the file no longer imports Scope (ensure any remaining imports on that line are
preserved if shared).
libs/sdk/src/transport/flows/handle.streamable-http.flow.ts (1)

304-307: Consider using a specific error class for transport service unavailability.

The guard clause pattern is consistent across all stage methods, which is good. However, per coding guidelines, specific error classes with MCP error codes are preferred over generic Error. This error is thrown in 5 places (onInitialize, onElicitResult, onMessage, onSseListener, onExtApps).

♻️ Suggested error class approach

Create a specific error class (e.g., TransportServiceNotAvailableError) with an appropriate MCP error code (likely INTERNAL_ERROR: -32603), then use it consistently:

-    if (!transportService) {
-      throw new Error('Transport service not available');
-    }
+    if (!transportService) {
+      throw new TransportServiceNotAvailableError();
+    }
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@libs/sdk/src/transport/flows/handle.streamable-http.flow.ts` around lines 304
- 307, Replace the generic throw new Error('Transport service not available')
guard with a specific error class: create TransportServiceNotAvailableError
(extend the project MCP error base) that encodes the MCP error code (e.g.,
INTERNAL_ERROR -32603) and use it in all stage methods (onInitialize,
onElicitResult, onMessage, onSseListener, onExtApps) where the transportService
guard appears; update each guard to throw new
TransportServiceNotAvailableError(...) with a clear contextual message so
callers can distinguish this failure type from other errors.
libs/sdk/src/common/entries/app.entry.ts (1)

10-10: Constrain Metadata here unless BaseEntry already does it.

This declaration no longer shows an AppMetadata bound, so AppEntry loses the local guarantee that subclasses carry app-shaped metadata. Metadata extends AppMetadata = AppMetadata keeps the new unknown middle generic without weakening the metadata contract.

♻️ Suggested type constraint
-export abstract class AppEntry<Metadata = AppMetadata> extends BaseEntry<AppRecord, unknown, Metadata> {
+export abstract class AppEntry<Metadata extends AppMetadata = AppMetadata>
+  extends BaseEntry<AppRecord, unknown, Metadata> {
As per coding guidelines, "Use type parameter constraints with unknown defaults for generic classes. Create constrained generic types like `ResourceContext = Record, Out = unknown>` instead of unconstrained generics with `any`."
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@libs/sdk/src/common/entries/app.entry.ts` at line 10, AppEntry currently
declares a generic Metadata without constraining it, which weakens the
expectation that subclasses carry app-shaped metadata; update the class generic
on AppEntry to constrain Metadata to AppMetadata (e.g., Metadata extends
AppMetadata = AppMetadata) so the middle generic of BaseEntry can remain unknown
without losing the metadata contract—locate the export abstract class AppEntry
declaration and adjust its generic parameter accordingly (referencing AppEntry,
BaseEntry, and AppMetadata).
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@libs/sdk/src/agent/agent.scope.ts`:
- Around line 368-390: Add an explicit implements declaration to the
AgentScopeEntry class so it declares that it conforms to the ScopeEntry
interface; update the class signature for AgentScopeEntry to include "implements
ScopeEntry" (the existing getters transportService, rateLimitManager,
elicitationStore, metadata, record, and ready already satisfy the contract),
ensuring no change to their return values (undefined for the absent services)
and leaving metadata and ready as-is.

In `@libs/sdk/src/app/instances/app.remote.instance.ts`:
- Around line 296-305: The getters tools, resources, and prompts return the
backing registries directly and never trigger lazy discovery, so callers see
empty sets unless they explicitly call ensureCapabilitiesLoaded(); update the
accessors (get tools, get resources, get prompts) to invoke or await
ensureCapabilitiesLoaded() before returning _tools, _resources, and _prompts
(respecting the existing ready/initialization flow so you don't double-load),
ensuring the first access to each registry triggers capability discovery via
ensureCapabilitiesLoaded() and returns the populated registries.

In `@libs/sdk/src/common/entries/scope.entry.ts`:
- Line 21: The ScopeEntry file is importing AuthRegistry (and wiring
authProviders) from an internal SDK auth path which leaks auth implementation
into common; remove the direct import of AuthRegistry and any direct
construction/wiring of authProviders in ScopeEntry (and related lines around the
authProviders usage) and instead obtain authentication dependencies via the
public auth boundary (inject an auth provider/registry interface into ScopeEntry
or accept it via constructor/parameters), or import them from the public package
symbol exported by `@frontmcp/auth`; update ScopeEntry to depend only on the
abstract auth interface passed in rather than ../../auth.auth.registry so all
auth implementation stays in libs/auth.

In `@libs/sdk/src/common/interfaces/provider.interface.ts`:
- Around line 12-16: The generic default type for the ProviderType alias is
unsafe: change the generic parameter default from Provide = any to Provide =
unknown so ProviderType (and its variants ProviderClassType, ProviderValueType,
ProviderFactoryType) no longer opt into unsafe any when consumers omit the
Provide type; update the ProviderType declaration to use Provide = unknown and
run type checks to ensure no call sites rely on implicit any.

In `@libs/sdk/src/elicitation/flows/elicitation-request.flow.ts`:
- Around line 166-169: Replace the generic throw in the block that checks
this.scope.elicitationStore with a framework-specific MCP error: create or reuse
a typed SDK error class (e.g., ElicitationStoreNotInitializedError) that
includes the appropriate MCP error code and implements toJsonRpcError(), and
throw an instance of that class from the check around
this.scope.elicitationStore so error mapping remains consistent across flows.

In `@libs/sdk/src/elicitation/helpers/fallback.helper.ts`:
- Around line 150-154: The early-return rejection when scope.elicitationStore is
missing must clear the pending timeout and use a typed error: before calling
reject(...) clearTimeout(timeoutHandle) so the timeout callback won't fire
later, and replace the generic Error with a domain-specific error (e.g.,
MissingElicitationStoreError) or an exported typed error class; update the call
site in the block that checks scope.elicitationStore (the code referencing
scope.elicitationStore and reject) to clear the timer and reject with the new
specific error type, and add/import the error type definition if needed.

In `@libs/sdk/src/elicitation/send-elicitation-result.tool.ts`:
- Line 129: The cast is used because ScopeEntry lacks the runFlowForOutput
method; add an abstract declaration runFlowForOutput(name: string, params:
Record<string, any>): Promise<any> (matching the existing concrete signature) to
the ScopeEntry abstract class, implement that method in the concrete Scope class
(delegate to the existing implementation), then remove the cast in
send-elicitation-result.tool.ts so you can call this.scope.runFlowForOutput(...)
directly; ensure the method signature matches usages (e.g., the
'tools:call-tool' call) and update any related type imports if needed.

In `@libs/sdk/src/scope/flows/http.request.flow.ts`:
- Around line 528-529: The current early return when transportService is falsy
can drop DELETE responses; modify the branch around transportService (in the
function handling the flow) so that instead of unconditional "if
(!transportService) return" you detect when authorization?.token exists and in
that case call httpRespond.noContent() (or the appropriate completion for
DELETE) before returning; keep the original early return only for cases without
authorization.token. Ensure you reference transportService, authorization.token
and httpRespond.noContent() when making the change so DELETE requests still
receive a response.

In `@libs/sdk/src/transport/flows/handle.stateless-http.flow.ts`:
- Around line 98-101: Replace the generic throw new Error('Transport service not
available') when this.scope.transportService is falsy with a typed MCP SDK error
(e.g., TransportServiceNotAvailableError) that extends your base MCP error
class, includes the appropriate MCP error code, and implements toJsonRpcError();
create the new error class if missing and use it in the check around
transportService (referencing transportService and this.scope.transportService)
so error translation remains consistent across the SDK.

---

Outside diff comments:
In `@libs/sdk/src/transport/flows/handle.sse.flow.ts`:
- Line 17: Remove the unused import of Scope from the top-level imports in
handle.sse.flow.ts: locate the import statement "import { Scope } from
'../../scope';" and delete it so there is no dead/unused import remaining;
ensure remaining imports still satisfy lint rules and build.

---

Nitpick comments:
In `@libs/sdk/src/agent/flows/call-agent.flow.ts`:
- Line 16: Remove the unused import Scope from the top of the file: delete the
import token "Scope" from the import statement that currently reads "import {
Scope } from '../../scope';" so the file no longer imports Scope (ensure any
remaining imports on that line are preserved if shared).

In `@libs/sdk/src/common/entries/app.entry.ts`:
- Line 10: AppEntry currently declares a generic Metadata without constraining
it, which weakens the expectation that subclasses carry app-shaped metadata;
update the class generic on AppEntry to constrain Metadata to AppMetadata (e.g.,
Metadata extends AppMetadata = AppMetadata) so the middle generic of BaseEntry
can remain unknown without losing the metadata contract—locate the export
abstract class AppEntry declaration and adjust its generic parameter accordingly
(referencing AppEntry, BaseEntry, and AppMetadata).

In `@libs/sdk/src/common/interfaces/app.interface.ts`:
- Around line 6-8: Replace the generic default from `any` to `unknown` in the
`AppType` alias (i.e., change `export type AppType<T = any>` to `export type
AppType<T = unknown>`), remove the `// eslint-disable-next-line
`@typescript-eslint/no-explicit-any`` line, and update the preceding comment to
reflect the use of `unknown` for broader safety while preserving compatibility
via explicit narrowing; ensure references to `Type<T>`, `AppValueType<T>`, and
`RemoteAppMetadata` remain unchanged.

In `@libs/sdk/src/elicitation/flows/elicitation-result.flow.ts`:
- Line 14: The import "Scope" is no longer used after switching to
ScopeEntry-based access; remove the unused type import (the `Scope` identifier)
from the import statement so only needed symbols (e.g., ScopeEntry) remain and
eliminate the dead import in elicitation-result.flow.ts where `import type {
Scope } from '../../scope';` currently appears.

In `@libs/sdk/src/transport/flows/handle.streamable-http.flow.ts`:
- Around line 304-307: Replace the generic throw new Error('Transport service
not available') guard with a specific error class: create
TransportServiceNotAvailableError (extend the project MCP error base) that
encodes the MCP error code (e.g., INTERNAL_ERROR -32603) and use it in all stage
methods (onInitialize, onElicitResult, onMessage, onSseListener, onExtApps)
where the transportService guard appears; update each guard to throw new
TransportServiceNotAvailableError(...) with a clear contextual message so
callers can distinguish this failure type from other errors.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: 6d70459d-f02a-43b3-bc80-421729bd2474

📥 Commits

Reviewing files that changed from the base of the PR and between 122102b and db6165a.

📒 Files selected for processing (61)
  • .gitignore
  • libs/sdk/src/__test-utils__/fixtures/plugin.fixtures.ts
  • libs/sdk/src/__test-utils__/fixtures/provider.fixtures.ts
  • libs/sdk/src/agent/agent.instance.ts
  • libs/sdk/src/agent/agent.registry.ts
  • libs/sdk/src/agent/agent.scope.ts
  • libs/sdk/src/agent/flows/call-agent.flow.ts
  • libs/sdk/src/app/instances/app.esm.instance.ts
  • libs/sdk/src/app/instances/app.local.instance.ts
  • libs/sdk/src/app/instances/app.remote.instance.ts
  • libs/sdk/src/auth/auth.registry.ts
  • libs/sdk/src/auth/instances/instance.remote-primary-auth.ts
  • libs/sdk/src/common/entries/app.entry.ts
  • libs/sdk/src/common/entries/plugin.entry.ts
  • libs/sdk/src/common/entries/provider.entry.ts
  • libs/sdk/src/common/entries/scope.entry.ts
  • libs/sdk/src/common/interfaces/app.interface.ts
  • libs/sdk/src/common/interfaces/internal/registry.interface.ts
  • libs/sdk/src/common/interfaces/plugin.interface.ts
  • libs/sdk/src/common/interfaces/provider.interface.ts
  • libs/sdk/src/common/interfaces/scope.interface.ts
  • libs/sdk/src/elicitation/flows/elicitation-request.flow.ts
  • libs/sdk/src/elicitation/flows/elicitation-result.flow.ts
  • libs/sdk/src/elicitation/helpers/fallback.helper.ts
  • libs/sdk/src/elicitation/send-elicitation-result.tool.ts
  • libs/sdk/src/flows/flow.instance.ts
  • libs/sdk/src/hooks/hook.registry.ts
  • libs/sdk/src/job/job.instance.ts
  • libs/sdk/src/plugin/__tests__/plugin.registry.spec.ts
  • libs/sdk/src/plugin/__tests__/plugin.utils.spec.ts
  • libs/sdk/src/plugin/plugin.registry.ts
  • libs/sdk/src/prompt/prompt.instance.ts
  • libs/sdk/src/prompt/prompt.registry.ts
  • libs/sdk/src/provider/provider.registry.ts
  • libs/sdk/src/resource/flows/read-resource.flow.ts
  • libs/sdk/src/resource/resource.instance.ts
  • libs/sdk/src/resource/resource.registry.ts
  • libs/sdk/src/scope/flows/http.request.flow.ts
  • libs/sdk/src/scope/scope.instance.ts
  • libs/sdk/src/skill/__tests__/memory-skill.provider.spec.ts
  • libs/sdk/src/skill/__tests__/skill-http.utils.spec.ts
  • libs/sdk/src/skill/__tests__/skill-validator.spec.ts
  • libs/sdk/src/skill/flows/http/skills-api.flow.ts
  • libs/sdk/src/skill/flows/load-skill.flow.ts
  • libs/sdk/src/skill/skill-http.utils.ts
  • libs/sdk/src/skill/skill-storage.factory.ts
  • libs/sdk/src/skill/skill-validator.ts
  • libs/sdk/src/skill/skill.instance.ts
  • libs/sdk/src/skill/skill.registry.ts
  • libs/sdk/src/skill/tools/load-skills.tool.ts
  • libs/sdk/src/tool/flows/call-tool.flow.ts
  • libs/sdk/src/tool/flows/tools-list.flow.ts
  • libs/sdk/src/tool/tool.instance.ts
  • libs/sdk/src/tool/tool.registry.ts
  • libs/sdk/src/transport/adapters/transport.local.adapter.ts
  • libs/sdk/src/transport/adapters/transport.sse.adapter.ts
  • libs/sdk/src/transport/adapters/transport.streamable-http.adapter.ts
  • libs/sdk/src/transport/flows/handle.sse.flow.ts
  • libs/sdk/src/transport/flows/handle.stateless-http.flow.ts
  • libs/sdk/src/transport/flows/handle.streamable-http.flow.ts
  • libs/sdk/src/workflow/workflow.instance.ts

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 (1)
libs/sdk/src/elicitation/flows/elicitation-result.flow.ts (1)

196-202: Asymmetric handling of missing store between stages.

In lookupPending, a missing store throws an error (line 114), but here in publishResult, a missing store is silently treated as "not handled" (line 198-201). This inconsistency may cause confusion:

  • If the store is missing in lookupPending, the flow fails with an exception.
  • If the store becomes unavailable between stages (unlikely but possible), publishResult silently fails.

Consider whether both stages should have the same behavior. If graceful degradation is intended, lookupPending should also handle missing store gracefully. If store availability is a prerequisite, publishResult should throw.

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

In `@libs/sdk/src/elicitation/flows/elicitation-result.flow.ts` around lines 196 -
202, The handling of a missing store is inconsistent between lookupPending
(which throws) and publishResult (which silently sets handled=false); choose and
implement a consistent policy: either make lookupPending degrade gracefully like
publishResult by checking this.scope.elicitationStore and setting
this.state.set('handled', false) and logging via this.logger.verbose in
lookupPending, or make publishResult enforce the prerequisite by throwing an
Error when this.scope.elicitationStore is missing (e.g., mirror lookupPending’s
behavior), updating publishResult’s early-return to raise the same exception and
remove the silent handled=false path; update whichever function you change
(lookupPending or publishResult) so both use the same error/logging pattern and
reference this.scope.elicitationStore, this.state.set('handled', false), and
this.logger.verbose consistently.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@libs/sdk/src/elicitation/flows/elicitation-result.flow.ts`:
- Around line 112-115: Replace the plain Error throw in the lookupPending stage
with an ElicitationStoreNotInitializedError (same subclass used by
storePendingRecord) so missing this.scope.elicitationStore consistently raises
the InternalMcpError subclass; also make the missing-store behavior in
publishResult symmetric (either throw the same
ElicitationStoreNotInitializedError instead of returning handled:false or
explicitly document why it differs) by updating the publishResult path that
checks this.scope.elicitationStore to throw ElicitationStoreNotInitializedError
to match lookupPending/storePendingRecord.

---

Nitpick comments:
In `@libs/sdk/src/elicitation/flows/elicitation-result.flow.ts`:
- Around line 196-202: The handling of a missing store is inconsistent between
lookupPending (which throws) and publishResult (which silently sets
handled=false); choose and implement a consistent policy: either make
lookupPending degrade gracefully like publishResult by checking
this.scope.elicitationStore and setting this.state.set('handled', false) and
logging via this.logger.verbose in lookupPending, or make publishResult enforce
the prerequisite by throwing an Error when this.scope.elicitationStore is
missing (e.g., mirror lookupPending’s behavior), updating publishResult’s
early-return to raise the same exception and remove the silent handled=false
path; update whichever function you change (lookupPending or publishResult) so
both use the same error/logging pattern and reference
this.scope.elicitationStore, this.state.set('handled', false), and
this.logger.verbose consistently.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: b076a11f-9e75-4c51-8768-c8f1091b6fbe

📥 Commits

Reviewing files that changed from the base of the PR and between db6165a and 5c29be5.

📒 Files selected for processing (19)
  • libs/sdk/src/__test-utils__/fixtures/plugin.fixtures.ts
  • libs/sdk/src/agent/agent.scope.ts
  • libs/sdk/src/agent/flows/call-agent.flow.ts
  • libs/sdk/src/common/entries/scope.entry.ts
  • libs/sdk/src/common/interfaces/app.interface.ts
  • libs/sdk/src/common/interfaces/provider.interface.ts
  • libs/sdk/src/elicitation/flows/elicitation-request.flow.ts
  • libs/sdk/src/elicitation/flows/elicitation-result.flow.ts
  • libs/sdk/src/elicitation/helpers/fallback.helper.ts
  • libs/sdk/src/elicitation/send-elicitation-result.tool.ts
  • libs/sdk/src/errors/index.ts
  • libs/sdk/src/errors/transport.errors.ts
  • libs/sdk/src/plugin/__tests__/plugin.registry.spec.ts
  • libs/sdk/src/provider/provider.registry.ts
  • libs/sdk/src/resource/flows/read-resource.flow.ts
  • libs/sdk/src/scope/flows/http.request.flow.ts
  • libs/sdk/src/transport/flows/handle.sse.flow.ts
  • libs/sdk/src/transport/flows/handle.stateless-http.flow.ts
  • libs/sdk/src/transport/flows/handle.streamable-http.flow.ts
✅ Files skipped from review due to trivial changes (3)
  • libs/sdk/src/scope/flows/http.request.flow.ts
  • libs/sdk/src/test-utils/fixtures/plugin.fixtures.ts
  • libs/sdk/src/elicitation/send-elicitation-result.tool.ts
🚧 Files skipped from review as they are similar to previous changes (9)
  • libs/sdk/src/transport/flows/handle.stateless-http.flow.ts
  • libs/sdk/src/elicitation/flows/elicitation-request.flow.ts
  • libs/sdk/src/elicitation/helpers/fallback.helper.ts
  • libs/sdk/src/common/interfaces/app.interface.ts
  • libs/sdk/src/transport/flows/handle.sse.flow.ts
  • libs/sdk/src/common/interfaces/provider.interface.ts
  • libs/sdk/src/provider/provider.registry.ts
  • libs/sdk/src/agent/agent.scope.ts
  • libs/sdk/src/agent/flows/call-agent.flow.ts

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)
libs/sdk/src/elicitation/flows/elicitation-result.flow.ts (1)

198-200: Update skip log message to match the new guard condition.

Line 200 says “no pending or no result”, but Line 198 also skips on missing store. Consider making the log explicit for easier debugging.

🔧 Proposed log text update
-      this.logger.verbose('publishResult:skip (no pending or no result)');
+      this.logger.verbose('publishResult:skip (no pending, no result, or no store)');
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@libs/sdk/src/elicitation/flows/elicitation-result.flow.ts` around lines 198 -
200, The guard in publishResult checks three variables (pendingRecord,
elicitResult, store) but the verbose log only mentions missing pending/result;
update the message emitted by this.logger.verbose in the branch that sets
this.state.set('handled', false) to explicitly mention which of pendingRecord,
elicitResult or store is missing (or a concise combined message like
"publishResult:skip (missing pendingRecord, elicitResult or store)") so logs
accurately reflect the guard; locate the check using symbols pendingRecord,
elicitResult, store, this.state.set('handled', false) and this.logger.verbose to
make the fix.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Nitpick comments:
In `@libs/sdk/src/elicitation/flows/elicitation-result.flow.ts`:
- Around line 198-200: The guard in publishResult checks three variables
(pendingRecord, elicitResult, store) but the verbose log only mentions missing
pending/result; update the message emitted by this.logger.verbose in the branch
that sets this.state.set('handled', false) to explicitly mention which of
pendingRecord, elicitResult or store is missing (or a concise combined message
like "publishResult:skip (missing pendingRecord, elicitResult or store)") so
logs accurately reflect the guard; locate the check using symbols pendingRecord,
elicitResult, store, this.state.set('handled', false) and this.logger.verbose to
make the fix.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: 1988daf0-f257-4e38-91d1-22ece66c4bde

📥 Commits

Reviewing files that changed from the base of the PR and between 5c29be5 and 271f606.

📒 Files selected for processing (1)
  • libs/sdk/src/elicitation/flows/elicitation-result.flow.ts

@frontegg-david frontegg-david merged commit bbb5464 into release/1.0.x Mar 27, 2026
63 checks passed
@frontegg-david frontegg-david deleted the refactor-code branch March 27, 2026 01:52
github-actions bot pushed a commit that referenced this pull request Mar 27, 2026
…ling across files

Cherry-picked from #310 (merged to release/1.0.x)
Original commit: bbb5464

Co-Authored-By: frontegg-david <69419539+frontegg-david@users.noreply.github.com>
@github-actions
Copy link
Contributor

Cherry-pick Created

A cherry-pick PR to main has been automatically created.

Please review and merge if this change should also be in main.

If the cherry-pick is not needed, close the PR.

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