Skip to content

Init script now installs MCP servers#979

Merged
N2D4 merged 5 commits intodevfrom
init-mcp
Oct 24, 2025
Merged

Init script now installs MCP servers#979
N2D4 merged 5 commits intodevfrom
init-mcp

Conversation

@N2D4
Copy link
Contributor

@N2D4 N2D4 commented Oct 24, 2025

Summary by CodeRabbit

  • New Features

    • Git workspace readiness check before install with a skip option.
    • Configure and update multiple editors/IDEs (Cursor, VS Code, Claude, Windsurf, Gemini).
    • Deferred command execution for post-write operations and visible file-change tracking.
    • Safer config updates with dry-run support, backups, and enhanced verbose diagnostics for troubleshooting.
  • Chores

    • Test/run scripts updated to include a new --no-warn-uncommitted-changes flag.

Copilot AI review requested due to automatic review settings October 24, 2025 20:57
@cursor
Copy link

cursor bot commented Oct 24, 2025

You have run out of free Bugbot PR reviews for this billing cycle. This will reset on November 10.

To receive reviews on all of your PRs, visit the Cursor dashboard to activate Pro and start your 14-day free trial.

@vercel
Copy link

vercel bot commented Oct 24, 2025

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Preview Comments Updated (UTC)
stack-backend Ready Ready Preview Comment Oct 24, 2025 9:56pm
stack-dashboard Ready Ready Preview Comment Oct 24, 2025 9:56pm
stack-demo Ready Ready Preview Comment Oct 24, 2025 9:56pm
stack-docs Ready Ready Preview Comment Oct 24, 2025 9:56pm

@coderabbitai
Copy link
Contributor

coderabbitai bot commented Oct 24, 2025

Note

Other AI code review bot(s) detected

CodeRabbit has detected other AI code review bot(s) in this pull request and will avoid duplicating their findings in the review comments. This may lead to a less comprehensive review.

Walkthrough

Adds verbose logging and utilities, a pre-install Git workspace readiness check and new CLI flag (--no-warn-uncommitted-changes), deferred command scheduling and file-change recording, a new MCP configuration scheduler for multiple editor targets, and updates test-run scripts to include the new flag.

Changes

Cohort / File(s) Summary
Test-run command flags
packages/init-stack/package.json
Added --no-warn-uncommitted-changes to several test-run-* scripts while preserving existing flags (--js, --server, --npm, --no-browser).
Core initialization & verbose instrumentation
packages/init-stack/src/index.ts
Added verbose logging instrumentation, pre-install Git workspace readiness check (skip via --no-warn-uncommitted-changes), deferred command scheduling/execution, recordFileChange, registration of write handlers, and re-exported templateIdentity.
MCP configuration scheduler (new)
packages/init-stack/src/mcp.ts
New module exporting scheduleMcpConfiguration(ctx) to schedule safe JSON updates across Cursor, VS Code, Claude, Windsurf, and Gemini targets; includes JSON read/merge/write pipeline, backup writes, CLI probing, path resolution, dry-run support, and registers writes with scheduler context.
Utility module (new)
packages/init-stack/src/util.ts
New utilities: configurable verbose logging (configureVerboseLogging, getVerboseLevel, logVerbose), color/template helpers (Colorize, templateIdentity), object helper omit, command resolution getCommandPath, and config-write decision helper shouldWriteConfigFile.

Sequence Diagram(s)

sequenceDiagram
    participant CLI as init-stack (index.ts)
    participant Git as Git workspace check
    participant MCP as MCP scheduler (mcp.ts)
    participant Files as File writer pipeline
    participant Cmds as Deferred commands
    participant Util as util.ts

    CLI->>Git: ensureGitWorkspaceIsReady()
    alt Uncommitted changes
        Git-->>CLI: warn / prompt / error (mode-dependent)
    else Clean
        Git-->>CLI: proceed
    end

    CLI->>MCP: scheduleMcpConfiguration(ctx)
    MCP->>Files: scheduleJsonFileUpdate(targets...)
    Files->>Files: read JSON -> apply updater -> diff -> backup+write
    Files-->>MCP: registerWriteHandler() & recordFileChange()
    CLI->>Cmds: runDeferredCommands()
    Cmds->>Cmds: execute scheduled commands (async)
    note right of Util: logVerbose invoked throughout flows
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

  • Pay attention to: packages/init-stack/src/mcp.ts (JSON merge/write safety, cross-OS paths, CLI probing).
  • packages/init-stack/src/index.ts (deferred command flow, write handler registration, Git-check branching and prompts).
  • packages/init-stack/src/util.ts (command resolution and logging configuration side effects).
  • packages/init-stack/package.json (ensure CI/local script behavior with new flag).

Possibly related PRs

Suggested reviewers

  • N2D4

"I hopped through lines with twitchy paws,
verbose carrots strewn across my laws.
MCP servers tucked in neat arrays,
deferred commands pranced in happy days.
A bunny's cheer for cleaner, brighter ways." 🐇✨

Pre-merge checks and finishing touches

❌ Failed checks (2 warnings)
Check name Status Explanation Resolution
Description Check ⚠️ Warning The pull request description contains only the repository's contribution guideline template placeholder (an HTML comment referencing CONTRIBUTING.md) with no actual content added by the author. While the template itself is minimal, the author has not provided any description of the changes, their purpose, testing approach, or potential impacts. A meaningful pull request description should include at least a brief explanation of what is being changed and why, which is entirely absent here. Please add a substantive pull request description that explains the changes being made (adding MCP server configuration to the init script), the motivation behind these changes, which editors/environments are now supported, and any testing or validation performed. At minimum, describe what MCP configuration is being scheduled and why this integration is important for the initialization flow.
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
✅ Passed checks (1 passed)
Check name Status Explanation
Title Check ✅ Passed The title "Init script now installs MCP servers" directly and accurately summarizes the primary change in this pull request. The changeset introduces a new MCP configuration module (src/mcp.ts), integrates MCP scheduling into the main init script (src/index.ts), and enables the init script to configure MCP servers across multiple editor environments (Cursor, VS Code, Claude, Windsurf, Gemini). The title is concise, specific, and clearly conveys the main objective without unnecessary noise. The branch name "init-mcp" and the substantial additions to support MCP scheduling align well with this title.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch init-mcp

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

❤️ Share

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

Copy link

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull Request Overview

This PR enhances the init-stack script to automatically install and configure MCP (Model Context Protocol) servers for various AI-powered code editors. It adds verbose logging capabilities throughout the initialization process, implements Git workspace checking to warn users about uncommitted changes, and refactors shared utility functions into a separate module.

  • Added MCP server configuration for Cursor, VS Code, Claude, Windsurf, and Gemini editors
  • Implemented verbose logging system with configurable levels via environment variable
  • Added Git repository status checking with user warnings for uncommitted changes

Reviewed Changes

Copilot reviewed 4 out of 4 changed files in this pull request and generated 2 comments.

File Description
packages/init-stack/src/util.ts New utility module containing shared functions for verbose logging, template processing, and file system operations
packages/init-stack/src/mcp.ts New module implementing MCP server configuration scheduling for multiple editors
packages/init-stack/src/index.ts Integrated MCP configuration, added verbose logging throughout, implemented Git workspace checking, and refactored to use shared utilities
packages/init-stack/package.json Updated test scripts to include --no-warn-uncommitted-changes flag

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Copy link
Contributor

@greptile-apps greptile-apps bot left a comment

Choose a reason for hiding this comment

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

Greptile Overview

Greptile Summary

Added automatic MCP (Model Context Protocol) server configuration during Stack Auth initialization. The init script now detects and configures MCP support for multiple editors (VS Code, Cursor, Claude, Windsurf, Gemini) by writing to their respective config files and running CLI registration commands where available.

Key changes:

  • New mcp.ts module handles MCP server configuration for various editors
  • New util.ts module provides verbose logging, template string handling, and command detection utilities
  • Git workspace validation now warns users about uncommitted changes before modifying files (can be disabled with --no-warn-uncommitted-changes)
  • Deferred command execution system allows CLI commands to run after file writes complete
  • Extensive verbose logging added throughout (controlled by STACK_VERBOSE env var)
  • Test scripts updated to include --no-warn-uncommitted-changes flag

Confidence Score: 4/5

  • This PR is safe to merge with minor considerations
  • The implementation is well-structured with proper error handling, dry-run support, and best-effort command execution. Command injection is prevented by using spawnSync with separate args array. The Git workspace check provides good UX. Score of 4 instead of 5 due to the complexity of the changes and potential edge cases in cross-platform file path handling and editor CLI detection.
  • No files require special attention - all implementations follow good practices with proper error handling

Important Files Changed

File Analysis

Filename Score Overview
packages/init-stack/package.json 5/5 Added --no-warn-uncommitted-changes flag to all test scripts to suppress Git warnings during automated testing
packages/init-stack/src/util.ts 5/5 Added utility types and functions for verbose logging, template string handling, and command path detection
packages/init-stack/src/mcp.ts 5/5 New file implementing MCP server configuration for various editors (VS Code, Cursor, Claude, Windsurf, Gemini) with proper error handling and dry-run support
packages/init-stack/src/index.ts 4/5 Integrated MCP configuration scheduling, added verbose logging throughout, implemented Git workspace validation with uncommitted changes warning, and added deferred command execution

Sequence Diagram

sequenceDiagram
    participant User
    participant InitScript as init-stack CLI
    participant MCP as mcp.ts
    participant FileSystem as File System
    participant Git
    participant Editors as Editor CLIs

    User->>InitScript: Run init-stack
    InitScript->>InitScript: Parse CLI options
    InitScript->>InitScript: Configure verbose logging
    InitScript->>Git: Check if workspace is Git repo
    Git-->>InitScript: Repo status
    alt Has uncommitted changes & warnUncommittedChanges=true
        InitScript->>User: Warn about uncommitted changes
        User->>InitScript: Confirm proceed
    end
    InitScript->>InitScript: Get project type & package manager
    InitScript->>MCP: scheduleMcpConfiguration()
    MCP->>MCP: Schedule Cursor configs
    MCP->>MCP: Schedule VS Code configs
    MCP->>MCP: Schedule Claude configs
    MCP->>MCP: Schedule Windsurf configs
    MCP->>MCP: Schedule Gemini configs
    MCP->>InitScript: Register write handlers
    MCP->>InitScript: Register command handlers
    InitScript->>InitScript: Schedule Stack SDK installation
    InitScript->>InitScript: Schedule config file writes
    InitScript->>InitScript: Install dependencies
    InitScript->>FileSystem: Execute write handlers
    loop For each write handler
        FileSystem->>FileSystem: Write/update config files
        FileSystem->>InitScript: Record file change
    end
    InitScript->>InitScript: runDeferredCommands()
    loop For each command handler
        InitScript->>Editors: Execute editor CLI commands
        Editors-->>InitScript: Registration result (best effort)
    end
    InitScript->>User: Display success & next steps
Loading

4 files reviewed, no comments

Edit Code Review Agent Settings | Greptile

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

Caution

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

⚠️ Outside diff range comments (2)
packages/init-stack/src/index.ts (2)

410-421: Telemetry: avoid sending file names and command strings; send counts only.

Current payload includes repo file paths and commands to a third‑party endpoint, which is a compliance/privacy risk. Emit only aggregate counts.

   await capture("complete", {
     success: true,
     type,
     packageManager,
     isNeon,
     isClient,
     isServer,
     noBrowser,
-    filesCreated,
-    filesModified,
-    commandsExecuted,
+    filesCreatedCount: filesCreated.length,
+    filesModifiedCount: filesModified.length,
+    commandsExecutedCount: commandsExecuted.length,
   });

Optionally add a global opt‑out:

   .option("--on-question <mode>", "How to handle interactive questions: ask | guess | error | default", "default")
+  .option("--no-telemetry", "Disable telemetry")
 const options = program.opts();
+const telemetryEnabled: boolean = options.telemetry ?? true;
 async function capture(event: string, properties: Record<string, any>) {
-  logVerbose("capture event", { event, properties });
+  if (!telemetryEnabled) return;
+  logVerbose("capture event", { event, properties });
   ph_client.capture({ ... });
 }

949-951: Fix message spacing and clarity.

Minor copy tweak for readability.

-        `A file at the path ${handlerPath} already exists.Stack uses the / handler path to handle incoming requests.Please remove the existing file and try again.`
+        `A file at the path ${handlerPath} already exists. Stack uses the /handler path to handle incoming requests. Please remove the existing file and try again.`
🧹 Nitpick comments (1)
packages/init-stack/src/util.ts (1)

49-51: Minor: avoid O(n·m) lookups in omit.

Convert keys to a Set for faster membership on larger inputs.

-export function omit(object: Record<string, any>, keys: string[]): Record<string, any> {
-  return Object.fromEntries(Object.entries(object).filter(([key]) => !keys.includes(key)));
-}
+export function omit(object: Record<string, any>, keys: string[]): Record<string, any> {
+  const drop = new Set(keys);
+  return Object.fromEntries(Object.entries(object).filter(([key]) => !drop.has(key)));
+}
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 5f8cb02 and b6d829f.

📒 Files selected for processing (4)
  • packages/init-stack/package.json (1 hunks)
  • packages/init-stack/src/index.ts (58 hunks)
  • packages/init-stack/src/mcp.ts (1 hunks)
  • packages/init-stack/src/util.ts (1 hunks)
🧰 Additional context used
📓 Path-based instructions (1)
**/*.{ts,tsx}

📄 CodeRabbit inference engine (AGENTS.md)

Use ES6 Maps instead of Records wherever possible in TypeScript code

Files:

  • packages/init-stack/src/mcp.ts
  • packages/init-stack/src/index.ts
  • packages/init-stack/src/util.ts
🧬 Code graph analysis (3)
packages/init-stack/src/mcp.ts (1)
packages/init-stack/src/util.ts (5)
  • JsonRecord (15-15)
  • Colorize (7-13)
  • shouldWriteConfigFile (70-83)
  • getCommandPath (53-68)
  • logVerbose (31-38)
packages/init-stack/src/index.ts (2)
packages/init-stack/src/util.ts (2)
  • configureVerboseLogging (22-25)
  • logVerbose (31-38)
packages/init-stack/src/mcp.ts (1)
  • scheduleMcpConfiguration (37-47)
packages/init-stack/src/util.ts (1)
packages/init-stack/src/index.ts (1)
  • templateIdentity (14-14)
🪛 ast-grep (0.39.6)
packages/init-stack/src/index.ts

[warning] 1752-1752: Regular expression constructed from variable input detected. This can lead to Regular Expression Denial of Service (ReDoS) attacks if the variable contains malicious patterns. Use libraries like 'recheck' to validate regex safety or use static patterns.
Context: new RegExp(import\\s+[^;]*\\b${identifier}\\b)
Note: [CWE-1333] Inefficient Regular Expression Complexity [REFERENCES]
- https://owasp.org/www-community/attacks/Regular_expression_Denial_of_Service_-_ReDoS
- https://cwe.mitre.org/data/definitions/1333.html

(regexp-from-variable)


[warning] 1831-1831: Regular expression constructed from variable input detected. This can lead to Regular Expression Denial of Service (ReDoS) attacks if the variable contains malicious patterns. Use libraries like 'recheck' to validate regex safety or use static patterns.
Context: new RegExp(\\b${escapeRegExp(variableName)}\\s*\\.setAuth\\s*\\()
Note: [CWE-1333] Inefficient Regular Expression Complexity [REFERENCES]
- https://owasp.org/www-community/attacks/Regular_expression_Denial_of_Service_-_ReDoS
- https://cwe.mitre.org/data/definitions/1333.html

(regexp-from-variable)

⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (12)
  • GitHub Check: Vercel Agent Review
  • GitHub Check: restart-dev-and-test
  • GitHub Check: build (22.x)
  • GitHub Check: build (22.x)
  • GitHub Check: check_prisma_migrations (22.x)
  • GitHub Check: build (22.x)
  • GitHub Check: setup-tests
  • GitHub Check: all-good
  • GitHub Check: docker
  • GitHub Check: restart-dev-and-test-with-custom-base-port
  • GitHub Check: lint_and_build (latest)
  • GitHub Check: Security Check
🔇 Additional comments (2)
packages/init-stack/package.json (1)

21-21: Verified: --no-warn-uncommitted-changes flag is properly implemented.

The flag is defined in packages/init-stack/src/index.ts:99 with the description "Don't warn about uncommitted changes in the Git repository" and is consistently applied across all automated test-run scripts in package.json. The uncommitted changes validation logic exists in the same file, and the flag appropriately suppresses warnings in automated test environments while manual test scripts intentionally retain the warnings for developer feedback.

packages/init-stack/src/index.ts (1)

1397-1400: Verify BottomBar piping target.

child.stdout.pipe(ui.log) assumes ui.log is a Writable stream. In inquirer, ui.log.write(...) is the documented API. Confirm ui.log is a stream in your version; otherwise switch to child.stdout.on("data", d => ui.log.write(d)).

Run locally and confirm output appears without exceptions.

Co-authored-by: Konsti Wohlwend <N2D4@users.noreply.github.com>
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: 0

♻️ Duplicate comments (2)
packages/init-stack/src/index.ts (2)

398-400: MCP success message prints unconditionally.

This message displays even when no MCP editors were detected or configured. Consider gating it on whether any editors were actually updated, or rephrasing to indicate "attempted configuration."


1257-1263: Warning doesn't catch staged changes.

The current filter only examines the working tree status column (line[1]), which means staged but uncommitted changes won't trigger a warning. Users might lose visibility of modifications they've staged but not yet committed.

Consider checking both the index and worktree columns:

 const unstagedLines = lines.filter((line) => {
   if (line.startsWith("!!")) return false;
   if (line.startsWith("??")) return true;
   if (line.length < 2) return false;
-  const workingTreeStatus = line[1];
-  return Boolean(workingTreeStatus && workingTreeStatus !== " ");
+  const indexStatus = line[0];
+  const worktreeStatus = line[1];
+  return (indexStatus && indexStatus !== " " && indexStatus !== "?") || 
+         (worktreeStatus && worktreeStatus !== " ");
 });
🧹 Nitpick comments (1)
packages/init-stack/src/index.ts (1)

14-14: Consider documenting the purpose of exporting templateIdentity.

This export appears to serve a niche use case for external verbose formatting customization. Adding a brief JSDoc comment explaining when and why consumers would use this export would improve maintainability.

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between b6d829f and 858bfa3.

📒 Files selected for processing (1)
  • packages/init-stack/src/index.ts (58 hunks)
🧰 Additional context used
📓 Path-based instructions (1)
**/*.{ts,tsx}

📄 CodeRabbit inference engine (AGENTS.md)

Use ES6 Maps instead of Records wherever possible in TypeScript code

Files:

  • packages/init-stack/src/index.ts
🧬 Code graph analysis (1)
packages/init-stack/src/index.ts (2)
packages/init-stack/src/util.ts (2)
  • configureVerboseLogging (22-25)
  • logVerbose (31-38)
packages/init-stack/src/mcp.ts (1)
  • scheduleMcpConfiguration (37-47)
🪛 ast-grep (0.39.6)
packages/init-stack/src/index.ts

[warning] 1752-1752: Regular expression constructed from variable input detected. This can lead to Regular Expression Denial of Service (ReDoS) attacks if the variable contains malicious patterns. Use libraries like 'recheck' to validate regex safety or use static patterns.
Context: new RegExp(import\\s+[^;]*\\b${identifier}\\b)
Note: [CWE-1333] Inefficient Regular Expression Complexity [REFERENCES]
- https://owasp.org/www-community/attacks/Regular_expression_Denial_of_Service_-_ReDoS
- https://cwe.mitre.org/data/definitions/1333.html

(regexp-from-variable)


[warning] 1831-1831: Regular expression constructed from variable input detected. This can lead to Regular Expression Denial of Service (ReDoS) attacks if the variable contains malicious patterns. Use libraries like 'recheck' to validate regex safety or use static patterns.
Context: new RegExp(\\b${escapeRegExp(variableName)}\\s*\\.setAuth\\s*\\()
Note: [CWE-1333] Inefficient Regular Expression Complexity [REFERENCES]
- https://owasp.org/www-community/attacks/Regular_expression_Denial_of_Service_-_ReDoS
- https://cwe.mitre.org/data/definitions/1333.html

(regexp-from-variable)

⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (11)
  • GitHub Check: Vercel Agent Review
  • GitHub Check: docker
  • GitHub Check: all-good
  • GitHub Check: build (22.x)
  • GitHub Check: build (22.x)
  • GitHub Check: restart-dev-and-test
  • GitHub Check: lint_and_build (latest)
  • GitHub Check: build (22.x)
  • GitHub Check: restart-dev-and-test-with-custom-base-port
  • GitHub Check: check_prisma_migrations (22.x)
  • GitHub Check: setup-tests
🔇 Additional comments (1)
packages/init-stack/src/index.ts (1)

1831-1831: LGTM: ReDoS protection in place.

While static analysis flagged this dynamic RegExp as a potential ReDoS vector, the use of escapeRegExp(variableName) on line 1831 properly sanitizes the input, making this safe.

N2D4 and others added 3 commits October 24, 2025 14:43
Remove 'n/a' fallback and use String() conversion to match native behavior
where undefined becomes 'undefined' and null becomes 'null'.

Co-authored-by: Konsti Wohlwend <N2D4@users.noreply.github.com>
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: 0

♻️ Duplicate comments (1)
packages/init-stack/src/util.ts (1)

40-47: The "n/a" fallback issue remains unresolved.

The previous review comment about line 46 using "n/a" instead of preserving native template literal semantics is still applicable. Native templates render undefined as "undefined" and null as "null", but this implementation substitutes "n/a", which can mask bugs or create confusion.

Apply this diff to preserve native semantics:

-  return strings.slice(1).reduce((result, string, i) => `${result}${values[i] ?? "n/a"}${string}`, strings[0]);
+  return strings.slice(1).reduce((result, string, i) => `${result}${String(values[i])}${string}`, strings[0]);
🧹 Nitpick comments (1)
packages/init-stack/src/util.ts (1)

53-68: Command resolution works correctly. Consider minor optimization.

The bash invocation issue from the previous review has been addressed. The function now correctly passes the command to the shell as a single interpolated string.

For a minor optimization, consider adding encoding: "utf8" to the spawn options:

-    const result = child_process.spawnSync(spawnArgs[0], spawnArgs[1], { stdio: "pipe" });
+    const result = child_process.spawnSync(spawnArgs[0], spawnArgs[1], { stdio: "pipe", encoding: "utf8" });
     if (result.status === 0) {
-      return result.stdout.toString().trim().split('\n')[0];
+      return result.stdout.trim().split('\n')[0];
     }
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 858bfa3 and 0e4a9d0.

📒 Files selected for processing (2)
  • packages/init-stack/package.json (1 hunks)
  • packages/init-stack/src/util.ts (1 hunks)
🧰 Additional context used
📓 Path-based instructions (1)
**/*.{ts,tsx}

📄 CodeRabbit inference engine (AGENTS.md)

Use ES6 Maps instead of Records wherever possible in TypeScript code

Files:

  • packages/init-stack/src/util.ts
🧬 Code graph analysis (1)
packages/init-stack/src/util.ts (1)
packages/init-stack/src/index.ts (1)
  • templateIdentity (14-14)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (14)
  • GitHub Check: sync
  • GitHub Check: claude
  • GitHub Check: build (22.x)
  • GitHub Check: build (22.x)
  • GitHub Check: build (22.x)
  • GitHub Check: restart-dev-and-test
  • GitHub Check: setup-tests
  • GitHub Check: restart-dev-and-test-with-custom-base-port
  • GitHub Check: lint_and_build (latest)
  • GitHub Check: Vercel Agent Review
  • GitHub Check: check_prisma_migrations (22.x)
  • GitHub Check: all-good
  • GitHub Check: docker
  • GitHub Check: Security Check
🔇 Additional comments (5)
packages/init-stack/package.json (1)

21-21: Consistent and appropriate flag rollout across test scripts.

The --no-warn-uncommitted-changes flag has been consistently added to all non-interactive automated test scenarios (those with --on-question error), while manual test scripts remain unchanged. This pattern is sensible—suppress warnings during automated CI runs where uncommitted changes are expected.

Please verify that the --no-warn-uncommitted-changes CLI flag is properly implemented in the init-stack source code (src/index.ts and related files) to handle this new parameter correctly. The test script changes are only useful if the underlying command recognizes and properly processes the flag without errors.

Also applies to: 23-23, 25-25, 27-27, 28-28, 29-29, 30-30

packages/init-stack/src/util.ts (4)

1-15: LGTM! Clean type definitions and imports.

The imports and type definitions are well-structured. The use of Record for JsonRecord is appropriate here as it represents plain object structures, not collections that would benefit from ES6 Maps.


17-38: LGTM! Solid verbose logging implementation.

The logging system correctly uses module-level state, clamps the verbosity level to non-negative values, and provides conditional detail output based on level thresholds. The use of console.dir with depth: null for detailed inspection is appropriate.


49-51: LGTM! Clean object utility.

The omit function correctly filters out specified keys using a straightforward entries/filter/fromEntries pattern.


70-83: The original review comment is based on a misunderstanding of the code flow.

The shouldWriteConfigFile() function is a pre-check that determines whether a write should be scheduled, not an assertion that the file is immediately writable. The actual directory creation happens later in the writeJsonFile() function (line 249) via fs.mkdirSync(path.dirname(absolutePath), { recursive: true }), which executes before the write (line 258).

When allowCreate is true, shouldWriteConfigFile() correctly returns true without checking directory existence because the calling code is designed to create directories at write time, not during the pre-check phase. This separation of concerns is intentional and correct.

Likely an incorrect or invalid review comment.

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)
packages/init-stack/src/util.ts (1)

56-71: Consider adding UTF-8 encoding to spawnSync for cleaner code.

The function correctly resolves command paths with a two-step lookup strategy. However, you can specify the encoding directly in the spawnSync options to avoid the .toString() call.

Apply this diff:

   for (const spawnArgs of commands) {
-    const result = child_process.spawnSync(spawnArgs[0], spawnArgs[1], { stdio: "pipe" });
+    const result = child_process.spawnSync(spawnArgs[0], spawnArgs[1], { stdio: "pipe", encoding: "utf8" });
     if (result.status === 0) {
-      return result.stdout.toString().trim().split('\n')[0];
+      return result.stdout.trim().split('\n')[0];
     }
   }
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 0e4a9d0 and 8603c02.

📒 Files selected for processing (1)
  • packages/init-stack/src/util.ts (1 hunks)
🧰 Additional context used
📓 Path-based instructions (1)
**/*.{ts,tsx}

📄 CodeRabbit inference engine (AGENTS.md)

Use ES6 Maps instead of Records wherever possible in TypeScript code

Files:

  • packages/init-stack/src/util.ts
🧬 Code graph analysis (1)
packages/init-stack/src/util.ts (1)
packages/init-stack/src/index.ts (1)
  • templateIdentity (14-14)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (11)
  • GitHub Check: build (22.x)
  • GitHub Check: restart-dev-and-test-with-custom-base-port
  • GitHub Check: setup-tests
  • GitHub Check: lint_and_build (latest)
  • GitHub Check: restart-dev-and-test
  • GitHub Check: check_prisma_migrations (22.x)
  • GitHub Check: docker
  • GitHub Check: all-good
  • GitHub Check: build (22.x)
  • GitHub Check: build (22.x)
  • GitHub Check: Vercel Agent Review
🔇 Additional comments (4)
packages/init-stack/src/util.ts (4)

22-25: LGTM: Verbose logging configuration.

The module-level state pattern is appropriate for a configuration utility, and the use of Math.max(0, ...) correctly prevents negative verbosity levels.


31-38: LGTM: Two-tier verbose logging.

The implementation correctly provides two verbosity levels: basic messages at level 1 and detailed object inspection at level 2+.


40-50: LGTM: Template identity function correctly preserves native semantics.

The function now uses String(values[i]) instead of the previous ?? "n/a" fallback, correctly matching native template literal behavior where undefined and null are stringified naturally.


52-54: LGTM: Clean omit utility.

The implementation correctly filters out specified keys and returns a new object without mutation.

Comment on lines +73 to +86
export function shouldWriteConfigFile(
fullPath: string | null | undefined,
options: { allowCreate?: boolean } = {}
): boolean {
if (!fullPath) return false;
if (fs.existsSync(fullPath)) return true;

const dir = path.dirname(fullPath);
if (!options.allowCreate) {
return fs.existsSync(dir);
}

return true;
}
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

Fix shouldWriteConfigFile logic when allowCreate is true.

When allowCreate is true, the function unconditionally returns true (line 85), even if the parent directory doesn't exist. This will cause subsequent fs.writeFileSync calls to fail with ENOENT errors.

Either create the directory or verify it exists:

Option 1: Create the directory when allowCreate is true (recommended):

   const dir = path.dirname(fullPath);
   if (!options.allowCreate) {
     return fs.existsSync(dir);
   }
 
+  // Ensure directory exists when allowCreate is true
+  if (!fs.existsSync(dir)) {
+    fs.mkdirSync(dir, { recursive: true });
+  }
   return true;

Option 2: Just verify the directory exists:

   const dir = path.dirname(fullPath);
-  if (!options.allowCreate) {
-    return fs.existsSync(dir);
-  }
-
-  return true;
+  return fs.existsSync(dir);

Note: Option 2 makes the allowCreate parameter meaningless since it doesn't change behavior.

🤖 Prompt for AI Agents
In packages/init-stack/src/util.ts around lines 73 to 86, the function currently
returns true when allowCreate is true even if the parent directory doesn't
exist, which leads to ENOENT on subsequent writes; update the logic so that when
options.allowCreate is true you ensure the directory exists (create it if
missing) before returning true (e.g., call a synchronous recursive mkdir or
equivalent), otherwise keep the existing behavior of returning whether the
directory exists.

@N2D4 N2D4 merged commit 5b28349 into dev Oct 24, 2025
23 of 25 checks passed
@N2D4 N2D4 deleted the init-mcp branch October 24, 2025 23:58
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