Tab completion crashes TUI with React error #31 when plugin command argument-hint is parsed as YAML object

Resolved 💬 3 comments Opened Feb 27, 2026 by solon Closed Feb 27, 2026

Summary

Pressing Tab to autocomplete certain slash commands crashes the TUI with a React rendering error. The root cause is that YAML frontmatter in command definition files can produce non-string values for argument-hint, and the tab-completion renderer passes these directly as React children without coercing to string.

Claude Code version

2.1.37

OS

macOS 26.0.1 (Tahoe), Apple Silicon (arm64)

Steps to Reproduce

  1. Install the compound-engineering plugin (any version up to and including current main)
  2. Start a Claude Code session
  3. Type /heal-skill at the input prompt
  4. Press Tab

The TUI crashes immediately. 100% reproducible.

Expected Behavior

Tab completion renders the argument hint as text, or gracefully handles non-string argument-hint values from command frontmatter.

Actual Behavior

The TUI crashes with:

ERROR Minified React error #31; visit https://react.dev/errors/31?args[]=object%20with%20keys%20%7Boptional%7D
      for the full message or use the non-minified dev environment for full errors and additional helpful warnings.

This is followed by a full minified React reconciler stack dump (~700 lines) and process exit.

Root Cause Analysis

The heal-skill command has this frontmatter:

argument-hint: [optional: specific issue to fix]

YAML parses [optional: specific issue to fix] as an array containing a mapping: [{ optional: "specific issue to fix" }], not a string literal. When tab completion renders this value as a React child in the autocomplete UI, React throws error #31: "Objects are not valid as a React child (found: object with keys {optional})".

Other commands in the same plugin that properly quote the value work fine:

# These are fine — quoted strings
argument-hint: "[optional: daily|weekly, or time period in days]"
argument-hint: "[path to plan file]"

# These crash — unquoted, parsed as YAML arrays/objects
argument-hint: [optional: specific issue to fix]
argument-hint: [skill description or requirements]

Affected commands in the plugin

4 commands in the compound-engineering plugin have unquoted argument-hint values that would trigger this. 3 produce the identical {optional} error:

| Command | argument-hint (raw) | YAML parses as |
|---|---|---|
| heal-skill | [optional: specific issue to fix] | [{optional: "..."}] — crashes |
| resolve_parallel | [optional: specific TODO pattern or file] | [{optional: "..."}] — crashes |
| resolve_todo_parallel | [optional: specific todo ID or pattern] | [{optional: "..."}] — crashes |
| create-agent-skill | [skill description or requirements] | ["skill description or requirements"] — likely also crashes (array, not string) |

The remaining 18 commands in the plugin have properly quoted values and work fine.

Suggested Fix

The tab-completion renderer should coerce argument-hint to a string before passing it as a React child (e.g., String(hint) or JSON.stringify(hint)), or validate command frontmatter at load time and warn on non-string values. A malformed plugin value should not be able to crash the entire TUI.

Stack Trace (abbreviated)

/$bunfs/root/claude:656:8780

- O7 (/$bunfs/root/claude:656:8780)     # throwOnInvalidObjectType
- $_ (/$bunfs/root/claude:656:10892)    # createChild
- o5 (/$bunfs/root/claude:656:12462)    # reconcileChildrenArray
- Av (/$bunfs/root/claude:656:14752)    # reconcileChildFibers
- cq (/$bunfs/root/claude:656:35656)    # reconcileChildren
- yb (/$bunfs/root/claude:656:51821)    # beginWork
- dx (/$bunfs/root/claude:656:86058)    # performUnitOfWork
- Se (/$bunfs/root/claude:656:85032)    # workLoopSync
- Ap (/$bunfs/root/claude:656:84857)    # renderRootSync

View original on GitHub ↗

This issue has 3 comments on GitHub. Read the full discussion on GitHub ↗