Agent skills let OpenCode discover reusable instructions from your repo or home directory.
Skills are loaded on-demand via the native skill tool—agents see available skills and can load the full content when needed.
##Place files
Create one folder per skill name and put a SKILL.md inside it.
OpenCode searches these locations:
- Project config:
.opencode/skills/<name>/SKILL.md - Global config:
~/.config/opencode/skills/<name>/SKILL.md - Project Claude-compatible:
.claude/skills/<name>/SKILL.md - Global Claude-compatible:
~/.claude/skills/<name>/SKILL.md
##Understand discovery
For project-local paths, OpenCode walks up from your current working directory until it reaches the git worktree.
It loads any matching skills/*/SKILL.md in .opencode/ and any matching .claude/skills/*/SKILL.md along the way.
Global definitions are also loaded from ~/.config/opencode/skills/*/SKILL.md and ~/.claude/skills/*/SKILL.md.
##Write frontmatter
Each SKILL.md must start with YAML frontmatter.
Only these fields are recognized:
name(required)description(required)license(optional)compatibility(optional)metadata(optional, string-to-string map)
Unknown frontmatter fields are ignored.
##Validate names
name must:
- Be 1–64 characters
- Be lowercase alphanumeric with single hyphen separators
- Not start or end with
- - Not contain consecutive
-- - Match the directory name that contains
SKILL.md
Equivalent regex:
^[a-z0-9]+(-[a-z0-9]+)*$
##Follow length rules
description must be 1-1024 characters.
Keep it specific enough for the agent to choose correctly.
##Use an example
Create .opencode/skills/git-release/SKILL.md like this:
---
name: git-release
description: Create consistent releases and changelogs
license: MIT
compatibility: opencode
metadata:
audience: maintainers
workflow: github
---
## What I do
- Draft release notes from merged PRs
- Propose a version bump
- Provide a copy-pasteable `gh release create` command
## When to use me
Use this when you are preparing a tagged release.
Ask clarifying questions if the target versioning scheme is unclear.
##Recognize tool description
OpenCode lists available skills in the skill tool description.
Each entry includes the skill name and description:
<available_skills>
<skill>
<name>git-release</name>
<description>Create consistent releases and changelogs</description>
</skill>
</available_skills>
The agent loads a skill by calling the tool:
skill({ name: "git-release" })
##Configure permissions
Control which skills agents can access using pattern-based permissions in opencode.json:
{
"permission": {
"skill": {
"*": "allow",
"pr-review": "allow",
"internal-*": "deny",
"experimental-*": "ask"
}
}
}
| Permission | Behavior |
| ---------- | ----------------------------------------- |
| allow | Skill loads immediately |
| deny | Skill hidden from agent, access rejected |
| ask | User prompted for approval before loading |
Patterns support wildcards: internal-* matches internal-docs, internal-tools, etc.
##Override per agent
Give specific agents different permissions than the global defaults.
For custom agents (in agent frontmatter):
---
permission:
skill:
"documents-*": "allow"
---
For built-in agents (in opencode.json):
{
"agent": {
"plan": {
"permission": {
"skill": {
"internal-*": "allow"
}
}
}
}
}
##Disable the skill tool
Completely disable skills for agents that shouldn't use them:
For custom agents:
---
tools:
skill: false
---
For built-in agents:
{
"agent": {
"plan": {
"tools": {
"skill": false
}
}
}
}
When disabled, the <available_skills> section is omitted entirely.
##Troubleshoot loading
If a skill does not show up:
- Verify
SKILL.mdis spelled in all caps - Check that frontmatter includes
nameanddescription - Ensure skill names are unique across all locations
- Check permissions—skills with
denyare hidden from agents