Skip to content

Commit a18b460

Browse files
fix(opencode): use singular directory names (agent/, skill/) to match OpenCode layout
OpenCode discovers agents in agent/ and skills in skill/ (singular), not agents/ or skills/ (plural). command/ was already correct. This fix makes the installed plugin visible to OpenCode immediately after install. Bumps version to 1.2.1. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
1 parent 40d4582 commit a18b460

File tree

4 files changed

+20
-20
lines changed

4 files changed

+20
-20
lines changed

ai_codebase_mentor/__init__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,3 @@
11
"""ai-codebase-mentor — multi-runtime Codebase Wizard installer."""
22

3-
__version__ = "1.2.0"
3+
__version__ = "1.2.1"

ai_codebase_mentor/converters/opencode.py

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,8 @@
55
Project: ./.opencode/codebase-wizard/
66
77
Agent frontmatter is converted from Claude Code format (allowed_tools: array)
8-
to OpenCode format (tools: object with lowercase keys). Command files are placed
9-
in command/ (singular). Skills are copied verbatim.
8+
to OpenCode format (tools: object with lowercase keys). OpenCode uses singular
9+
directory names: agent/, command/, skill/ (not agents/, commands/, skills/).
1010
"""
1111

1212
import json
@@ -231,8 +231,8 @@ def _resolve_dest(self, target: str) -> Path:
231231
def install(self, source: Path, target: str = "global") -> None:
232232
"""Convert and install the plugin to the OpenCode configuration directory.
233233
234-
Converts agent frontmatter, renames commands/ -> command/, copies skills
235-
verbatim, and writes opencode.json permission pre-authorization.
234+
Converts agent frontmatter, renames commands/ -> command/, agents/ -> agent/,
235+
skills/ -> skill/, and writes opencode.json permission pre-authorization.
236236
237237
Args:
238238
source: Path to the bundled plugin directory (contains .claude-plugin/).
@@ -254,7 +254,7 @@ def install(self, source: Path, target: str = "global") -> None:
254254

255255
# Convert and copy agent files
256256
agents_src = source / "agents"
257-
agents_dst = destination / "agents"
257+
agents_dst = destination / "agent"
258258
agents_dst.mkdir(parents=True, exist_ok=True)
259259
for agent_file in agents_src.glob("*.md"):
260260
content = agent_file.read_text(encoding="utf-8")
@@ -274,7 +274,7 @@ def install(self, source: Path, target: str = "global") -> None:
274274
# Copy skills verbatim (runtime-agnostic)
275275
skills_src = source / "skills"
276276
if skills_src.exists():
277-
shutil.copytree(skills_src, destination / "skills")
277+
shutil.copytree(skills_src, destination / "skill")
278278

279279
# Copy .claude-plugin directory (for version reading)
280280
claude_plugin_src = source / ".claude-plugin"

pyproject.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
44

55
[project]
66
name = "ai-codebase-mentor"
7-
version = "1.2.0"
7+
version = "1.2.1"
88
description = "Wizard-style codebase exploration and documentation. Install the Codebase Wizard plugin for Claude Code (and other runtimes in future releases)."
99
requires-python = ">=3.9"
1010
license = {text = "MIT"}

tests/test_opencode_installer.py

Lines changed: 12 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -32,26 +32,26 @@ def installer(tmp_path, monkeypatch):
3232

3333

3434
def test_global_install_creates_agent_files(installer, source_plugin_dir, tmp_path):
35-
"""install(source, 'global') creates agents dir at ~/.config/opencode/codebase-wizard/agents/."""
35+
"""install(source, 'global') creates agent dir at ~/.config/opencode/codebase-wizard/agent/."""
3636
installer.install(source_plugin_dir, "global")
3737
agents_dir = (
38-
tmp_path / "home" / ".config" / "opencode" / "codebase-wizard" / "agents"
38+
tmp_path / "home" / ".config" / "opencode" / "codebase-wizard" / "agent"
3939
)
40-
assert agents_dir.exists(), f"agents dir not found at {agents_dir}"
40+
assert agents_dir.exists(), f"agent dir not found at {agents_dir}"
4141
assert (agents_dir / "codebase-wizard-agent.md").exists(), (
42-
"codebase-wizard-agent.md not found in agents dir"
42+
"codebase-wizard-agent.md not found in agent dir"
4343
)
4444

4545

4646
def test_project_install_creates_agent_files(installer, source_plugin_dir, tmp_path):
47-
"""install(source, 'project') creates agents dir at ./.opencode/codebase-wizard/agents/."""
47+
"""install(source, 'project') creates agent dir at ./.opencode/codebase-wizard/agent/."""
4848
installer.install(source_plugin_dir, "project")
4949
agents_dir = (
50-
tmp_path / "cwd" / ".opencode" / "codebase-wizard" / "agents"
50+
tmp_path / "cwd" / ".opencode" / "codebase-wizard" / "agent"
5151
)
52-
assert agents_dir.exists(), f"agents dir not found at {agents_dir}"
52+
assert agents_dir.exists(), f"agent dir not found at {agents_dir}"
5353
assert (agents_dir / "codebase-wizard-agent.md").exists(), (
54-
"codebase-wizard-agent.md not found in agents dir"
54+
"codebase-wizard-agent.md not found in agent dir"
5555
)
5656

5757

@@ -103,7 +103,7 @@ def test_agent_tool_names_lowercased(installer, source_plugin_dir, tmp_path):
103103
installer.install(source_plugin_dir, "global")
104104
agent_file = (
105105
tmp_path / "home" / ".config" / "opencode" / "codebase-wizard"
106-
/ "agents" / "codebase-wizard-agent.md"
106+
/ "agent" / "codebase-wizard-agent.md"
107107
)
108108
content = agent_file.read_text()
109109
assert "read: true" in content, (
@@ -141,7 +141,7 @@ def test_special_tool_mapping_applied(installer, source_plugin_dir, tmp_path):
141141
installer.install(temp_source, "global")
142142
agent_out = (
143143
tmp_path / "home" / ".config" / "opencode" / "codebase-wizard"
144-
/ "agents" / "codebase-wizard-agent.md"
144+
/ "agent" / "codebase-wizard-agent.md"
145145
)
146146
content = agent_out.read_text()
147147
assert "question: true" in content, (
@@ -154,7 +154,7 @@ def test_name_field_stripped(installer, source_plugin_dir, tmp_path):
154154
installer.install(source_plugin_dir, "global")
155155
agent_file = (
156156
tmp_path / "home" / ".config" / "opencode" / "codebase-wizard"
157-
/ "agents" / "codebase-wizard-agent.md"
157+
/ "agent" / "codebase-wizard-agent.md"
158158
)
159159
content = agent_file.read_text()
160160
# Find the frontmatter section (between first and second '---')
@@ -198,7 +198,7 @@ def test_subagent_type_normalized(installer, source_plugin_dir, tmp_path):
198198
installer.install(temp_source, "global")
199199
agent_out = (
200200
tmp_path / "home" / ".config" / "opencode" / "codebase-wizard"
201-
/ "agents" / "codebase-wizard-agent.md"
201+
/ "agent" / "codebase-wizard-agent.md"
202202
)
203203
content = agent_out.read_text()
204204
assert 'subagent_type: "general"' in content, (

0 commit comments

Comments
 (0)