[BUG] Agent .md silently skipped when file has CRLF line endings AND unquoted description contains ": " (colon+space) — deterministic minimal repro

Status Open
Reported on v2.1.218
Maintainer reply None cached
Activity 1 comment · opened Jul 24, 2026

Preflight Checklist

  • [x] I have searched existing issues and this hasn't been reported yet
  • [x] This is a single bug report (please file separate reports for different bugs)
  • [x] I am using the latest version of Claude Code

What's Wrong?

Summary

A custom agent file in .claude/agents/ is silently skipped (never registered; --agent <name> not found / Agent type '<name>' not found) when both of the following hold:

  1. the file has CRLF line endings, and
  2. the unquoted description: value contains : (a colon followed by a space), e.g. description: My agent [ref: ABC-123].

Either condition alone is fine: the same file with LF endings registers correctly, and CRLF files without : in the description register correctly. There is no warning or error anywhere — the agent is just missing from the available-agents list, which makes this extremely hard to debug.

This looks like a plausible root cause for at least #76499 (files there are confirmed CRLF, and a deterministic subset of agents never loads) and possibly #73865 ("identical siblings work fine") — see "Relation to existing issues" below.

Environment

  • Claude Code 2.1.218 (native install, ~/.local/bin/claude); the symptom was first observed on 2.1.177 with real-world files, and the minimal pair below was isolated on 2.1.218
  • Windows 11 Pro (10.0.26200), Git Bash
  • Repro is in a clean empty directory (not a git repo, no settings.json, no hooks, no plugins) — project/user settings are ruled out

Minimal repro

mkdir -p repro/.claude/agents && cd repro

# LF + ": " in description -> registers fine
printf -- '---\nname: agent-lf\ndescription: test [ref: ABC-123]\ntools: Read\n---\nReply with exactly: LF_OK\n' \
  > .claude/agents/agent-lf.md

# CRLF + ": " in description -> silently skipped
printf -- '---\r\nname: agent-crlf\r\ndescription: test [ref: ABC-123]\r\ntools: Read\r\n---\r\nReply with exactly: CRLF_OK\r\n' \
  > .claude/agents/agent-crlf.md

claude -p "Follow your system prompt." --agent agent-lf --max-turns 1
# -> LF_OK

claude -p "Follow your system prompt." --agent agent-crlf --max-turns 1
# -> --agent 'agent-crlf' not found. Available agents: claude, claude-code-guide, Explore,
#    general-purpose, Plan, agent-lf, statusline-setup

The same registration failure is observed when launching via the Agent/Task tool (subagent_type: "agent-crlf"Agent type 'agent-crlf' not found).

Isolation matrix (all tested on 2.1.218, clean directory)

| Line endings | description value contains | Result |
|---|---|---|
| LF | [ref: ABC-123] (colon+space, unquoted) | ✅ registers |
| CRLF | plain ASCII, no colon | ✅ registers |
| CRLF | colon without space ([ref:ABC-123]) | ✅ registers |
| CRLF | multibyte UTF-8 (Japanese text, é), no colon+space | ✅ registers |
| CRLF | YAML comment line in frontmatter | ✅ registers |
| CRLF | quoted scoped tools entries (- "Write(docs/**)") | ✅ registers |
| CRLF | [ref: ABC-123] (colon+space, unquoted) | ❌ silently skipped |
| CRLF | same value but double-quoted (description: "test [ref: ABC-123]") | ✅ registers |

Extra fields (model, maxTurns, permissionMode) were also tested individually under CRLF and are not involved.

Hypothesis (mechanism)

An unquoted plain scalar containing : is technically ambiguous YAML. The frontmatter parser appears to tolerate this ambiguity when lines end in \n, but fails when the line ends in \r\n — and a parse failure causes the whole agent file to be dropped silently.

Why this clusters on Windows

git config core.autocrlf=true (a very common Windows default) converts working-tree files to CRLF on checkout. So agent files that are committed with LF and work for macOS/Linux teammates silently vanish on Windows machines — and only those whose descriptions contain : , which makes the failing subset look arbitrary ("identical siblings work fine").

Relation to existing issues (hypothesis — for the reporters to check)

  • #76499: all 14 files are reported as CRLF, and the same 5 agents deterministically fail while 9 load. Prediction: the 5 failing files have : in their unquoted description, the 9 working ones don't.
  • #73865: one agent never registers while structurally identical siblings work, on Windows. Same prediction for the failing file's description.

Workarounds (verified)

  1. Quote the description: description: "test [ref: ABC-123]" — works even with CRLF.
  2. Normalize the file to LF, and pin it with .gitattributes: .claude/agents/*.md text eol=lf.
  3. Avoid : inside unquoted description values.

Suggested fixes

  1. Normalize \r\n before frontmatter parsing (split on /\r?\n/ or strip trailing \r per line).
  2. Independent of the fix above: when an agents file fails frontmatter parsing, emit a visible warning naming the file instead of skipping silently. The silence is what turns a one-character YAML quirk into hours of debugging.

What Should Happen?

The CRLF agent file should register exactly like the LF one does (line endings should not affect agent discovery). At minimum, when an agent file fails frontmatter parsing, Claude Code should emit a visible warning naming the file instead of silently skipping it.

Error Messages/Logs

--agent 'agent-crlf' not found. Available agents: claude, claude-code-guide, Explore, general-purpose, Plan, agent-lf, statusline-setup

(No other error or warning is emitted anywhere — the agent file is skipped silently. When invoked via the Agent/Task tool instead of --agent, the error is: Agent type 'agent-crlf' not found.)

Steps to Reproduce

  1. On Windows, create a clean empty directory and an agents folder inside it: mkdir -p repro/.claude/agents && cd repro (Git Bash)
  2. Create two agent files that are byte-identical except for line endings — both have an unquoted description containing : (colon+space):
# LF version
printf -- '---\nname: agent-lf\ndescription: test [ref: ABC-123]\ntools: Read\n---\nReply with exactly: LF_OK\n' > .claude/agents/agent-lf.md

# CRLF version
printf -- '---\r\nname: agent-crlf\r\ndescription: test [ref: ABC-123]\r\ntools: Read\r\n---\r\nReply with exactly: CRLF_OK\r\n' > .claude/agents/agent-crlf.md
  1. Run the LF agent: claude -p "Follow your system prompt." --agent agent-lf --max-turns 1 → replies LF_OK (registers correctly)
  2. Run the CRLF agent: claude -p "Follow your system prompt." --agent agent-crlf --max-turns 1--agent 'agent-crlf' not found (silently skipped; it is also absent from the available-agents list)
  3. Control experiments (see isolation matrix in the description): removing the : from the CRLF file's description makes it register; double-quoting the description also makes it register; so the failure requires CRLF and an unquoted : in the description.

Claude Model

None

Is this a regression?

I don't know

Last Working Version

_No response_

Claude Code Version

2.1.218 (Claude Code)

Platform

Anthropic API

Operating System

Windows

Terminal/Shell

Non-interactive/CI environment

Additional Information

_No response_

View original on GitHub ↗

This issue has 1 comment on GitHub. Read the full discussion on GitHub ↗