⚒️ skillsmith

"Stop writing AI agent skills by hand. Write once, export to Claude Code, Cursor & OpenCode."

npm version GitHub Release GitHub Stars License CI Sponsor OpenCode Downloads


Write AI agent skills in one canonical format → export to Claude Code, Cursor, and OpenCode with a single command.

npm install -g skillsmithskillsmith init my-skillskillsmith export . --all → done.


🚨 The Problem

AI agents are only as good as the skills you give them. But every framework has its own format:

  • Claude Code uses [Name] metadata blocks in markdown
  • Cursor uses YAML frontmatter in .mdc files
  • OpenCode uses YAML frontmatter in .md files

The result? You write the same skill 3 times. Or you pick one framework and pray it works everywhere. Or worse — you don't write skills at all because the friction is too high.

Every time a new framework comes out, skill authors scramble to rewrite their entire collection. With skillsmith, you write once and ship everywhere.

🎯 What skillsmith Does

# Create a skill in 1 second
skillsmith init my-skill

# Validate and test it
skillsmith test ./my-skill

# Export to every framework at once
skillsmith export ./my-skill --all

Real Output From a Real Skill Test

skillsmith — Testing my-skill v0.1.0
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
✔ SKILL.md format valid
✔ skillsmith.json valid
✔ Framework compatibility: claude ✅ cursor ✅ opencode ✅
✔ Prompt simulation: 4/4 passed
━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
All checks passed.

One skill file. Three frameworks. Zero manual copying.


📊 Why skillsmith? (vs Alternatives)

Feature skillsmith Raw SKILL.md (Manual) Bash Scripts Copied Templates
Multi-framework export Claude, Cursor, OpenCode ❌ One format only ❌ One at a time ❌ One at a time
Skill validation Structure + frontmatter + files ❌ None ❌ None ❌ None
Built-in testing Prompt simulation without LLM
Scaffolding skillsmith init ❌ mkdir + touch
Versioning skillsmith.json + semver ❌ git only ❌ git only ❌ git only
Registry GitHub-based (free)
Install npm i -g skillsmith ❌ git clone ❌ curl | bash ❌ git clone
Dependency-free runtime Node.js built-ins only
CI/CD ready Exit codes, JSON validation
Open source MIT, free forever ❌ varies

The bottom line: If you write AI agent skills for more than one framework — or even if you just want structure and validation — skillsmith saves you an hour per skill. Zero config. Zero lock-in.


⚡ Quick Start

# Install
npm install -g skillsmith

# Create your first skill
skillsmith init my-skill
cd my-skill

What you get

my-skill/
├── SKILL.md              # ← Your skill (canonical format)
├── skillsmith.json        # ← Metadata
├── prompts/
│   ├── example.md         # ← Example prompts
│   └── test-cases.md      # ← Test cases
└── README.md

Write your skill

---
name: my-skill
version: 0.1.0
description: "Expert TypeScript review skill"
frameworks: [claude, cursor, opencode]
---

# Instruction
You are an expert TypeScript reviewer.

# Behaviors
- Check for proper type annotations
- Identify unused imports
- Suggest generic constraints

# Constraints
- Do not suggest `any` types
- Keep feedback under 200 words

Test it

skillsmith test . --prompt "Review this TypeScript function"

Export to every framework

# All frameworks at once
skillsmith export . --all

# Or one at a time
skillsmith export . --framework claude
skillsmith export . --framework cursor
skillsmith export . --framework opencode
Framework Output Generated File
Claude Code [Name] + markdown .claude/skills/my-skill.md
Cursor YAML frontmatter .mdc .cursor/rules/my-skill.mdc
OpenCode YAML frontmatter .md .opencode/skills/my-skill.md

Publish to the community

skillsmith publish .

📦 Installation

Global install (recommended)

npm install -g skillsmith

Run without installing

npx skillsmith --help

Prerequisites

  • Node.js 18+ — any modern version works
  • Your AI agent of choice — OpenCode, Claude Code, or Cursor
  • Zero API keys, zero accounts, zero config

🔧 CLI Reference

skillsmith init <skill-name>

Scaffold a new skill project.

Option Description
--template <framework> Use specific framework as default (claude, cursor, opencode)

skillsmith test <skill-path>

Validate skill structure and run prompt simulations.

Option Description
--prompt <text> Test with a custom prompt instead of prompt files

skillsmith export <skill-path>

Export skill to framework-specific formats.

Option Description
--framework <name> Target framework (claude, cursor, opencode)
--all Export to all supported frameworks at once

skillsmith publish <skill-path>

Validate skill and show step-by-step instructions for publishing to GitHub.

skillsmith list

List skills installed in ~/.skillsmith/.

Option Description
--remote List available skills from the GitHub registry

🧠 Canonical Format

---
name: my-skill
version: 0.1.0
description: "What this skill does"
author: "Your Name"
frameworks: [claude, cursor, opencode]
---

# Instruction
[Natural language instructions for the AI agent]

# Behaviors
- [Specific behavior 1]
- [Specific behavior 2]

# Constraints
- [Constraint 1]
- [Constraint 2]
{
  "name": "my-skill",
  "version": "0.1.0",
  "description": "What this skill does",
  "author": "",
  "license": "MIT",
  "frameworks": ["claude", "cursor", "opencode"],
  "keywords": ["ai-agent", "skill"],
  "repository": {
    "type": "github",
    "url": "https://github.com/FMATheNomad/my-skill"
  }
}
Framework File Format
Claude Code .claude/skills/<name>.md [Name] + [Description] + free-form markdown
Cursor .cursor/rules/<name>.mdc YAML frontmatter (description, globs) + markdown body
OpenCode .opencode/skills/<name>.md YAML frontmatter (name, description) + markdown body

🔄 CI/CD Integration

GitHub Actions — Validate Skills on Push

# .github/workflows/skillsmith.yml
name: Validate Skills
on: [push, pull_request]
jobs:
  validate:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - uses: actions/setup-node@v4
        with:
          node-version: 20
      - run: npm install -g skillsmith
      - run: skillsmith test ./my-skill

Pre-commit Hook — Validate Before Every Commit

#!/bin/sh
# .git/hooks/pre-commit
SKILL_DIRS=$(git diff --cached --name-only --diff-filter=ACM | grep -oP '.*(?=/SKILL\.md)' | sort -u)
for dir in $SKILL_DIRS; do
  skillsmith test "$dir" || exit 1
done

Package.json Script — Validate in Your Workflow

{
  "scripts": {
    "validate-skills": "skillsmith test ./skills/my-skill"
  }
}

🛠 Configuration

skillsmith is zero-config by design. Everything works out of the box.

But you can customize via ~/.skillsmith/config.json:

{
  "author": "FMATheNomad",
  "license": "MIT",
  "defaultFramework": "opencode"
}
Setting Default Description
author "" Default author for new skills
license "MIT" Default license for new skills
defaultFramework "opencode" Default framework template
registryUrl "https://raw.githubusercontent.com/skillsmith-skills/index/main" Registry URL

🏗 How It Works

graph LR
    A[SKILL.md] --> B{skillsmith}
    B --> C[Validate]
    B --> D[Test]
    B --> E[Export]
    B --> F[Publish]
    C --> G[Structure + Frontmatter]
    D --> H[Prompt Simulation]
    E --> I[Claude Code .md]
    E --> J[Cursor .mdc]
    E --> K[OpenCode .md]
    F --> L[GitHub Registry]

🗺 Roadmap

  • Cursor glob patterns — file-type-specific rules per skill
  • skillsmith install — one-command install from registry
  • Human-readable docs — generate markdown docs from SKILL.md
  • Skill composition — import behaviors from other skills
  • Template marketplace — community templates for common patterns
  • VS Code extension — visual skill editor
  • Registry searchskillsmith search <keyword>

🧑‍💻 Development

git clone https://github.com/FMATheNomad/skillsmith
cd skillsmith
npm install
npm run build
npm test

Project Structure

src/
├── cli.ts                # Entry point (Commander)
├── commands/             # CLI commands
│   ├── init.ts           # skillsmith init
│   ├── test.ts           # skillsmith test
│   ├── export.ts         # skillsmith export
│   ├── publish.ts        # skillsmith publish
│   └── list.ts           # skillsmith list
├── formats/              # Framework format converters
│   ├── base.ts           # SkillDefinition interface
│   ├── claude.ts         # Claude Code ↔ canonical
│   ├── cursor.ts         # Cursor ↔ canonical
│   └── opencode.ts       # OpenCode ↔ canonical
├── engine/               # Core engine
│   ├── validator.ts      # Structure validation
│   ├── sandbox.ts        # Prompt simulation
│   └── tester.ts         # Full test suite runner
├── registry/             # Registry client
│   └── github.ts         # GitHub-based registry
└── utils/                # Shared utilities

Adding a New Framework

  1. Create a format file in src/formats/ implementing SkillFormat
  2. Export parse() (framework → canonical) and generate() (canonical → framework)
  3. Register in src/formats/base.ts
  4. Add export case in src/commands/export.ts
  5. Add tests in tests/formats/

📜 License

MIT © FMA Software Labs