Skip to content

t1345: Fix markdown-formatter MCP tool — 100% error rate#2443

Merged
alex-solovyev merged 4 commits intomainfrom
bugfix/fix-markdown-formatter-errors
Feb 27, 2026
Merged

t1345: Fix markdown-formatter MCP tool — 100% error rate#2443
alex-solovyev merged 4 commits intomainfrom
bugfix/fix-markdown-formatter-errors

Conversation

@alex-solovyev
Copy link
Collaborator

@alex-solovyev alex-solovyev commented Feb 27, 2026

Summary

  • Fixed two bugs causing 100% failure rate in the markdown-formatter MCP tool (issue t1345: Add cross-repo improvement guidance to AGENTS.md #2440)
  • Bug 1: MCP tool exposed actions lint, check, fix but bash script only handled format, advanced, cleanup — unknown actions returned exit 1
  • Bug 2: fix_markdown_file() returned $changes_made (1 when successful) instead of 0, causing set -e to abort even on success

Changes

File Change
.agents/scripts/markdown-formatter.sh Added lint/check (dry-run mode) and fix (alias for format) actions; fixed return value bug
.agents/scripts/markdown-lint-fix.sh Fixed same return value bug in apply_manual_fixes()
.opencode/tool/markdown-formatter.ts Replaced Bun.$ (throws on non-zero) with Bun.spawn() (captures output gracefully)
.agents/prompts/build.txt Updated error prevention section #2 with correct root cause diagnosis
todo/tasks/t1345-brief.md Task brief

Verification

  • All 5 actions (format, fix, lint, check, help) return exit 0
  • ShellCheck: zero violations on both scripts
  • lint/check mode correctly reports issues without modifying files

Closes #2440

Summary by CodeRabbit

  • New Features

    • Formatter now exposes expanded actions: lint, check, fix, advanced, and cleanup, plus improved help and messaging.
  • Bug Fixes

    • Resolved exit-code and output-capture issues so success/failure are reported reliably.
    • Improved per-file change detection and safer backup/restore behavior.
  • Documentation

    • Updated guidance and acceptance criteria, plus a new troubleshooting check to verify the formatter script is present and executable.

…turn value bug)

Two root causes: (1) MCP tool exposed lint/check/fix actions but bash script
only handled format/advanced/cleanup — unknown actions hit default case exit 1;
(2) fix_markdown_file() returned $changes_made (1=success) instead of 0,
causing set -e to abort. MCP wrapper now uses Bun.spawn() to capture output
on non-zero exit instead of throwing.

Closes #2440
@gemini-code-assist
Copy link

Warning

You have reached your daily quota limit. Please wait up to 24 hours and I will start processing your requests again!

@github-actions github-actions bot added the bug Auto-created from TODO.md tag label Feb 27, 2026
@coderabbitai
Copy link
Contributor

coderabbitai bot commented Feb 27, 2026

Walkthrough

Fixes for the markdown-formatter MCP: scripts now support additional actions (format/fix/lint/check/advanced/cleanup), fix routines return success correctly, and the TypeScript wrapper uses Bun.spawn to capture stdout/stderr even on non-zero exits; docs and a task brief were added/updated.

Changes

Cohort / File(s) Summary
Formatter prompt docs
.agents/prompts/build.txt
Replaced prior exit-code note with bug-root-cause narrative, added supported actions list and a post-failure check to ensure .agents/scripts/markdown-formatter.sh exists and is executable.
Formatter script
.agents/scripts/markdown-formatter.sh
Added/aliased commands (format, fix, lint, check, advanced, cleanup), refactored internal flow (trap/_save_cleanup_scope use), switched per-file change detection to hash-based, and made fix_markdown_file return 0 unconditionally on success path; messaging and help updated.
Lint-fix script
.agents/scripts/markdown-lint-fix.sh
Restructured main/control flow and formatting, expanded .markdownlint.json generation, and fixed return-value handling in manual-fix flow while preserving existing behavior.
TypeScript wrapper
.opencode/tool/markdown-formatter.ts
Replaced Bun.$ usage with Bun.spawn() to pipe stdout/stderr, concurrently read streams, await exit, and include exit code context in returned output when non-zero.
Task brief
todo/tasks/t1345-brief.md
New brief documenting observed failures, identified root causes, files changed, acceptance criteria, and verification steps.

Sequence Diagram(s)

sequenceDiagram
  participant User
  participant TS as markdown-formatter.ts
  participant SH as markdown-formatter.sh
  participant FS as Filesystem

  User->>TS: invoke formatter (action)
  TS->>SH: spawn process (stdin/stdout/stderr piped)
  SH->>FS: read/write markdown files (format/fix/lint/check/cleanup)
  FS-->>SH: file contents / write ack
  SH-->>TS: stdout/stderr streamed
  SH-->>TS: exit code
  TS-->>User: aggregated output (includes stderr and exit code if non-zero)
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

Suggested labels

needs-review

Poem

🛠️ Shells aligned, Bun listens clear,
Lines trimmed, fixes now appear,
Exit codes tamed, outputs flow,
Formatter healed — on with the show! ✨

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Linked Issues check ⚠️ Warning The PR partially addresses issue #2440: it fixes the markdown-formatter tool's 100% error rate through three specific bugs (action mismatch, return values, output handling), but does not implement the guidance addition to AGENTS.md as required by the issue's primary objective. Add cross-repo improvement guidance to both root AGENTS.md and .agents/AGENTS.md as specified in #2440, explaining that aidevops improvements must be made in the source repo or captured as todos/plans there.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title 't1345: Fix markdown-formatter MCP tool — 100% error rate' directly and specifically describes the main fix: addressing the complete failure of the markdown-formatter MCP tool.
Out of Scope Changes check ✅ Passed All changes directly support fixing the markdown-formatter tool's failures: script refactoring, return value fixes, process spawning, and task documentation are all in scope for the stated bugfix objective.
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 docstrings (stacked PR)
  • 📝 Generate docstrings (commit on current branch)
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch bugfix/fix-markdown-formatter-errors

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.

@github-actions
Copy link

🔍 Code Quality Report

�[0;35m[MONITOR]�[0m Code Review Monitoring Report

�[0;34m[INFO]�[0m Latest Quality Status:
SonarCloud: 0 bugs, 0 vulnerabilities, 53 code smells

�[0;34m[INFO]�[0m Recent monitoring activity:
Fri Feb 27 03:00:41 UTC 2026: Code review monitoring started
Fri Feb 27 03:00:41 UTC 2026: SonarCloud - Bugs: 0, Vulnerabilities: 0, Code Smells: 53

📈 Current Quality Metrics

  • BUGS: 0
  • CODE SMELLS: 53
  • VULNERABILITIES: 0

Generated on: Fri Feb 27 03:00:44 UTC 2026


Generated by AI DevOps Framework Code Review Monitoring

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

Caution

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

⚠️ Outside diff range comments (1)
.agents/scripts/markdown-lint-fix.sh (1)

70-87: ⚠️ Potential issue | 🔴 Critical

Generated .markdownlint.json is invalid JSON.

Line 85 writes return 0 inside the heredoc payload, which corrupts the config file.

Proposed fix
 {
   "default": true,
   "MD013": {
     "line_length": 120,
     "code_blocks": false,
     "tables": false
   },
   "MD033": {
     "allowed_elements": ["br", "sub", "sup"]
   },
   "MD041": false,
   "MD046": {
     "style": "fenced"
   }
-    return 0
 }
 EOF

As per coding guidelines .agents/scripts/*.sh: Automation scripts should prioritize reliability and robustness.

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

In @.agents/scripts/markdown-lint-fix.sh around lines 70 - 87, The generated
heredoc written to the config_file in markdown-lint-fix.sh contains a stray
"return 0" inside the JSON payload which makes .markdownlint.json invalid;
remove the "return 0" from the heredoc so only valid JSON is written, and ensure
the script still returns success after the EOF by placing any return/exit or
status checks outside the heredoc (e.g., after the cat >>"$config_file" <<'EOF'
... EOF block), keeping the JSON keys shown (default, MD013, MD033, MD041,
MD046) intact.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In @.agents/scripts/markdown-formatter.sh:
- Around line 101-105: The script counts unchanged files as modified because
fix_markdown_file always returns 0; modify either the fix_markdown_file function
to return non-zero when no edits were made (or return 0 only when a change
occurred), or change the loop to detect actual changes (e.g., compare original
vs formatted content, check a generated "changed" flag or use a
diff/exit-status) and only increment changed_files when that indicator is true;
update references in the loop that use changed_files and the function name
fix_markdown_file accordingly so the summary reflects real modifications.
- Around line 189-196: In the advanced-fixes block in markdown-formatter.sh,
treat the "no changes needed" branch as success: replace the else branch's
"return 1" with "return 0" so that cmp -s no-op cases don't cause failures under
set -e, and remove the unreachable trailing "return 0" that follows this
conditional; keep the existing mv "$temp_file" "$file" and print_success
behavior unchanged so only the exit code is adjusted.
- Around line 263-266: The script currently dereferences "$1" into local _arg1
and then uses "${1:-...}" while running under set -u, causing an unbound
variable error when no args are passed; update the positional-arg handling in
the top-level argument parsing (variables _arg1, command, target) to guard
against unset parameters by using parameter expansions with defaults (e.g.,
${1:-} and ${2:-.}) or an explicit check on $# before reading "$1"/"$2" so the
script safely works under set -u and falls back to the intended defaults.

In @.agents/scripts/markdown-lint-fix.sh:
- Around line 123-137: The script calls markdownlint --fix twice in each branch
which can exit early under set -e; update the branches handling "$target" (the
file branch and the directory branch) to call markdownlint --fix only once and
capture its exit status, then use that status to choose between print_success
and print_warning; specifically remove the unconditional markdownlint --fix
"$target" and markdownlint --fix "$target/**/*.md" calls and instead run
markdownlint --fix once (for the file: markdownlint --fix "$target"; for the
dir: markdownlint --fix "$target"/*.md or the glob you prefer), store the result
($? or use if command; e.g., if markdownlint --fix ...; then ...) and then call
print_success or print_warning accordingly while keeping print_info calls around
the operation.
- Around line 239-242: In main(), avoid an unbound variable error under set -u
by giving $1 a safe default when assigning _arg1: change the declaration local
_arg1="$1" to use parameter expansion with a default (e.g. local _arg1="${1-}"
or local _arg1="${1:-}") so the script won't fail when no arguments are
supplied; leave existing command="${1:-fix}" and target="${2:-.}" as-is.

In `@todo/tasks/t1345-brief.md`:
- Around line 17-24: Update the "Root Cause (two bugs)" heading to correctly
reflect the enumerated items by changing it to "Root Cause (three bugs)" (or
remove the numeric count and use "Root Cause") so the heading matches the list
items that follow; ensure the heading text exactly matches the intention used in
the block that lists the three root causes.

---

Outside diff comments:
In @.agents/scripts/markdown-lint-fix.sh:
- Around line 70-87: The generated heredoc written to the config_file in
markdown-lint-fix.sh contains a stray "return 0" inside the JSON payload which
makes .markdownlint.json invalid; remove the "return 0" from the heredoc so only
valid JSON is written, and ensure the script still returns success after the EOF
by placing any return/exit or status checks outside the heredoc (e.g., after the
cat >>"$config_file" <<'EOF' ... EOF block), keeping the JSON keys shown
(default, MD013, MD033, MD041, MD046) intact.

ℹ️ Review info

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between b7210be and 7c292eb.

📒 Files selected for processing (5)
  • .agents/prompts/build.txt
  • .agents/scripts/markdown-formatter.sh
  • .agents/scripts/markdown-lint-fix.sh
  • .opencode/tool/markdown-formatter.ts
  • todo/tasks/t1345-brief.md

alex-solovyev and others added 2 commits February 27, 2026 04:14
- Remove stray 'return 0' from heredoc corrupting .markdownlint.json
- Fix fix_markdown_file return value: use hash comparison to detect actual changes
- Fix 'return 1' in advanced-fixes no-op branch to 'return 0' (set -e safe)
- Guard $1 with ${1:-} in both scripts to prevent set -u unbound variable error
- Remove duplicate markdownlint --fix calls in file/directory branches
- Update t1345-brief.md heading to 'three bugs' matching enumerated list
…branches

Three functions had dead 'return 0' after if/else blocks that already
return in every branch: check_markdownlint(), install_markdownlint()
in markdown-lint-fix.sh, and process_directory() in markdown-formatter.sh.
Addresses remaining CodeRabbit dead-code findings on PR #2443.
@marcusquinn
Copy link
Owner

@coderabbitai review

@coderabbitai
Copy link
Contributor

coderabbitai bot commented Feb 27, 2026

✅ 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.

@github-actions
Copy link

🔍 Code Quality Report

�[0;35m[MONITOR]�[0m Code Review Monitoring Report

�[0;34m[INFO]�[0m Latest Quality Status:
SonarCloud: 0 bugs, 0 vulnerabilities, 36 code smells

�[0;34m[INFO]�[0m Recent monitoring activity:
Fri Feb 27 05:03:09 UTC 2026: Code review monitoring started
Fri Feb 27 05:03:09 UTC 2026: SonarCloud - Bugs: 0, Vulnerabilities: 0, Code Smells: 36

📈 Current Quality Metrics

  • BUGS: 0
  • CODE SMELLS: 36
  • VULNERABILITIES: 0

Generated on: Fri Feb 27 05:03:12 UTC 2026


Generated by AI DevOps Framework Code Review Monitoring

@sonarqubecloud
Copy link

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

🧹 Nitpick comments (2)
.agents/scripts/markdown-formatter.sh (1)

338-340: Apply null-delimited traversal to both markdown processing scripts for robustness.

The loop at line 338 uses line-delimited piping which is vulnerable to filenames with special characters. Switch to -print0 + read -r -d '' for consistency and maximum filename robustness across both .agents/scripts/markdown-formatter.sh:338 and .agents/scripts/markdown-lint-fix.sh:250 where this pattern appears.

Suggested patch
-			find "$target" -name "*.md" -type f | while read -r file; do
+			while IFS= read -r -d '' file; do
 				apply_advanced_fixes "$file"
-			done
+			done < <(find "$target" -name "*.md" -type f -print0)
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In @.agents/scripts/markdown-formatter.sh around lines 338 - 340, The find |
while read loop that calls apply_advanced_fixes "$file" is fragile for filenames
with spaces/newlines; replace the line-delimited pipeline with a null-delimited
pattern using find ... -print0 and a while IFS= read -r -d '' file; do ... done
loop (or feed the -print0 output into the while loop via process substitution)
to robustly handle arbitrary filenames; apply the same change to the matching
loop in the markdown-lint-fix script where the same find | while read pattern
appears.
.agents/scripts/markdown-lint-fix.sh (1)

250-252: Harden directory iteration for edge-case filenames.

Use null-delimited traversal (-print0 with process substitution) here to match the established pattern used throughout the codebase and handle filenames with special characters safely. This same unsafe pattern also appears in markdown-formatter.sh:338 and should be refactored together.

Suggested patch
-			find "$target" -name "*.md" -type f | while read -r file; do
+			while IFS= read -r -d '' file; do
 				apply_manual_fixes "$file"
-			done
+			done < <(find "$target" -name "*.md" -type f -print0)
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In @.agents/scripts/markdown-lint-fix.sh around lines 250 - 252, The loop that
iterates Markdown files uses plain newline-delimited find output which breaks on
filenames with spaces/newlines; change the traversal to use null-delimited
output from find (print0) and read with a null delimiter (e.g., IFS= and read -r
-d '') via process substitution so apply_manual_fixes("$file") receives safe
filenames; make the same change in markdown-formatter.sh where the same pattern
appears. Ensure you keep using the existing target variable and the
apply_manual_fixes function name so behavior is unchanged aside from robust
filename handling.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Nitpick comments:
In @.agents/scripts/markdown-formatter.sh:
- Around line 338-340: The find | while read loop that calls
apply_advanced_fixes "$file" is fragile for filenames with spaces/newlines;
replace the line-delimited pipeline with a null-delimited pattern using find ...
-print0 and a while IFS= read -r -d '' file; do ... done loop (or feed the
-print0 output into the while loop via process substitution) to robustly handle
arbitrary filenames; apply the same change to the matching loop in the
markdown-lint-fix script where the same find | while read pattern appears.

In @.agents/scripts/markdown-lint-fix.sh:
- Around line 250-252: The loop that iterates Markdown files uses plain
newline-delimited find output which breaks on filenames with spaces/newlines;
change the traversal to use null-delimited output from find (print0) and read
with a null delimiter (e.g., IFS= and read -r -d '') via process substitution so
apply_manual_fixes("$file") receives safe filenames; make the same change in
markdown-formatter.sh where the same pattern appears. Ensure you keep using the
existing target variable and the apply_manual_fixes function name so behavior is
unchanged aside from robust filename handling.

ℹ️ Review info

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 7c292eb and 1579435.

📒 Files selected for processing (4)
  • .agents/prompts/build.txt
  • .agents/scripts/markdown-formatter.sh
  • .agents/scripts/markdown-lint-fix.sh
  • todo/tasks/t1345-brief.md
✅ Files skipped from review due to trivial changes (1)
  • todo/tasks/t1345-brief.md

@alex-solovyev alex-solovyev merged commit 682b22f into main Feb 27, 2026
16 checks passed
@marcusquinn
Copy link
Owner

Also resolves #2458 (t1347: markdown-formatter MCP tool has 81% error rate).

@marcusquinn marcusquinn deleted the bugfix/fix-markdown-formatter-errors branch March 3, 2026 03:23
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug Auto-created from TODO.md tag

Projects

None yet

Development

Successfully merging this pull request may close these issues.

t1345: Add cross-repo improvement guidance to AGENTS.md

2 participants