Skill: create-skills-and-rules
Use this skill when you need to create or update skills and rules for Claude Code (.claude/), Cursor (.cursor/), and OpenCode (opencode.json).
Directory structure
.claude/
rules/ *.md – always-loaded project instructions
skills/ <name>/SKILL.md – step-by-step guides, invocable or auto-matched by description
.cursor/
rules/ *.mdc – Cursor rules with description/globs/alwaysApply frontmatter
skills/ *.md – flat files, same content as .claude/skills/ (Cursor reads them as reference)
opencode.json – OpenCode config: instructions array points to .claude/rules/*.md
Cross-tool compatibility:
- Claude Code reads both flat files and directory-based skills from
.claude/skills/ - OpenCode reads only directory-based skills (
.claude/skills/<name>/SKILL.md) — flat files are ignored - Cursor reads flat files from
.cursor/skills/*.mdas reference documents - Rules are loaded by OpenCode via
opencode.jsoninstructionsarray
Standard format: Always use directory-based skills (<name>/SKILL.md) for compatibility with all tools.
Step 1 – Decide: rule or skill
| Type | Purpose | When loaded |
|---|---|---|
| Rule | Constraints, conventions, best practices | Automatically, based on globs or alwaysApply |
| Skill | Step-by-step implementation guide | When description matches task, or invoked via /skill-name |
Rules say what to do / not do. Skills say how to do it step by step.
Step 2 – Create a skill (.claude/skills/<name>/SKILL.md)
Create the directory and file
mkdir -p .claude/skills/my-skill-name
# then create .claude/skills/my-skill-name/SKILL.md
Required frontmatter
---
name: my-skill-name
description: Short description of what this skill does and when to use it
---
| Field | Required by | Description |
|---|---|---|
name |
OpenCode, Claude Code | Must match directory name exactly. Lowercase, hyphens only, regex ^[a-z0-9]+(-[a-z0-9]+)*$, max 64 chars |
description |
All tools | When to use — Claude/OpenCode match this to decide auto-invocation |
Optional frontmatter fields (Claude Code only)
---
name: my-skill
description: What this skill does
user-invocable: true
disable-model-invocation: false
allowed-tools: Read, Grep, Bash
context: fork
agent: Explore
argument-hint: [filename]
model: sonnet
---
| Field | Default | Description |
|---|---|---|
user-invocable |
true |
Show in / menu |
disable-model-invocation |
false |
Prevent auto-loading by Claude |
allowed-tools |
– | Tools allowed without asking (e.g. Read, Grep, Bash) |
context |
– | Set to fork to run in isolated subagent |
agent |
– | Subagent type when context: fork (Explore, Plan, etc.) |
argument-hint |
– | Hint for autocomplete (e.g. [issue-number]) |
model |
inherited | Model override (sonnet, opus, haiku) |
OpenCode ignores unknown frontmatter fields, so these are safe to include.
Dynamic substitutions in skill content
$ARGUMENTS– all arguments passed when invoking$ARGUMENTS[0],$1– specific argument by index${CLAUDE_SESSION_ID}– current session ID${CLAUDE_SKILL_DIR}– directory containing SKILL.md
Body structure
---
name: my-skill-name
description: Build X with Y and Z
---
# Skill: my-skill-name
Use this skill when you build **X** using Y and Z.
## When to use
- Bullet list of scenarios
## Step 1 – First step
Explanation + code example.
## Step 2 – Second step
Explanation + code example.
Keep skills under 500 lines. Use clear step numbering. Include real code examples.
Step 3 – Create a Claude Code rule (.claude/rules/<name>.md)
Frontmatter
---
description: Short description of this rule's purpose
globs: **/front/src/**/*.{vue,js,ts}
---
| Field | Description |
|---|---|
description |
What this rule covers (used for matching) |
globs |
File patterns that trigger this rule (e.g. **/*.js, **/services/**/*.js) |
Backend / LiveChange service rules — standard globs
Rules for server-side LiveChange code (models, actions, triggers, service layout) should use a comma-separated globs line so they still match when a project stores services under different folder names (many teams copy .cursor/rules into other repos):
globs: **/services/**/*.js, **/server/**/*.js, server/**/*.js
| Pattern | Covers |
|---|---|
**/services/**/*.js |
Trees such as live-change-stack/services/<service>/ |
**/server/**/*.js |
Any nested server/ directory (e.g. app/server/, packages/foo/server/) |
server/**/*.js |
Backend rooted at top-level server/ |
Frontend rules keep their own globs (e.g. **/front/src/**/*.{vue,js,ts}). Do not drop the server variants for backend-only rules — otherwise Cursor will miss files after a layout change.
Body structure
---
description: Rules for X development
globs: **/*.js
---
# Title
## Section 1
- Rule bullet points
- Code examples
## Section 2
- More rules
Rules are concise. Lead with the constraint, then show a code example.
Step 4 – Create Cursor rule (.cursor/rules/<name>.mdc)
Same content as the Claude rule, but with Cursor-specific frontmatter:
---
description: Short description of this rule's purpose
globs: **/front/src/**/*.{vue,js,ts}
alwaysApply: false
---
| Field | Default | Description |
|---|---|---|
description |
– | What the rule does; Cursor uses this to decide when to apply |
globs |
– | Comma-separated file patterns (e.g. **/*.tsx, src/**/*.js) |
alwaysApply |
false |
If true, applies to every session regardless of context |
Notes:
- Do NOT quote glob patterns in frontmatter
- Keep rules short (target 25 lines, max 50 lines for best Cursor performance)
- The
.mdcextension is required for Cursor - For backend LiveChange rules, use the same
globsstandard as in Claude rules:**/services/**/*.js, **/server/**/*.js, server/**/*.js
Step 5 – Register rules in OpenCode (opencode.json)
OpenCode reads .claude/skills/<name>/SKILL.md natively for skills (no extra step needed). But rules must be registered in opencode.json:
{
"$schema": "https://opencode.ai/config.json",
"instructions": [
".claude/rules/live-change-backend-architecture.md",
".claude/rules/live-change-frontend-vue-primevue.md"
]
}
When you create a new rule, add its path to the instructions array in opencode.json.
Project rule live-change-node-toolchain-fnm should stay first (or early) in instructions so agents always load the requirement to run node, npm, npx, and tsx via fnm exec using .node-version / .nvmrc.
When you create a new skill, no opencode.json change is needed — OpenCode discovers skills from .claude/skills/<name>/SKILL.md automatically.
When a skill or rule shows shell examples that invoke node, npm, npx, or tsx, use the fnm exec -- … form (see .claude/rules/live-change-node-toolchain-fnm.md and skill live-change-node-toolchain-fnm).
Important: OpenCode ignores the globs frontmatter from Claude Code rules. All instructions listed in opencode.json are always loaded.
Step 6 – Mirror Cursor skills (.cursor/skills/<name>.md)
Copy the skill content to .cursor/skills/ as a flat file (Cursor reads flat .md files as reference):
cp .claude/skills/my-skill-name/SKILL.md .cursor/skills/my-skill-name.md
The content is the same (including name in frontmatter). Cursor ignores unknown frontmatter fields.
Step 7 – Mirror to sub-projects
If the project has sub-projects with their own .claude/ and .cursor/ directories, copy the files there too:
for dir in automation auto-firma; do
# Skills: directory format for .claude, flat for .cursor
mkdir -p "$dir/.claude/skills/my-skill-name"
cp .claude/skills/my-skill-name/SKILL.md "$dir/.claude/skills/my-skill-name/SKILL.md"
cp .claude/skills/my-skill-name/SKILL.md "$dir/.cursor/skills/my-skill-name.md"
# Rules
cp .claude/rules/my-rule.md "$dir/.claude/rules/"
cp .cursor/rules/my-rule.mdc "$dir/.cursor/rules/"
done
Naming conventions
- Use lowercase with hyphens:
live-change-frontend-editor-form - Must match regex
^[a-z0-9]+(-[a-z0-9]+)*$(OpenCode requirement) - Prefix with domain:
live-change-frontend-*,live-change-backend-* - Skills describe actions:
*-editor-form,*-range-list,*-action-buttons - Rules describe scope:
*-vue-primevue,*-models-and-relations
Checklist
- Shell examples for Node/npm use
fnm exec --perlive-change-node-toolchain-fnm - Directory created:
.claude/skills/<name>/SKILL.md - Frontmatter has both
name(matching dir) anddescription -
.cursor/skills/<name>.mdmirrored (flat file, same content) -
.claude/rules/*.mdcreated (if rule) -
.cursor/rules/*.mdccreated withglobs+alwaysApply(if rule) - Backend rules use standard
globs:**/services/**/*.js, **/server/**/*.js, server/**/*.js(when the rule targets LiveChange server code) -
opencode.jsoninstructionsarray updated (if new rule) - Sub-projects updated (automation, auto-firma)
Source: live-change/live-change-stack — distributed by TomeVault.