feat: implement Extension system #27

Merged
irammini merged 11 commits from feat/extension-system into main 2026-03-14 17:52:40 +00:00
irammini commented 2026-03-14 16:18:46 +00:00 (Migrated from github.com)

Closes #23

Summary by CodeRabbit

  • New Features

    • Added a runtime registry to register and invoke custom prompt implementations.
  • API Updates

    • Added a prompt-constructor type and new top-level exports for ANSI, input parsing, and text utilities (stringWidth/truncate/stripAnsi).
  • Examples

    • Added an example demonstrating how to extend the registry with a custom prompt.
  • Documentation

    • Added an Extensions (Custom Prompts) section and an Extension Registry guide.
  • Tests

    • Added tests covering registration, duplicate handling/overwrite, invocation, and error cases.
  • Chores

    • Bumped package version and added/updated dev typing dependencies.
Closes #23 <!-- This is an auto-generated comment: release notes by coderabbit.ai --> ## Summary by CodeRabbit * **New Features** * Added a runtime registry to register and invoke custom prompt implementations. * **API Updates** * Added a prompt-constructor type and new top-level exports for ANSI, input parsing, and text utilities (stringWidth/truncate/stripAnsi). * **Examples** * Added an example demonstrating how to extend the registry with a custom prompt. * **Documentation** * Added an Extensions (Custom Prompts) section and an Extension Registry guide. * **Tests** * Added tests covering registration, duplicate handling/overwrite, invocation, and error cases. * **Chores** * Bumped package version and added/updated dev typing dependencies. <!-- end of auto-generated comment: release notes by coderabbit.ai -->
coderabbitai[bot] commented 2026-03-14 16:19:01 +00:00 (Migrated from github.com)

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review
📝 Walkthrough

Walkthrough

Adds a typed extension system: a public PromptConstructor type, an empty ExtensionRegistry interface for declaration merging, a runtime registry on MepCLI with register() and prompt(), new exports from the index, a truncate utils alias, plus example, docs, tests, and a package bump.

Changes

Cohort / File(s) Summary
Prompt base
src/base.ts
Added export type PromptConstructor<T, O> = new (options: O) => Prompt<T, O>; — new exported constructor type only.
Registry & runtime dispatch
src/core.ts
Added private static registry = new Map<string, any>(), static register(...) to store prompt constructors, and static prompt(...) to lookup, instantiate, and run registered prompts; typed against ExtensionRegistry and PromptConstructor.
Extension typing
src/types.ts
Added export interface ExtensionRegistry { } to enable consumer declaration merging for custom prompt types.
Public API / utils
src/index.ts, src/utils.ts
Exported ANSI, InputParser, Prompt and type PromptConstructor; re-exported stringWidth, truncate (alias for Layout.truncate), and stripAnsi.
Examples & tests
examples/extension-registry.ts, test/extension-registry.test.ts
New example ConfettiPrompt and tests demonstrating registration, duplicate overwrite warning, prompt invocation, and error for unregistered types; tests include a local module augmentation for ExtensionRegistry.
Docs
README.md, docs/.../extension-registry.md, docs/guides/custom-prompts.md, docs/README.md
Added extension registry documentation and links in README and docs (new guide, usage examples, and rationale).
Dev tooling
package.json
Bumped version to 2.0.0-beta.4; added @types/jest and updated @types/node.

Sequence Diagram(s)

sequenceDiagram
    participant Client as Client Code
    participant MepCLI as MepCLI
    participant PromptCls as Prompt Constructor
    participant PromptInst as Prompt Instance

    Client->>MepCLI: register(type, PromptCls)
    MepCLI-->>MepCLI: store PromptCls in registry
    Client->>MepCLI: prompt({ type, ...options })
    MepCLI->>MepCLI: lookup constructor by type
    MepCLI->>PromptCls: new PromptCls(options)
    PromptCls-->>PromptInst: instance created
    MepCLI->>PromptInst: run()
    PromptInst-->>MepCLI: Promise<result>
    MepCLI-->>Client: resolved result

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

Poem

🐰 I hopped to the registry, a tiny bright door,
New constructors nestled, ready to soar,
Types and prompts twirling in a merry spree,
I toss confetti — register, run, and see! 🎉

🚥 Pre-merge checks | 5
Passed checks (5 passed)
Check name Status Explanation
Description Check Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check Passed The title accurately and concisely describes the main feature addition—implementing an extension system—which aligns with the primary changeset focus.
Linked Issues check Passed The PR closes issue #23 by implementing a complete extension system with registry, type safety, documentation, examples, and tests as required.
Out of Scope Changes check Passed All changes are in-scope: core extension system implementation, public API exports, type definitions, examples, tests, documentation, and dependency updates directly support the extension system feature.
Docstring Coverage Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.

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

Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch feat/extension-system
📝 Coding Plan
  • Generate coding plan for human review comments

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

<!-- This is an auto-generated comment: summarize by coderabbit.ai --> <!-- This is an auto-generated comment: review paused by coderabbit.ai --> > [!NOTE] > ## Reviews paused > > It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the `reviews.auto_review.auto_pause_after_reviewed_commits` setting. > > Use the following commands to manage reviews: > - `@coderabbitai resume` to resume automatic reviews. > - `@coderabbitai review` to trigger a single review. > > Use the checkboxes below for quick actions: > - [ ] <!-- {"checkboxId": "7f6cc2e2-2e4e-497a-8c31-c9e4573e93d1"} --> ▶️ Resume reviews > - [ ] <!-- {"checkboxId": "e9bb8d72-00e8-4f67-9cb2-caf3b22574fe"} --> 🔍 Trigger review <!-- end of auto-generated comment: review paused by coderabbit.ai --> <!-- walkthrough_start --> <details> <summary>📝 Walkthrough</summary> ## Walkthrough Adds a typed extension system: a public `PromptConstructor` type, an empty `ExtensionRegistry` interface for declaration merging, a runtime registry on `MepCLI` with `register()` and `prompt()`, new exports from the index, a `truncate` utils alias, plus example, docs, tests, and a package bump. ## Changes |Cohort / File(s)|Summary| |---|---| |**Prompt base** <br> `src/base.ts`|Added `export type PromptConstructor<T, O> = new (options: O) => Prompt<T, O>;` — new exported constructor type only.| |**Registry & runtime dispatch** <br> `src/core.ts`|Added `private static registry = new Map<string, any>()`, `static register(...)` to store prompt constructors, and `static prompt(...)` to lookup, instantiate, and run registered prompts; typed against `ExtensionRegistry` and `PromptConstructor`.| |**Extension typing** <br> `src/types.ts`|Added `export interface ExtensionRegistry { }` to enable consumer declaration merging for custom prompt types.| |**Public API / utils** <br> `src/index.ts`, `src/utils.ts`|Exported `ANSI`, `InputParser`, `Prompt` and `type PromptConstructor`; re-exported `stringWidth`, `truncate` (alias for `Layout.truncate`), and `stripAnsi`.| |**Examples & tests** <br> `examples/extension-registry.ts`, `test/extension-registry.test.ts`|New example `ConfettiPrompt` and tests demonstrating registration, duplicate overwrite warning, prompt invocation, and error for unregistered types; tests include a local module augmentation for `ExtensionRegistry`.| |**Docs** <br> `README.md`, `docs/.../extension-registry.md`, `docs/guides/custom-prompts.md`, `docs/README.md`|Added extension registry documentation and links in README and docs (new guide, usage examples, and rationale).| |**Dev tooling** <br> `package.json`|Bumped version to `2.0.0-beta.4`; added `@types/jest` and updated `@types/node`.| ## Sequence Diagram(s) ```mermaid sequenceDiagram participant Client as Client Code participant MepCLI as MepCLI participant PromptCls as Prompt Constructor participant PromptInst as Prompt Instance Client->>MepCLI: register(type, PromptCls) MepCLI-->>MepCLI: store PromptCls in registry Client->>MepCLI: prompt({ type, ...options }) MepCLI->>MepCLI: lookup constructor by type MepCLI->>PromptCls: new PromptCls(options) PromptCls-->>PromptInst: instance created MepCLI->>PromptInst: run() PromptInst-->>MepCLI: Promise<result> MepCLI-->>Client: resolved result ``` ## Estimated code review effort 🎯 3 (Moderate) | ⏱️ ~25 minutes ## Poem > 🐰 I hopped to the registry, a tiny bright door, > New constructors nestled, ready to soar, > Types and prompts twirling in a merry spree, > I toss confetti — register, run, and see! 🎉 </details> <!-- walkthrough_end --> <!-- pre_merge_checks_walkthrough_start --> <details> <summary>🚥 Pre-merge checks | ✅ 5</summary> <details> <summary>✅ Passed checks (5 passed)</summary> | Check name | Status | Explanation | | :------------------------: | :------- | :---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | | Description Check | ✅ Passed | Check skipped - CodeRabbit’s high-level summary is enabled. | | Title check | ✅ Passed | The title accurately and concisely describes the main feature addition—implementing an extension system—which aligns with the primary changeset focus. | | Linked Issues check | ✅ Passed | The PR closes issue `#23` by implementing a complete extension system with registry, type safety, documentation, examples, and tests as required. | | Out of Scope Changes check | ✅ Passed | All changes are in-scope: core extension system implementation, public API exports, type definitions, examples, tests, documentation, and dependency updates directly support the extension system feature. | | Docstring Coverage | ✅ Passed | Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%. | </details> <sub>✏️ Tip: You can configure your own custom pre-merge checks in the settings.</sub> </details> <!-- pre_merge_checks_walkthrough_end --> <!-- finishing_touch_checkbox_start --> <details> <summary>✨ Finishing Touches</summary> <details> <summary>🧪 Generate unit tests (beta)</summary> - [ ] <!-- {"checkboxId": "f47ac10b-58cc-4372-a567-0e02b2c3d479", "radioGroupId": "utg-output-choice-group-unknown_comment_id"} --> Create PR with unit tests - [ ] <!-- {"checkboxId": "07f1e7d6-8a8e-4e23-9900-8731c2c87f58", "radioGroupId": "utg-output-choice-group-unknown_comment_id"} --> Post copyable unit tests in a comment - [ ] <!-- {"checkboxId": "6ba7b810-9dad-11d1-80b4-00c04fd430c8", "radioGroupId": "utg-output-choice-group-unknown_comment_id"} --> Commit unit tests in branch `feat/extension-system` </details> </details> <!-- finishing_touch_checkbox_end --> <!-- pr_review_plan_action_start --> <details> <summary>📝 Coding Plan</summary> - [ ] <!-- {"checkboxId": "6ad8a4e1-0b3a-4ea2-9b5b-d82c1f47d1f2"} --> Generate coding plan for human review comments </details> <!-- pr_review_plan_action_end --> <!-- tips_start --> --- <sub>Comment `@coderabbitai help` to get the list of available commands and usage tips.</sub> <!-- tips_end --> <!-- internal state start --> <!-- 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 --> <!-- internal state end -->
coderabbitai[bot] (Migrated from github.com) reviewed 2026-03-14 16:21:38 +00:00
coderabbitai[bot] (Migrated from github.com) left a comment
🧹 Nitpick comments (2)
src/types.ts (1)

5-6: Add JSDoc explaining the declaration merging pattern.

The empty interface enables TypeScript module augmentation for extensions, but consumers won't know how to use it without documentation.

📝 Proposed documentation
+/**
+ * Extension registry for custom prompts.
+ * Extend this interface via declaration merging to register custom prompt types:
+ *
+ * `@example`
+ * declare module 'mep' {
+ *   interface ExtensionRegistry {
+ *     myPrompt: { options: MyPromptOptions; result: string };
+ *   }
+ * }
+ * MepCLI.register('myPrompt', MyPromptClass);
+ * const result = await MepCLI.prompt({ type: 'myPrompt', message: '...' });
+ */
 export interface ExtensionRegistry {}
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/types.ts` around lines 5 - 6, Add a JSDoc block above the empty exported
interface ExtensionRegistry in src/types.ts that explains this is intentionally
empty to support TypeScript declaration merging/module augmentation for
extensions, briefly describe how consumers should augment it (using `declare
module` or `interface ExtensionRegistry { ... }` in their augmentation files),
and include a short example note of adding new extension keys/types so IDEs and
type-checking pick them up; reference the symbol ExtensionRegistry so reviewers
can find the spot to update.
src/core.ts (1)

95-102: Consider warning on duplicate registration.

The current implementation silently overwrites if the same type is registered twice. This could mask configuration errors where two extensions claim the same type key.

🔧 Optional: warn or throw on duplicate registration
 public static register<K extends keyof ExtensionRegistry>(
     type: K,
     promptClass: PromptConstructor<ExtensionRegistry[K]["result"], ExtensionRegistry[K]["options"]>
 ): void {
+    if (MepCLI.registry.has(type as string)) {
+        console.warn(`Warning: Overwriting existing registration for prompt type "${String(type)}".`);
+    }
     MepCLI.registry.set(type as string, promptClass);
 }
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/core.ts` around lines 95 - 102, The register method currently overwrites
existing entries in MepCLI.registry silently; update MepCLI.register to detect
duplicates by checking MepCLI.registry.has(type as string) before setting, and
either emit a clear warning (e.g., console.warn or a logger.warn) including the
conflicting type and existing constructor, or throw an Error to prevent
accidental overwrite; modify the body of register (referencing MepCLI.registry,
register, ExtensionRegistry, and PromptConstructor) to perform this check and
then proceed to MepCLI.registry.set(...) only if no duplicate (or after
logging/throwing as desired).
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Nitpick comments:
In `@src/core.ts`:
- Around line 95-102: The register method currently overwrites existing entries
in MepCLI.registry silently; update MepCLI.register to detect duplicates by
checking MepCLI.registry.has(type as string) before setting, and either emit a
clear warning (e.g., console.warn or a logger.warn) including the conflicting
type and existing constructor, or throw an Error to prevent accidental
overwrite; modify the body of register (referencing MepCLI.registry, register,
ExtensionRegistry, and PromptConstructor) to perform this check and then proceed
to MepCLI.registry.set(...) only if no duplicate (or after logging/throwing as
desired).

In `@src/types.ts`:
- Around line 5-6: Add a JSDoc block above the empty exported interface
ExtensionRegistry in src/types.ts that explains this is intentionally empty to
support TypeScript declaration merging/module augmentation for extensions,
briefly describe how consumers should augment it (using `declare module` or
`interface ExtensionRegistry { ... }` in their augmentation files), and include
a short example note of adding new extension keys/types so IDEs and
type-checking pick them up; reference the symbol ExtensionRegistry so reviewers
can find the spot to update.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: dd22002f-4700-41e9-beb7-14977f0228d9

📥 Commits

Reviewing files that changed from the base of the PR and between b275a73159 and 3ae5af4836.

📒 Files selected for processing (5)
  • src/base.ts
  • src/core.ts
  • src/index.ts
  • src/types.ts
  • src/utils.ts
<details> <summary>🧹 Nitpick comments (2)</summary><blockquote> <details> <summary>src/types.ts (1)</summary><blockquote> `5-6`: **Add JSDoc explaining the declaration merging pattern.** The empty interface enables TypeScript module augmentation for extensions, but consumers won't know how to use it without documentation. <details> <summary>📝 Proposed documentation</summary> ```diff +/** + * Extension registry for custom prompts. + * Extend this interface via declaration merging to register custom prompt types: + * + * `@example` + * declare module 'mep' { + * interface ExtensionRegistry { + * myPrompt: { options: MyPromptOptions; result: string }; + * } + * } + * MepCLI.register('myPrompt', MyPromptClass); + * const result = await MepCLI.prompt({ type: 'myPrompt', message: '...' }); + */ export interface ExtensionRegistry {} ``` </details> <details> <summary>🤖 Prompt for AI Agents</summary> ``` Verify each finding against the current code and only fix it if needed. In `@src/types.ts` around lines 5 - 6, Add a JSDoc block above the empty exported interface ExtensionRegistry in src/types.ts that explains this is intentionally empty to support TypeScript declaration merging/module augmentation for extensions, briefly describe how consumers should augment it (using `declare module` or `interface ExtensionRegistry { ... }` in their augmentation files), and include a short example note of adding new extension keys/types so IDEs and type-checking pick them up; reference the symbol ExtensionRegistry so reviewers can find the spot to update. ``` </details> </blockquote></details> <details> <summary>src/core.ts (1)</summary><blockquote> `95-102`: **Consider warning on duplicate registration.** The current implementation silently overwrites if the same `type` is registered twice. This could mask configuration errors where two extensions claim the same type key. <details> <summary>🔧 Optional: warn or throw on duplicate registration</summary> ```diff public static register<K extends keyof ExtensionRegistry>( type: K, promptClass: PromptConstructor<ExtensionRegistry[K]["result"], ExtensionRegistry[K]["options"]> ): void { + if (MepCLI.registry.has(type as string)) { + console.warn(`Warning: Overwriting existing registration for prompt type "${String(type)}".`); + } MepCLI.registry.set(type as string, promptClass); } ``` </details> <details> <summary>🤖 Prompt for AI Agents</summary> ``` Verify each finding against the current code and only fix it if needed. In `@src/core.ts` around lines 95 - 102, The register method currently overwrites existing entries in MepCLI.registry silently; update MepCLI.register to detect duplicates by checking MepCLI.registry.has(type as string) before setting, and either emit a clear warning (e.g., console.warn or a logger.warn) including the conflicting type and existing constructor, or throw an Error to prevent accidental overwrite; modify the body of register (referencing MepCLI.registry, register, ExtensionRegistry, and PromptConstructor) to perform this check and then proceed to MepCLI.registry.set(...) only if no duplicate (or after logging/throwing as desired). ``` </details> </blockquote></details> </blockquote></details> <details> <summary>🤖 Prompt for all review comments with AI agents</summary> ``` Verify each finding against the current code and only fix it if needed. Nitpick comments: In `@src/core.ts`: - Around line 95-102: The register method currently overwrites existing entries in MepCLI.registry silently; update MepCLI.register to detect duplicates by checking MepCLI.registry.has(type as string) before setting, and either emit a clear warning (e.g., console.warn or a logger.warn) including the conflicting type and existing constructor, or throw an Error to prevent accidental overwrite; modify the body of register (referencing MepCLI.registry, register, ExtensionRegistry, and PromptConstructor) to perform this check and then proceed to MepCLI.registry.set(...) only if no duplicate (or after logging/throwing as desired). In `@src/types.ts`: - Around line 5-6: Add a JSDoc block above the empty exported interface ExtensionRegistry in src/types.ts that explains this is intentionally empty to support TypeScript declaration merging/module augmentation for extensions, briefly describe how consumers should augment it (using `declare module` or `interface ExtensionRegistry { ... }` in their augmentation files), and include a short example note of adding new extension keys/types so IDEs and type-checking pick them up; reference the symbol ExtensionRegistry so reviewers can find the spot to update. ``` </details> --- <details> <summary>ℹ️ Review info</summary> <details> <summary>⚙️ Run configuration</summary> **Configuration used**: defaults **Review profile**: CHILL **Plan**: Pro **Run ID**: `dd22002f-4700-41e9-beb7-14977f0228d9` </details> <details> <summary>📥 Commits</summary> Reviewing files that changed from the base of the PR and between b275a73159d211aa251162db5217764c28eaffd1 and 3ae5af483682b75f7821f7de9a265a79b3dca3eb. </details> <details> <summary>📒 Files selected for processing (5)</summary> * `src/base.ts` * `src/core.ts` * `src/index.ts` * `src/types.ts` * `src/utils.ts` </details> </details> <!-- This is an auto-generated comment by CodeRabbit for review status -->
github-code-quality[bot] (Migrated from github.com) reviewed 2026-03-14 16:48:22 +00:00
@ -0,0 +1,113 @@
import { MepCLI } from '../src/core';
github-code-quality[bot] (Migrated from github.com) commented 2026-03-14 16:48:22 +00:00

Unused variable, import, function or class

Unused variable delay.


In general, the correct way to fix an unused variable warning is either to remove the declaration if it is truly unused, or to refactor code so that the variable is actually used if it was intended to be. For a test helper function in a unit test file, the usual fix is simply to delete it when it is no longer needed.

The best fix here, without changing existing functionality, is to remove the unused delay constant declaration entirely from test/extension-registry.test.ts. Since it is not referenced in the visible tests and is only a helper, deleting it will not affect the behavior of the tests. No other lines need to be adjusted, and no imports or type declarations depend on delay.

Concretely, in test/extension-registry.test.ts, delete line 34 that declares delay. No additional methods, imports, or definitions are required.

## Unused variable, import, function or class Unused variable delay. --- In general, the correct way to fix an unused variable warning is either to remove the declaration if it is truly unused, or to refactor code so that the variable is actually used if it was intended to be. For a test helper function in a unit test file, the usual fix is simply to delete it when it is no longer needed.</p> <p>The best fix here, without changing existing functionality, is to remove the unused <code>delay</code> constant declaration entirely from <code>test/extension-registry.test.ts</code>. Since it is not referenced in the visible tests and is only a helper, deleting it will not affect the behavior of the tests. No other lines need to be adjusted, and no imports or type declarations depend on <code>delay</code>.</p> <p>Concretely, in <code>test/extension-registry.test.ts</code>, delete line 34 that declares <code>delay</code>. No additional methods, imports, or definitions are required.
coderabbitai[bot] (Migrated from github.com) reviewed 2026-03-14 16:50:42 +00:00
coderabbitai[bot] (Migrated from github.com) left a comment
🧹 Nitpick comments (2)
test/extension-registry.test.ts (2)

34-34: Remove unused delay helper.

This function is defined but never used in the test suite.

🧹 Proposed fix
-const delay = (ms: number) => new Promise(resolve => setTimeout(resolve, ms));
-
 describe('Extension Registry', () => {
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@test/extension-registry.test.ts` at line 34, Remove the unused helper
function declaration "const delay = (ms: number) => new Promise(resolve =>
setTimeout(resolve, ms));" from the test file; locate the top-level "delay"
symbol in the test module (extension-registry.test.ts) and delete its definition
(or replace with actual awaited uses if it was intended to be used), ensuring no
other references remain and tests still compile.

91-95: Test relies on synchronous throw behavior.

This test works because the error is thrown synchronously before the Promise is created. If the implementation changes to validate asynchronously, this test would pass incorrectly (unhandled rejection instead of caught throw). Consider using expect(...).rejects.toThrow() for robustness.

♻️ Proposed improvement for async-safe error testing
-        it('should throw for an unregistered type', () => {
-            expect(() => {
-                MepCLI.prompt({ type: 'countdown', message: 'Test', from: 1 });
-            }).toThrow('Prompt type "countdown" is not registered.');
+        it('should throw for an unregistered type', async () => {
+            await expect(
+                MepCLI.prompt({ type: 'countdown', message: 'Test', from: 1 })
+            ).rejects.toThrow('Prompt type "countdown" is not registered.');
         });
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@test/extension-registry.test.ts` around lines 91 - 95, The test currently
asserts a synchronous throw from MepCLI.prompt which will miss async validation
paths; change the spec to treat MepCLI.prompt as a Promise and use an async-safe
assertion (e.g., await expect(MepCLI.prompt({ type: 'countdown', message:
'Test', from: 1 })).rejects.toThrow('Prompt type "countdown" is not
registered.')) so it correctly catches both synchronous and asynchronous
rejections; update the test case around the MepCLI.prompt invocation to
return/await the promise and use .rejects.toThrow to make the test robust.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Nitpick comments:
In `@test/extension-registry.test.ts`:
- Line 34: Remove the unused helper function declaration "const delay = (ms:
number) => new Promise(resolve => setTimeout(resolve, ms));" from the test file;
locate the top-level "delay" symbol in the test module
(extension-registry.test.ts) and delete its definition (or replace with actual
awaited uses if it was intended to be used), ensuring no other references remain
and tests still compile.
- Around line 91-95: The test currently asserts a synchronous throw from
MepCLI.prompt which will miss async validation paths; change the spec to treat
MepCLI.prompt as a Promise and use an async-safe assertion (e.g., await
expect(MepCLI.prompt({ type: 'countdown', message: 'Test', from: 1
})).rejects.toThrow('Prompt type "countdown" is not registered.')) so it
correctly catches both synchronous and asynchronous rejections; update the test
case around the MepCLI.prompt invocation to return/await the promise and use
.rejects.toThrow to make the test robust.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 2cc4728e-58e7-4e9c-8ec2-95b777ff3a82

📥 Commits

Reviewing files that changed from the base of the PR and between dd62c550e0 and 724cd3c193.

Files ignored due to path filters (1)
  • bun.lock is excluded by !**/*.lock
📒 Files selected for processing (3)
  • examples/extension-registry.ts
  • package.json
  • test/extension-registry.test.ts
<details> <summary>🧹 Nitpick comments (2)</summary><blockquote> <details> <summary>test/extension-registry.test.ts (2)</summary><blockquote> `34-34`: **Remove unused `delay` helper.** This function is defined but never used in the test suite. <details> <summary>🧹 Proposed fix</summary> ```diff -const delay = (ms: number) => new Promise(resolve => setTimeout(resolve, ms)); - describe('Extension Registry', () => { ``` </details> <details> <summary>🤖 Prompt for AI Agents</summary> ``` Verify each finding against the current code and only fix it if needed. In `@test/extension-registry.test.ts` at line 34, Remove the unused helper function declaration "const delay = (ms: number) => new Promise(resolve => setTimeout(resolve, ms));" from the test file; locate the top-level "delay" symbol in the test module (extension-registry.test.ts) and delete its definition (or replace with actual awaited uses if it was intended to be used), ensuring no other references remain and tests still compile. ``` </details> --- `91-95`: **Test relies on synchronous throw behavior.** This test works because the error is thrown synchronously before the Promise is created. If the implementation changes to validate asynchronously, this test would pass incorrectly (unhandled rejection instead of caught throw). Consider using `expect(...).rejects.toThrow()` for robustness. <details> <summary>♻️ Proposed improvement for async-safe error testing</summary> ```diff - it('should throw for an unregistered type', () => { - expect(() => { - MepCLI.prompt({ type: 'countdown', message: 'Test', from: 1 }); - }).toThrow('Prompt type "countdown" is not registered.'); + it('should throw for an unregistered type', async () => { + await expect( + MepCLI.prompt({ type: 'countdown', message: 'Test', from: 1 }) + ).rejects.toThrow('Prompt type "countdown" is not registered.'); }); ``` </details> <details> <summary>🤖 Prompt for AI Agents</summary> ``` Verify each finding against the current code and only fix it if needed. In `@test/extension-registry.test.ts` around lines 91 - 95, The test currently asserts a synchronous throw from MepCLI.prompt which will miss async validation paths; change the spec to treat MepCLI.prompt as a Promise and use an async-safe assertion (e.g., await expect(MepCLI.prompt({ type: 'countdown', message: 'Test', from: 1 })).rejects.toThrow('Prompt type "countdown" is not registered.')) so it correctly catches both synchronous and asynchronous rejections; update the test case around the MepCLI.prompt invocation to return/await the promise and use .rejects.toThrow to make the test robust. ``` </details> </blockquote></details> </blockquote></details> <details> <summary>🤖 Prompt for all review comments with AI agents</summary> ``` Verify each finding against the current code and only fix it if needed. Nitpick comments: In `@test/extension-registry.test.ts`: - Line 34: Remove the unused helper function declaration "const delay = (ms: number) => new Promise(resolve => setTimeout(resolve, ms));" from the test file; locate the top-level "delay" symbol in the test module (extension-registry.test.ts) and delete its definition (or replace with actual awaited uses if it was intended to be used), ensuring no other references remain and tests still compile. - Around line 91-95: The test currently asserts a synchronous throw from MepCLI.prompt which will miss async validation paths; change the spec to treat MepCLI.prompt as a Promise and use an async-safe assertion (e.g., await expect(MepCLI.prompt({ type: 'countdown', message: 'Test', from: 1 })).rejects.toThrow('Prompt type "countdown" is not registered.')) so it correctly catches both synchronous and asynchronous rejections; update the test case around the MepCLI.prompt invocation to return/await the promise and use .rejects.toThrow to make the test robust. ``` </details> --- <details> <summary>ℹ️ Review info</summary> <details> <summary>⚙️ Run configuration</summary> **Configuration used**: defaults **Review profile**: CHILL **Plan**: Pro **Run ID**: `2cc4728e-58e7-4e9c-8ec2-95b777ff3a82` </details> <details> <summary>📥 Commits</summary> Reviewing files that changed from the base of the PR and between dd62c550e0bb9e84903df94f52cacadc4ee57edf and 724cd3c1932a6707fb25b0caf5bc7314ad626629. </details> <details> <summary>⛔ Files ignored due to path filters (1)</summary> * `bun.lock` is excluded by `!**/*.lock` </details> <details> <summary>📒 Files selected for processing (3)</summary> * `examples/extension-registry.ts` * `package.json` * `test/extension-registry.test.ts` </details> </details> <!-- This is an auto-generated comment by CodeRabbit for review status -->
coderabbitai[bot] (Migrated from github.com) reviewed 2026-03-14 17:17:30 +00:00
coderabbitai[bot] (Migrated from github.com) left a comment

Actionable comments posted: 1

🧹 Nitpick comments (3)
test/extension-registry.test.ts (2)

32-35: Minor: Remove extra blank lines.

Lines 34-35 appear to be residual blank lines, possibly from removing the previously flagged unused delay variable. Consider removing the extra blank line to keep formatting consistent.

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

In `@test/extension-registry.test.ts` around lines 32 - 35, Remove the two
residual blank lines near the end of test/extension-registry.test.ts (the extra
empty lines at the end of the file after the test block); edit the file to
delete those blank lines so there are no trailing blank lines and formatting is
consistent.

67-75: Consider consistent spy cleanup pattern.

The spy on console.warn is not captured, relying on jest.restoreAllMocks() at the end. This differs from the pattern in lines 55-65 where warnSpy is captured and explicitly restored. If the test fails before reaching jest.restoreAllMocks(), the mock may leak.

Consider either capturing the spy consistently, or moving jest.restoreAllMocks() to afterEach for guaranteed cleanup.

♻️ Option: Add global cleanup in afterEach
     afterEach(() => {
         stdoutSpy.mockRestore();
+        jest.restoreAllMocks();
     });

Then individual test cleanup becomes unnecessary:

         it('should overwrite the existing entry after warning', () => {
             jest.spyOn(console, 'warn').mockImplementation(() => { });

             MepCLI.register('countdown', CountdownPrompt);
             MepCLI.register('countdown', AltCountdownPrompt);

             expect((MepCLI as any).registry.get('countdown')).toBe(AltCountdownPrompt);
-            jest.restoreAllMocks();
         });
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@test/extension-registry.test.ts` around lines 67 - 75, The test "should
overwrite the existing entry after warning" uses jest.spyOn(console, 'warn') but
doesn't capture the returned spy for deterministic cleanup; update this test to
follow the pattern used earlier by assigning the spy to a variable (e.g., const
warnSpy = jest.spyOn(console, 'warn').mockImplementation(() => {})) and then
call warnSpy.mockRestore() at the end of the test, or alternatively add a global
afterEach(() => jest.restoreAllMocks()) so MepCLI.register and console.warn
spies are always cleaned up; ensure references to MepCLI.register,
CountdownPrompt, AltCountdownPrompt, and console.warn remain correct.
examples/extension-registry.ts (1)

85-99: Consider using or removing the intensity option.

The intensity: 4 option is passed at line 89 but ConfettiPrompt never reads this.options.intensity. This may confuse developers using this example as a template.

Either implement the intensity behavior (e.g., adjust animation speed or confetti density) or remove the unused option from the example call.

♻️ Option A: Remove unused option
     const result = await MepCLI.prompt({
         type: 'confetti',
         message: 'Congratulations on your new extension!',
-        intensity: 4,
     });
♻️ Option B: Use intensity in the implementation
     protected render(firstRender: boolean): void {
         const width = this.stdout.columns || 60;
+        const intensity = this.options.intensity ?? 3;
         
         // Build a rotating emoji line
-        const safeWidth = Math.min(width - 5, 40); // Keep it safe for Windows bounds
+        const safeWidth = Math.min(width - 5, 20 + (intensity * 8)); // Scale width by intensity
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@examples/extension-registry.ts` around lines 85 - 99, The example passes
intensity: 4 to MepCLI.prompt but the ConfettiPrompt implementation never reads
this.options.intensity; either remove the unused option from the example call to
MepCLI.prompt, or update the ConfettiPrompt class (e.g., constructor or render
method in ConfettiPrompt) to read this.options.intensity and apply it to
confetti behavior (animation speed, spawn rate, or particle count) so the
provided option has effect; look for the MepCLI.prompt call in the example and
the ConfettiPrompt class/methods to make the corresponding change.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@examples/extension-registry.ts`:
- Line 28: The field declaration using ReturnType<typeof NodeJS.setInterval> is
invalid TypeScript; update the interval property type to use the correct
NodeJS.Timeout type used elsewhere (e.g., in
spinner.ts/tasks.ts/prompts/wait.ts). Locate the private interval? declaration
in the class and replace its type annotation so it reads as an optional
NodeJS.Timeout, ensuring imports or ambient types remain consistent with the
rest of the codebase.

---

Nitpick comments:
In `@examples/extension-registry.ts`:
- Around line 85-99: The example passes intensity: 4 to MepCLI.prompt but the
ConfettiPrompt implementation never reads this.options.intensity; either remove
the unused option from the example call to MepCLI.prompt, or update the
ConfettiPrompt class (e.g., constructor or render method in ConfettiPrompt) to
read this.options.intensity and apply it to confetti behavior (animation speed,
spawn rate, or particle count) so the provided option has effect; look for the
MepCLI.prompt call in the example and the ConfettiPrompt class/methods to make
the corresponding change.

In `@test/extension-registry.test.ts`:
- Around line 32-35: Remove the two residual blank lines near the end of
test/extension-registry.test.ts (the extra empty lines at the end of the file
after the test block); edit the file to delete those blank lines so there are no
trailing blank lines and formatting is consistent.
- Around line 67-75: The test "should overwrite the existing entry after
warning" uses jest.spyOn(console, 'warn') but doesn't capture the returned spy
for deterministic cleanup; update this test to follow the pattern used earlier
by assigning the spy to a variable (e.g., const warnSpy = jest.spyOn(console,
'warn').mockImplementation(() => {})) and then call warnSpy.mockRestore() at the
end of the test, or alternatively add a global afterEach(() =>
jest.restoreAllMocks()) so MepCLI.register and console.warn spies are always
cleaned up; ensure references to MepCLI.register, CountdownPrompt,
AltCountdownPrompt, and console.warn remain correct.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 2db53302-5ecf-41aa-903d-f56c81f40d09

📥 Commits

Reviewing files that changed from the base of the PR and between 724cd3c193 and 11e2e2b645.

📒 Files selected for processing (2)
  • examples/extension-registry.ts
  • test/extension-registry.test.ts
**Actionable comments posted: 1** <details> <summary>🧹 Nitpick comments (3)</summary><blockquote> <details> <summary>test/extension-registry.test.ts (2)</summary><blockquote> `32-35`: **Minor: Remove extra blank lines.** Lines 34-35 appear to be residual blank lines, possibly from removing the previously flagged unused `delay` variable. Consider removing the extra blank line to keep formatting consistent. <details> <summary>🤖 Prompt for AI Agents</summary> ``` Verify each finding against the current code and only fix it if needed. In `@test/extension-registry.test.ts` around lines 32 - 35, Remove the two residual blank lines near the end of test/extension-registry.test.ts (the extra empty lines at the end of the file after the test block); edit the file to delete those blank lines so there are no trailing blank lines and formatting is consistent. ``` </details> --- `67-75`: **Consider consistent spy cleanup pattern.** The spy on `console.warn` is not captured, relying on `jest.restoreAllMocks()` at the end. This differs from the pattern in lines 55-65 where `warnSpy` is captured and explicitly restored. If the test fails before reaching `jest.restoreAllMocks()`, the mock may leak. Consider either capturing the spy consistently, or moving `jest.restoreAllMocks()` to `afterEach` for guaranteed cleanup. <details> <summary>♻️ Option: Add global cleanup in afterEach</summary> ```diff afterEach(() => { stdoutSpy.mockRestore(); + jest.restoreAllMocks(); }); ``` Then individual test cleanup becomes unnecessary: ```diff it('should overwrite the existing entry after warning', () => { jest.spyOn(console, 'warn').mockImplementation(() => { }); MepCLI.register('countdown', CountdownPrompt); MepCLI.register('countdown', AltCountdownPrompt); expect((MepCLI as any).registry.get('countdown')).toBe(AltCountdownPrompt); - jest.restoreAllMocks(); }); ``` </details> <details> <summary>🤖 Prompt for AI Agents</summary> ``` Verify each finding against the current code and only fix it if needed. In `@test/extension-registry.test.ts` around lines 67 - 75, The test "should overwrite the existing entry after warning" uses jest.spyOn(console, 'warn') but doesn't capture the returned spy for deterministic cleanup; update this test to follow the pattern used earlier by assigning the spy to a variable (e.g., const warnSpy = jest.spyOn(console, 'warn').mockImplementation(() => {})) and then call warnSpy.mockRestore() at the end of the test, or alternatively add a global afterEach(() => jest.restoreAllMocks()) so MepCLI.register and console.warn spies are always cleaned up; ensure references to MepCLI.register, CountdownPrompt, AltCountdownPrompt, and console.warn remain correct. ``` </details> </blockquote></details> <details> <summary>examples/extension-registry.ts (1)</summary><blockquote> `85-99`: **Consider using or removing the `intensity` option.** The `intensity: 4` option is passed at line 89 but `ConfettiPrompt` never reads `this.options.intensity`. This may confuse developers using this example as a template. Either implement the intensity behavior (e.g., adjust animation speed or confetti density) or remove the unused option from the example call. <details> <summary>♻️ Option A: Remove unused option</summary> ```diff const result = await MepCLI.prompt({ type: 'confetti', message: 'Congratulations on your new extension!', - intensity: 4, }); ``` </details> <details> <summary>♻️ Option B: Use intensity in the implementation</summary> ```diff protected render(firstRender: boolean): void { const width = this.stdout.columns || 60; + const intensity = this.options.intensity ?? 3; // Build a rotating emoji line - const safeWidth = Math.min(width - 5, 40); // Keep it safe for Windows bounds + const safeWidth = Math.min(width - 5, 20 + (intensity * 8)); // Scale width by intensity ``` </details> <details> <summary>🤖 Prompt for AI Agents</summary> ``` Verify each finding against the current code and only fix it if needed. In `@examples/extension-registry.ts` around lines 85 - 99, The example passes intensity: 4 to MepCLI.prompt but the ConfettiPrompt implementation never reads this.options.intensity; either remove the unused option from the example call to MepCLI.prompt, or update the ConfettiPrompt class (e.g., constructor or render method in ConfettiPrompt) to read this.options.intensity and apply it to confetti behavior (animation speed, spawn rate, or particle count) so the provided option has effect; look for the MepCLI.prompt call in the example and the ConfettiPrompt class/methods to make the corresponding change. ``` </details> </blockquote></details> </blockquote></details> <details> <summary>🤖 Prompt for all review comments with AI agents</summary> ``` Verify each finding against the current code and only fix it if needed. Inline comments: In `@examples/extension-registry.ts`: - Line 28: The field declaration using ReturnType<typeof NodeJS.setInterval> is invalid TypeScript; update the interval property type to use the correct NodeJS.Timeout type used elsewhere (e.g., in spinner.ts/tasks.ts/prompts/wait.ts). Locate the private interval? declaration in the class and replace its type annotation so it reads as an optional NodeJS.Timeout, ensuring imports or ambient types remain consistent with the rest of the codebase. --- Nitpick comments: In `@examples/extension-registry.ts`: - Around line 85-99: The example passes intensity: 4 to MepCLI.prompt but the ConfettiPrompt implementation never reads this.options.intensity; either remove the unused option from the example call to MepCLI.prompt, or update the ConfettiPrompt class (e.g., constructor or render method in ConfettiPrompt) to read this.options.intensity and apply it to confetti behavior (animation speed, spawn rate, or particle count) so the provided option has effect; look for the MepCLI.prompt call in the example and the ConfettiPrompt class/methods to make the corresponding change. In `@test/extension-registry.test.ts`: - Around line 32-35: Remove the two residual blank lines near the end of test/extension-registry.test.ts (the extra empty lines at the end of the file after the test block); edit the file to delete those blank lines so there are no trailing blank lines and formatting is consistent. - Around line 67-75: The test "should overwrite the existing entry after warning" uses jest.spyOn(console, 'warn') but doesn't capture the returned spy for deterministic cleanup; update this test to follow the pattern used earlier by assigning the spy to a variable (e.g., const warnSpy = jest.spyOn(console, 'warn').mockImplementation(() => {})) and then call warnSpy.mockRestore() at the end of the test, or alternatively add a global afterEach(() => jest.restoreAllMocks()) so MepCLI.register and console.warn spies are always cleaned up; ensure references to MepCLI.register, CountdownPrompt, AltCountdownPrompt, and console.warn remain correct. ``` </details> --- <details> <summary>ℹ️ Review info</summary> <details> <summary>⚙️ Run configuration</summary> **Configuration used**: defaults **Review profile**: CHILL **Plan**: Pro **Run ID**: `2db53302-5ecf-41aa-903d-f56c81f40d09` </details> <details> <summary>📥 Commits</summary> Reviewing files that changed from the base of the PR and between 724cd3c1932a6707fb25b0caf5bc7314ad626629 and 11e2e2b64502065c3543c3fa1c8e08f67cf109c8. </details> <details> <summary>📒 Files selected for processing (2)</summary> * `examples/extension-registry.ts` * `test/extension-registry.test.ts` </details> </details> <!-- This is an auto-generated comment by CodeRabbit for review status -->
@ -0,0 +1,101 @@
/**
coderabbitai[bot] (Migrated from github.com) commented 2026-03-14 17:17:29 +00:00

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Verify if the current syntax compiles without errors
# Check TypeScript compilation for this file
fd -t f 'tsconfig' --exec cat {} \;
echo "---"
# Try to find if there are any type definitions that might make NodeJS.setInterval valid
rg -n "setInterval" --type ts -g '*.d.ts' | head -20

Repository: CodeTease/mep

Length of output: 803


🏁 Script executed:

cat -n examples/extension-registry.ts | head -40

Repository: CodeTease/mep

Length of output: 1640


🏁 Script executed:

# Check if there are any TypeScript compilation errors in the file
# Also search for how 'interval' is used in the codebase
rg -n "interval" examples/extension-registry.ts

Repository: CodeTease/mep

Length of output: 297


🏁 Script executed:

# Check if NodeJS.setInterval exists by looking at node types
rg -n "NodeJS.*setInterval|setInterval" --type ts

Repository: CodeTease/mep

Length of output: 718


🏁 Script executed:

# Check if there are any error logs or build outputs
git log --oneline -10 2>/dev/null | head -5

Repository: CodeTease/mep

Length of output: 111


🏁 Script executed:

# Look at the imports and how other parts of the codebase handle interval typing
rg -A2 -B2 "setInterval\|Timeout" src/ --type ts | head -40

Repository: CodeTease/mep

Length of output: 39


🏁 Script executed:

# Check package.json to see if there's any TypeScript compilation info
cat package.json | jq '.scripts' 2>/dev/null || cat package.json | grep -A5 '"scripts"'

Repository: CodeTease/mep

Length of output: 427


🏁 Script executed:

# Check how other files in src handle the interval/timer type declaration
rg -B5 "this\.timer = setInterval|this\.spinnerTimer = setInterval" src/ --type ts | head -50

Repository: CodeTease/mep

Length of output: 1118


🏁 Script executed:

# Look at spinner.ts specifically to see how it declares the timer property
cat -n src/spinner.ts | sed -n '1,40p'

Repository: CodeTease/mep

Length of output: 1224


🏁 Script executed:

# Check if NodeJS.Timeout is used anywhere in the codebase
rg "NodeJS\.Timeout" --type ts

Repository: CodeTease/mep

Length of output: 510


Invalid TypeScript syntax: typeof NodeJS.setInterval does not exist.

NodeJS.setInterval is not a valid property—setInterval is a global function, not part of the NodeJS namespace. This line will produce a TypeScript compilation error. The correct type for the return value of setInterval() is NodeJS.Timeout, which is consistently used throughout the codebase (e.g., src/spinner.ts, src/tasks.ts, src/prompts/wait.ts).

🐛 Fix
-    private interval?: ReturnType<typeof NodeJS.setInterval>;
+    private interval?: NodeJS.Timeout;
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

    private interval?: NodeJS.Timeout;
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@examples/extension-registry.ts` at line 28, The field declaration using
ReturnType<typeof NodeJS.setInterval> is invalid TypeScript; update the interval
property type to use the correct NodeJS.Timeout type used elsewhere (e.g., in
spinner.ts/tasks.ts/prompts/wait.ts). Locate the private interval? declaration
in the class and replace its type annotation so it reads as an optional
NodeJS.Timeout, ensuring imports or ambient types remain consistent with the
rest of the codebase.

Addressed in commits 610e390 to f648265

_⚠️ Potential issue_ | _🟠 Major_ <details> <summary>🧩 Analysis chain</summary> 🏁 Script executed: ```shell #!/bin/bash # Verify if the current syntax compiles without errors # Check TypeScript compilation for this file fd -t f 'tsconfig' --exec cat {} \; echo "---" # Try to find if there are any type definitions that might make NodeJS.setInterval valid rg -n "setInterval" --type ts -g '*.d.ts' | head -20 ``` Repository: CodeTease/mep Length of output: 803 --- 🏁 Script executed: ```shell cat -n examples/extension-registry.ts | head -40 ``` Repository: CodeTease/mep Length of output: 1640 --- 🏁 Script executed: ```shell # Check if there are any TypeScript compilation errors in the file # Also search for how 'interval' is used in the codebase rg -n "interval" examples/extension-registry.ts ``` Repository: CodeTease/mep Length of output: 297 --- 🏁 Script executed: ```shell # Check if NodeJS.setInterval exists by looking at node types rg -n "NodeJS.*setInterval|setInterval" --type ts ``` Repository: CodeTease/mep Length of output: 718 --- 🏁 Script executed: ```shell # Check if there are any error logs or build outputs git log --oneline -10 2>/dev/null | head -5 ``` Repository: CodeTease/mep Length of output: 111 --- 🏁 Script executed: ```shell # Look at the imports and how other parts of the codebase handle interval typing rg -A2 -B2 "setInterval\|Timeout" src/ --type ts | head -40 ``` Repository: CodeTease/mep Length of output: 39 --- 🏁 Script executed: ```shell # Check package.json to see if there's any TypeScript compilation info cat package.json | jq '.scripts' 2>/dev/null || cat package.json | grep -A5 '"scripts"' ``` Repository: CodeTease/mep Length of output: 427 --- 🏁 Script executed: ```shell # Check how other files in src handle the interval/timer type declaration rg -B5 "this\.timer = setInterval|this\.spinnerTimer = setInterval" src/ --type ts | head -50 ``` Repository: CodeTease/mep Length of output: 1118 --- 🏁 Script executed: ```shell # Look at spinner.ts specifically to see how it declares the timer property cat -n src/spinner.ts | sed -n '1,40p' ``` Repository: CodeTease/mep Length of output: 1224 --- 🏁 Script executed: ```shell # Check if NodeJS.Timeout is used anywhere in the codebase rg "NodeJS\.Timeout" --type ts ``` Repository: CodeTease/mep Length of output: 510 --- </details> **Invalid TypeScript syntax: `typeof NodeJS.setInterval` does not exist.** `NodeJS.setInterval` is not a valid property—`setInterval` is a global function, not part of the `NodeJS` namespace. This line will produce a TypeScript compilation error. The correct type for the return value of `setInterval()` is `NodeJS.Timeout`, which is consistently used throughout the codebase (e.g., `src/spinner.ts`, `src/tasks.ts`, `src/prompts/wait.ts`). <details> <summary>🐛 Fix</summary> ```diff - private interval?: ReturnType<typeof NodeJS.setInterval>; + private interval?: NodeJS.Timeout; ``` </details> <!-- suggestion_start --> <details> <summary>📝 Committable suggestion</summary> > ‼️ **IMPORTANT** > Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements. ```suggestion private interval?: NodeJS.Timeout; ``` </details> <!-- suggestion_end --> <details> <summary>🤖 Prompt for AI Agents</summary> ``` Verify each finding against the current code and only fix it if needed. In `@examples/extension-registry.ts` at line 28, The field declaration using ReturnType<typeof NodeJS.setInterval> is invalid TypeScript; update the interval property type to use the correct NodeJS.Timeout type used elsewhere (e.g., in spinner.ts/tasks.ts/prompts/wait.ts). Locate the private interval? declaration in the class and replace its type annotation so it reads as an optional NodeJS.Timeout, ensuring imports or ambient types remain consistent with the rest of the codebase. ``` </details> <!-- fingerprinting:phantom:poseidon:ocelot --> <!-- This is an auto-generated comment by CodeRabbit --> ✅ Addressed in commits 610e390 to f648265
irammini commented 2026-03-14 17:38:50 +00:00 (Migrated from github.com)

@coderabbitai review

@coderabbitai review
coderabbitai[bot] commented 2026-03-14 17:39:00 +00:00 (Migrated from github.com)
Actions performed

Review triggered.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

<!-- This is an auto-generated reply by CodeRabbit --> <details> <summary>✅ Actions performed</summary> Review triggered. > Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused. </details>
coderabbitai[bot] (Migrated from github.com) reviewed 2026-03-14 17:41:12 +00:00
coderabbitai[bot] (Migrated from github.com) left a comment
🧹 Nitpick comments (1)
docs/guides/extension-registry.md (1)

68-69: Use the public import path instead of deep internal path.

Line 68 uses mepcli/dist/base, which is an internal implementation detail. Change to import { Prompt } from 'mepcli' to reference the stable public API exported in src/index.ts.

Suggested change
-import { Prompt } from 'mepcli/dist/base';
+import { Prompt } from 'mepcli';
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@docs/guides/extension-registry.md` around lines 68 - 69, Replace the deep
import "mepcli/dist/base" with the public package entry point by changing the
import of Prompt to use "mepcli" (i.e., import { Prompt } from 'mepcli') so the
code references the stable public API (symbol: Prompt) instead of internal
implementation paths.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Nitpick comments:
In `@docs/guides/extension-registry.md`:
- Around line 68-69: Replace the deep import "mepcli/dist/base" with the public
package entry point by changing the import of Prompt to use "mepcli" (i.e.,
import { Prompt } from 'mepcli') so the code references the stable public API
(symbol: Prompt) instead of internal implementation paths.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 9d746738-a5a4-4404-b4b8-8c516adcebaf

📥 Commits

Reviewing files that changed from the base of the PR and between 724cd3c193 and 71c4fbd871.

Files ignored due to path filters (1)
  • bun.lock is excluded by !**/*.lock
📒 Files selected for processing (7)
  • README.md
  • docs/README.md
  • docs/guides/custom-prompts.md
  • docs/guides/extension-registry.md
  • examples/extension-registry.ts
  • package.json
  • test/extension-registry.test.ts
Files skipped from review due to trivial changes (1)
  • README.md
🚧 Files skipped from review as they are similar to previous changes (2)
  • test/extension-registry.test.ts
  • examples/extension-registry.ts
<details> <summary>🧹 Nitpick comments (1)</summary><blockquote> <details> <summary>docs/guides/extension-registry.md (1)</summary><blockquote> `68-69`: **Use the public import path instead of deep internal path.** Line 68 uses `mepcli/dist/base`, which is an internal implementation detail. Change to `import { Prompt } from 'mepcli'` to reference the stable public API exported in src/index.ts. <details> <summary>Suggested change</summary> ```diff -import { Prompt } from 'mepcli/dist/base'; +import { Prompt } from 'mepcli'; ``` </details> <details> <summary>🤖 Prompt for AI Agents</summary> ``` Verify each finding against the current code and only fix it if needed. In `@docs/guides/extension-registry.md` around lines 68 - 69, Replace the deep import "mepcli/dist/base" with the public package entry point by changing the import of Prompt to use "mepcli" (i.e., import { Prompt } from 'mepcli') so the code references the stable public API (symbol: Prompt) instead of internal implementation paths. ``` </details> </blockquote></details> </blockquote></details> <details> <summary>🤖 Prompt for all review comments with AI agents</summary> ``` Verify each finding against the current code and only fix it if needed. Nitpick comments: In `@docs/guides/extension-registry.md`: - Around line 68-69: Replace the deep import "mepcli/dist/base" with the public package entry point by changing the import of Prompt to use "mepcli" (i.e., import { Prompt } from 'mepcli') so the code references the stable public API (symbol: Prompt) instead of internal implementation paths. ``` </details> --- <details> <summary>ℹ️ Review info</summary> <details> <summary>⚙️ Run configuration</summary> **Configuration used**: defaults **Review profile**: CHILL **Plan**: Pro **Run ID**: `9d746738-a5a4-4404-b4b8-8c516adcebaf` </details> <details> <summary>📥 Commits</summary> Reviewing files that changed from the base of the PR and between 724cd3c1932a6707fb25b0caf5bc7314ad626629 and 71c4fbd8717b116d325cfd927b5b947c6ba54d66. </details> <details> <summary>⛔ Files ignored due to path filters (1)</summary> * `bun.lock` is excluded by `!**/*.lock` </details> <details> <summary>📒 Files selected for processing (7)</summary> * `README.md` * `docs/README.md` * `docs/guides/custom-prompts.md` * `docs/guides/extension-registry.md` * `examples/extension-registry.ts` * `package.json` * `test/extension-registry.test.ts` </details> <details> <summary>✅ Files skipped from review due to trivial changes (1)</summary> * README.md </details> <details> <summary>🚧 Files skipped from review as they are similar to previous changes (2)</summary> * test/extension-registry.test.ts * examples/extension-registry.ts </details> </details> <!-- This is an auto-generated comment by CodeRabbit for review status -->
Sign in to join this conversation.
No description provided.