Install
$ agentstack add skill-oubakiou-md2idx-md2idx-read ✓ scanned · ✓ verified — works with Claude Code, Cursor, and more.
Security review
✓ PassedNo issues found. Passed automated security review. · v0.1.0 How review works →
- ✓ Prompt-injection patterns
- ✓ Secret / credential exfiltration
- ✓ Dangerous shell & filesystem operations
- ✓ Untrusted network calls
- ✓ Known-malicious package signatures
What it can access
- ✓ Network access No
- ✓ Filesystem access No
- ✓ Shell / process execution No
- ✓ Environment & secrets No
- ✓ Dynamic code execution No
From automated source analysis of v0.1.0. “Used” means the capability is present in the source — more access means more to trust, not that it’s unsafe.
About
md2idx-read
A skill for reading large Markdown files efficiently using md2idx. Instead of loading an entire file into context, first fetch the index (heading table of contents), then selectively retrieve only the sections needed for the current task.
The bundled scripts/md2idx-run.sh wrapper handles file size checking, md2idx command resolution (local build, PATH, npx), and execution. All Bash operations go through this single script, so one permissions.allow prefix covers the full workflow.
When to use
- Reading a large Markdown file (guideline: more than 200 lines or 10 KB)
- Only specific sections are needed, not the entire file
- The user explicitly asks to "read via md2idx", "check the index", or "read selectively"
When NOT to use
- Small Markdown files (under 200 lines) — reading directly with the Read tool is faster
- The entire file needs to be edited — the Edit tool requires full content
- Non-Markdown files
Workflow
Call the wrapper via bash with a project-root-relative path (not absolute) so it matches permissions.allow prefix rules. The base directory depends on which agent installed the skill — .claude/skills/ for Claude Code, .agents/skills/ for other agents (Codex CLI uses .codex/skills/ in some configurations):
# Claude Code:
bash .claude/skills/md2idx-read/scripts/md2idx-run.sh "" --index
# Other agents:
bash .agents/skills/md2idx-read/scripts/md2idx-run.sh "" --index
Use the path that matches your agent's install directory throughout all commands below.
The wrapper performs these steps internally:
- File size check — if the file is under 200 lines AND under 10 KB, it exits with code 2 and prints
SMALL: ... — use Read tool directlyto stderr. In that case, use the Read tool to read the file directly and stop. - md2idx command resolution — tries
node dist/md2idx.mjs(local build), thenmd2idx(PATH), thennpx -y md2idx(auto-download). Exits with code 3 if none are available. - Execution — runs the resolved md2idx with
jqand outputs the result to stdout.
Step 1: Fetch the index
# Claude Code:
bash .claude/skills/md2idx-read/scripts/md2idx-run.sh "" --index
# Other agents:
bash .agents/skills/md2idx-read/scripts/md2idx-run.sh "" --index
If exit code is 2 (file too small), use Read tool directly. If exit code is 3 (md2idx unavailable), skip to the fallback procedure.
Example output:
# 0. Project README
## 1. Install
## 2. Usage
### 3. Options
## 4. License
Each line follows the format . . The serial number corresponds to the sections array index. The number of # marks indicates the heading depth. If there is text before the first heading (preamble), it appears as 0. with no heading markers and is stored in sections[0].
Step 2: Determine which sections are needed
Read the index and identify which sections are relevant to the current task.
Guidelines:
- Select headings directly related to the user's question or task
- Child headings appear as consecutive numbers immediately after their parent. A contiguous range of deeper
#marks after a heading represents that heading's entire subtree - When in doubt, fetch fewer sections first and add more later — this is more token-efficient
Step 3: Retrieve sections
Single section:
# Claude Code:
bash .claude/skills/md2idx-read/scripts/md2idx-run.sh "" --sections '.sections[2]'
# Other agents:
bash .agents/skills/md2idx-read/scripts/md2idx-run.sh "" --sections '.sections[2]'
Contiguous range (a heading and all its children):
Using the index example above, to retrieve "Usage" (2) and its child "Options" (3):
# Claude Code:
bash .claude/skills/md2idx-read/scripts/md2idx-run.sh "" --sections '.sections[2:4][]'
# Other agents:
bash .agents/skills/md2idx-read/scripts/md2idx-run.sh "" --sections '.sections[2:4][]'
The jq slice [N:M] returns indices N through M-1.
Multiple non-contiguous sections:
# Claude Code:
bash .claude/skills/md2idx-read/scripts/md2idx-run.sh "" --sections '.sections[0], .sections[3], .sections[7]'
# Other agents:
bash .agents/skills/md2idx-read/scripts/md2idx-run.sh "" --sections '.sections[0], .sections[3], .sections[7]'
All sections (reconstruct the full document):
# Claude Code:
bash .claude/skills/md2idx-read/scripts/md2idx-run.sh "" --sections '.sections | join("\n\n")'
# Other agents:
bash .agents/skills/md2idx-read/scripts/md2idx-run.sh "" --sections '.sections | join("\n\n")'
This loads the whole file into context, which defeats the token-saving purpose of this skill. Only use it when you genuinely need every section — otherwise prefer the selective retrieval above.
Step 4: Repeat if more sections are needed
If the retrieved sections indicate that additional sections are needed, return to Step 3. The index from Step 1 is already available — use it to determine the additional section numbers.
Fallback when md2idx is unavailable
If the wrapper exits with code 3, or if Bash permissions are denied, notify the user: "md2idx is unavailable — falling back to Read + grep", then use the following alternative procedure.
Fallback: Get heading list via grep
grep -nE '^ {0,3}#{1,6}[[:space:]]' ""
This returns a line-numbered list of ATX headings. Use this as a substitute for the index.
Fallback: Retrieve sections via Read tool
From the grep output, determine the range to read based on what you need:
Single section (one heading only): read from the heading's line up to (but not including) the next heading at any level.
A heading and all its children: read from the heading's line up to (but not including) the next heading at the same or shallower level (same or fewer # marks). This includes all deeper child headings in between.
In both cases, let start_line be the heading's line number from grep, and next_line be the line number of the boundary heading (exclusive). Then use the Read tool:
Read(file, offset=, limit=)
Read's offset is the 1-based line number to start from, matching grep -n output directly. If the target heading is the last one in the file, omit limit to read to the end.
The fallback cannot distinguish setext headings (=== / ---) or # inside fenced code blocks. For full accuracy, grant Bash permissions and use the wrapper script.
Permissions setup
One permissions.allow rule covers the entire workflow. Use the path matching your agent:
// Claude Code:
{
"permissions": {
"allow": ["Bash(bash .claude/skills/md2idx-read/scripts/md2idx-run.sh:*)"]
}
}
// Other agents:
{
"permissions": {
"allow": ["Bash(bash .agents/skills/md2idx-read/scripts/md2idx-run.sh:*)"]
}
}
Notes
- The wrapper uses the same md2idx binary for both index and section retrieval, guaranteeing consistent indices
- md2idx output is deterministic for the same input and the same md2idx version
- Section content is returned as raw Markdown strings, including the heading line itself
npx -y md2idxskips the install confirmation prompt; in network-restricted environments, pre-install md2idx globally instead
Source & license
This open-source skill is cataloged on AgentStack and links to its original source — we do not rehost the code.
- Author: oubakiou
- Source: oubakiou/md2idx
- License: MIT
Install and usage instructions live in the source repository linked above.
Reviews
No reviews yet — be the first.
Write a review
Versions
- v0.1.0 Imported from the upstream source.