Skip to main content
The Skills CLI uses the AgentConfig interface to define how to detect and install skills for each supported coding agent.

AgentConfig Interface

Defined in src/types.ts, the AgentConfig interface specifies the configuration for each agent:
export interface AgentConfig {
  name: string;
  displayName: string;
  skillsDir: string;
  globalSkillsDir: string | undefined;
  detectInstalled: () => Promise<boolean>;
  showInUniversalList?: boolean;
}

Field Reference

name
string
required
Unique identifier for the agent in kebab-case. Used in CLI commands with the --agent flag.Examples:
  • claude-code
  • cursor
  • github-copilot
This is also the AgentType used throughout the codebase.
displayName
string
required
Human-readable name shown in CLI output and prompts.Examples:
  • "Claude Code"
  • "Cursor"
  • "GitHub Copilot"
skillsDir
string
required
Relative path where skills are installed in project scope.Examples:
  • .claude/skills - Claude Code
  • .agents/skills - Universal agents (Cursor, OpenCode, etc.)
  • skills - OpenClaw (no dot prefix)
This path is relative to the current working directory when installing project-scoped skills.
globalSkillsDir
string | undefined
required
Absolute path where global skills are installed (typically in user’s home directory).Set to undefined if the agent doesn’t support global installation.Examples:
  • ~/.claude/skills - Claude Code global skills
  • ~/.config/opencode/skills - OpenCode global skills
  • ~/.codeium/windsurf/skills - Windsurf global skills
Use join(home, '.agent/skills') or join(configHome, 'agent/skills') to construct platform-independent paths.
detectInstalled
() => Promise<boolean>
required
Async function that returns true if the agent is installed on the system.Common detection strategies:
  • Check if config directory exists: existsSync(join(home, '.agent'))
  • Check for project marker file: existsSync(join(cwd(), '.replit'))
  • Check multiple possible locations (OpenClaw supports 3 legacy paths)
Example implementation:
detectInstalled: async () => {
  return existsSync(join(home, '.claude'));
}
showInUniversalList
boolean
default:true
Whether to show this agent in the universal agents list.Set to false for:
  • Agents that shouldn’t be auto-selected (e.g., universal meta-agent)
  • Platform-specific agents (e.g., Replit)
Example:
showInUniversalList: false

Agent Types

All supported agent identifiers are defined in the AgentType union type:
export type AgentType =
  | 'amp'
  | 'antigravity'
  | 'augment'
  | 'claude-code'
  | 'openclaw'
  | 'cline'
  | 'codebuddy'
  | 'codex'
  | 'command-code'
  | 'continue'
  // ... 42+ agents total
  | 'universal';
See src/types.ts for the complete list of supported agent types.

Agent Registry

All agent configurations are stored in the agents object in src/agents.ts:
export const agents: Record<AgentType, AgentConfig> = {
  'claude-code': {
    name: 'claude-code',
    displayName: 'Claude Code',
    skillsDir: '.claude/skills',
    globalSkillsDir: join(claudeHome, 'skills'),
    detectInstalled: async () => {
      return existsSync(claudeHome);
    },
  },
  // ... more agents
};

Universal Agents

Some agents share a common skills directory (.agents/skills/). These are called “universal agents”:
  • Amp
  • Cline
  • Codex
  • Cursor
  • Gemini CLI
  • GitHub Copilot
  • Kimi Code CLI
  • OpenCode
  • Replit
Benefits:
  • No symlinks needed between agents
  • Single installation serves multiple agents
  • Easier to manage and update
Helper functions:
// Get all universal agents
const universalAgents = getUniversalAgents();

// Check if an agent is universal
const isUniversal = isUniversalAgent('cursor'); // true

// Get non-universal agents (need symlinks)
const nonUniversal = getNonUniversalAgents();

Agent Detection

The CLI automatically detects which agents are installed:
const installedAgents = await detectInstalledAgents();
// Returns: ['claude-code', 'cursor', 'opencode']
Detection flow:
1

Iterate all agents

Check each agent’s detectInstalled() function.
2

Run in parallel

All detection checks run concurrently using Promise.all().
3

Filter results

Return only agents where detectInstalled() returned true.

Environment Variables

Some agents support custom configuration paths via environment variables:
CLAUDE_CONFIG_DIR
string
Custom Claude Code config directory.Default: ~/.claudeExample:
export CLAUDE_CONFIG_DIR=~/my-custom-claude
npx skills add owner/repo -a claude-code
CODEX_HOME
string
Custom Codex home directory.Default: ~/.codexExample:
export CODEX_HOME=~/my-custom-codex
npx skills add owner/repo -a codex

Platform Differences

The agent system handles platform-specific path differences:

XDG Base Directory

On Linux/macOS, some agents follow the XDG Base Directory specification:
import { xdgConfig } from 'xdg-basedir';

const configHome = xdgConfig ?? join(home, '.config');

// OpenCode uses XDG config
globalSkillsDir: join(configHome, 'opencode/skills')
Agents using XDG:
  • OpenCode: ~/.config/opencode/skills/
  • Goose: ~/.config/goose/skills/
  • Amp: ~/.config/amp/skills/
  • Crush: ~/.config/crush/skills/

Windows Compatibility

Paths work across platforms using Node’s path module:
import { join } from 'path';

// Works on Windows and Unix
const skillsPath = join(home, '.claude', 'skills');

Adding a New Agent

To add support for a new agent:
1

Add to AgentType

Edit src/types.ts and add your agent to the AgentType union:
export type AgentType =
  | 'existing-agent'
  | 'my-new-agent'
  | ...;
2

Add configuration

Edit src/agents.ts and add your agent config:
'my-new-agent': {
  name: 'my-new-agent',
  displayName: 'My New Agent',
  skillsDir: '.myagent/skills',
  globalSkillsDir: join(home, '.myagent/skills'),
  detectInstalled: async () => {
    return existsSync(join(home, '.myagent'));
  },
},
3

Validate

Run the validation script:
pnpm run -C scripts validate-agents.ts
4

Sync to README

Update documentation:
pnpm run -C scripts sync-agents.ts
5

Test

Test installation:
pnpm dev add vercel-labs/agent-skills --agent my-new-agent
See the Contributing Guide for detailed instructions.

Agent-Specific Notes

OpenClaw supports three legacy directory names:
export function getOpenClawGlobalSkillsDir() {
  if (existsSync(join(home, '.openclaw'))) {
    return join(home, '.openclaw/skills');
  }
  if (existsSync(join(home, '.clawdbot'))) {
    return join(home, '.clawdbot/skills');
  }
  if (existsSync(join(home, '.moltbot'))) {
    return join(home, '.moltbot/skills');
  }
  return join(home, '.openclaw/skills');
}
This ensures backwards compatibility with older installations.
Kiro CLI requires manual configuration after skill installation:Edit .kiro/agents/<agent>.json:
{
  "resources": ["skill://.kiro/skills/**/SKILL.md"]
}
This is because Kiro uses a custom resource loading mechanism.
Replit detection looks for .replit file:
detectInstalled: async () => {
  return existsSync(join(process.cwd(), '.replit'));
}
Also has showInUniversalList: false since it’s platform-specific.
The universal agent is a meta-agent that never detects as installed:
universal: {
  name: 'universal',
  displayName: 'Universal',
  skillsDir: '.agents/skills',
  globalSkillsDir: join(configHome, 'agents/skills'),
  showInUniversalList: false,
  detectInstalled: async () => false,
}
It represents the shared .agents/skills/ directory used by universal agents.

Utility Functions

getAgentConfig(type: AgentType): AgentConfig

Get configuration for a specific agent:
const config = getAgentConfig('claude-code');
console.log(config.displayName); // "Claude Code"

getUniversalAgents(): AgentType[]

Get all agents using .agents/skills/ directory:
const universal = getUniversalAgents();
// ['amp', 'cline', 'codex', 'cursor', ...]

getNonUniversalAgents(): AgentType[]

Get agents with custom skill directories:
const nonUniversal = getNonUniversalAgents();
// ['claude-code', 'windsurf', 'goose', ...]

isUniversalAgent(type: AgentType): boolean

Check if an agent uses universal directory:
if (isUniversalAgent('cursor')) {
  console.log('No symlink needed');
}

CLI Options

Learn how to target specific agents

Compatibility

Agent feature compatibility matrix

Contributing

How to add a new agent

Skill Format

SKILL.md format specification

Build docs developers (and LLMs) love