sundial-hub 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/index.ts","../src/constants.ts","../src/core/agents.ts","../src/commands/add.ts","../src/core/config-manager.ts","../src/core/agent-detect.ts","../src/core/skill-install.ts","../src/core/skill-source.ts","../src/lib/supabase.ts","../src/utils/registry.ts","../src/core/skill-info.ts","../src/core/skill-hash.ts","../src/utils/prompts.ts","../src/utils/checkbox-extended.ts","../src/utils/tree.ts","../src/commands/remove.ts","../src/commands/list.ts","../src/commands/list-registry.ts","../src/commands/show.ts","../src/commands/show-dev.ts","../src/commands/config.ts","../src/utils/fuzzy-match.ts"],"sourcesContent":["#!/usr/bin/env node\n\nimport { Command } from 'commander';\nimport chalk from 'chalk';\nimport { createRequire } from 'module';\n\nconst require = createRequire(import.meta.url);\nconst { version } = require('../package.json');\nimport { SUPPORTED_AGENTS } from './core/agents';\nimport { addCommand } from './commands/add';\nimport { removeCommand } from './commands/remove';\nimport { listCommand } from './commands/list';\nimport { listRegistryCommand } from './commands/list-registry';\nimport { showCommand } from './commands/show';\nimport { configCommand } from './commands/config';\nimport { suggestCommand, getValidCommands } from './utils/fuzzy-match';\nimport type { CommandFlags } from './types/index';\n\nconst program = new Command();\n\nfunction isPromptExit(error: unknown): boolean {\n return error instanceof Error && error.name === 'ExitPromptError';\n}\n\nfunction handleCommandError(error: unknown): never {\n // Quietly exit when user cancels an interactive prompt (Ctrl+C / SIGINT).\n if (isPromptExit(error)) {\n process.exit(130);\n }\n\n console.error(chalk.red(error instanceof Error ? error.message : String(error)));\n process.exit(1);\n}\n\nprogram\n .name('sun')\n .description('Sundial CLI - Manage skills for your AI agents')\n .version(version);\n\n// Add command\nconst add = program\n .command('add <skills...>')\n .description('Add skill(s) to agent configuration(s)')\n .option('--global', 'Install to global agent config (~/.claude/, ~/.codex/, etc.)');\n\n// Add agent flags dynamically\nfor (const agent of SUPPORTED_AGENTS) {\n add.option(`--${agent.flag}`, `Install to ${agent.name}`);\n}\n\nadd.action(async (skills: string[], options: CommandFlags) => {\n try {\n await addCommand(skills, options);\n } catch (error) {\n handleCommandError(error);\n }\n});\n\n// Remove command\nconst remove = program\n .command('remove <skills...>')\n .description('Remove skill(s) from agent configuration(s)')\n .option('--global', 'Remove from global config');\n\nfor (const agent of SUPPORTED_AGENTS) {\n remove.option(`--${agent.flag}`, `Remove from ${agent.name}`);\n}\n\nremove.action(async (skills: string[], options: CommandFlags) => {\n try {\n await removeCommand(skills, options);\n } catch (error) {\n handleCommandError(error);\n }\n});\n\n// List command (registry)\nprogram\n .command('list')\n .description('List available skills from the registry')\n .action(async () => {\n try {\n await listRegistryCommand();\n } catch (error) {\n handleCommandError(error);\n }\n });\n\n// Installed command (alias for installed skills)\nprogram\n .command('installed')\n .alias('list-installed')\n .description('List installed skills for each agent')\n .action(async () => {\n try {\n await listCommand();\n } catch (error) {\n handleCommandError(error);\n }\n });\n\n// Show command\nprogram\n .command('show [skill]')\n .description('Show all agent folders and packages, or details for a specific skill')\n .action(async (skill?: string) => {\n try {\n await showCommand(skill);\n } catch (error) {\n handleCommandError(error);\n }\n });\n\n// Config command\nprogram\n .command('config')\n .description('Configure default agents')\n .action(async () => {\n try {\n await configCommand();\n } catch (error) {\n handleCommandError(error);\n }\n });\n\n// Handle unknown commands with fuzzy matching\nprogram.on('command:*', (operands) => {\n const unknownCommand = operands[0];\n const suggestion = suggestCommand(unknownCommand);\n\n console.error(chalk.red(`Error: Unknown command '${unknownCommand}'`));\n\n if (suggestion) {\n console.error(chalk.yellow(`Did you mean '${suggestion}'?`));\n }\n\n console.error();\n console.error(`Valid commands: ${getValidCommands().join(', ')}`);\n process.exit(1);\n});\n\n// Parse and execute\nprogram.parse();\n","import type { AgentConfig } from './types/index';\n\n/** Available CLI commands */\nexport const COMMANDS = ['add', 'remove', 'list', 'show', 'config'] as const;\n\n/** Supported AI agents */\nexport const AGENTS: AgentConfig[] = [\n { name: 'Claude Code', flag: 'claude', folderName: '.claude' },\n { name: 'Codex', flag: 'codex', folderName: '.codex' },\n { name: 'Gemini', flag: 'gemini', folderName: '.gemini' }\n];\n\nexport const STORAGE_URL = 'https://vfbndmrgggrhnlrileqv.supabase.co/storage/v1/object/public/skill-zips';\n","import type { AgentConfig } from '../types/index';\nimport { AGENTS } from '../constants';\n\n// Re-export for backwards compatibility\nexport const SUPPORTED_AGENTS = AGENTS;\n\nexport function getAgentByFlag(flag: string): AgentConfig | undefined {\n return AGENTS.find(agent => agent.flag === flag);\n}\n\nexport function getSupportedAgentsMessage(): string {\n return `Currently supported agents: ${AGENTS.map(a => a.name).join(', ')}`;\n}\n","import chalk from 'chalk';\nimport ora from 'ora';\nimport { getAgentByFlag, SUPPORTED_AGENTS } from '../core/agents';\nimport { isFirstRun, getDefaultAgents, setDefaultAgents } from '../core/config-manager';\nimport { detectLocalAgents } from '../core/agent-detect';\nimport { getSkillInstallPath, installSkill, type ConfirmSkillOverride } from '../core/skill-install';\nimport { promptAgentSelection, promptSkillOverride } from '../utils/prompts';\nimport { formatDirectoryTree, indentLines } from '../utils/tree';\nimport type { AgentType, CommandFlags } from '../types/index';\n\n/**\n * Determine which agents to install to and whether to install globally.\n *\n * Logic:\n * 1. If --global flag is set, always install globally\n * 2. If agent flags (--claude, --codex, etc.) are set, use those agents\n * 3. If first run, detect agents and prompt for selection\n * 4. Otherwise use saved default agents\n *\n * For local vs global:\n * - If --global: always global\n * - Otherwise: check if any configured agents have local folders\n * - If yes: install locally to those\n * - If no local folders exist for configured agents: install globally\n */\nasync function resolveTargetAgents(flags: CommandFlags): Promise<{ agents: AgentType[]; isGlobal: boolean }> {\n const forceGlobal = flags.global ?? false;\n\n // Check if any agent flags were explicitly set\n const explicitAgents: AgentType[] = [];\n for (const agent of SUPPORTED_AGENTS) {\n if (flags[agent.flag as keyof CommandFlags]) {\n explicitAgents.push(agent.flag as AgentType);\n }\n }\n\n let targetAgents: AgentType[];\n\n // Determine which agents to target\n if (explicitAgents.length > 0) {\n targetAgents = explicitAgents;\n } else if (await isFirstRun()) {\n // First run: show agent type selection dialog\n const selectedAgents = await promptAgentSelection();\n await setDefaultAgents(selectedAgents);\n targetAgents = selectedAgents;\n } else {\n // Use saved defaults\n const defaultAgents = await getDefaultAgents();\n if (defaultAgents.length === 0) {\n throw new Error('No default agents configured. Run \"sun config\" to set up your agents.');\n }\n targetAgents = defaultAgents;\n }\n\n // Determine if we should install globally or locally\n if (forceGlobal) {\n return { agents: targetAgents, isGlobal: true };\n }\n\n // Check if any of the target agents have local folders in current directory\n const localAgents = await detectLocalAgents();\n const localAgentFlags = new Set(localAgents.map(a => a.agent.flag));\n\n const hasLocalFolders = targetAgents.some(agentFlag => localAgentFlags.has(agentFlag));\n\n // If no local folders exist for any configured agent, install globally\n const isGlobal = !hasLocalFolders;\n\n return { agents: targetAgents, isGlobal };\n}\n\nfunction formatList(items: string[]): string {\n if (items.length === 0) {\n return '';\n }\n if (items.length === 1) {\n return items[0];\n }\n if (items.length === 2) {\n return `${items[0]} or ${items[1]}`;\n }\n return `${items.slice(0, -1).join(', ')}, or ${items[items.length - 1]}`;\n}\n\nexport interface AddResult {\n skill: string;\n installedNames: string[];\n agents: string[];\n isGlobal: boolean;\n error?: string;\n}\n\n/**\n * Add skill(s) to agent configuration(s).\n */\nexport async function addCommand(skills: string[], flags: CommandFlags): Promise<void> {\n // Resolve target agents\n const { agents, isGlobal } = await resolveTargetAgents(flags);\n const hasExplicitAgentFlags = SUPPORTED_AGENTS.some(agent => flags[agent.flag as keyof CommandFlags]);\n\n const results: AddResult[] = [];\n\n for (const skill of skills) {\n const spinner = ora(`Adding ${skill}...`).start();\n const confirmOverride: ConfirmSkillOverride = async params => {\n if (spinner.isSpinning) {\n spinner.stop();\n }\n return promptSkillOverride(params);\n };\n\n const result: AddResult = {\n skill,\n installedNames: [],\n agents: [],\n isGlobal\n };\n\n try {\n // Install to each target agent\n for (const agentFlag of agents) {\n const { skillNames } = await installSkill(skill, agentFlag, isGlobal, confirmOverride);\n if (skillNames.length > 0) {\n result.installedNames = [...new Set([...result.installedNames, ...skillNames])];\n result.agents.push(getAgentByFlag(agentFlag)!.name);\n }\n }\n\n if (result.installedNames.length === 0) {\n spinner.info(`Skipped ${skill}`);\n } else {\n spinner.succeed(`Added ${result.installedNames.join(', ')}`);\n }\n } catch (error) {\n const message = error instanceof Error ? error.message : String(error);\n result.error = message;\n spinner.fail(`Failed to add ${skill}: ${message}`);\n }\n\n results.push(result);\n }\n\n // Print summary\n const successful = results.filter(r => !r.error && r.installedNames.length > 0);\n if (successful.length > 0) {\n const allSkills = [...new Set(successful.flatMap(r => r.installedNames))];\n const agentFolders = [...new Set(successful.flatMap(r => r.agents))];\n\n const primaryAgent = agents[0];\n if (primaryAgent) {\n for (const result of successful) {\n const skillNames = [...new Set(result.installedNames)];\n for (const skillName of skillNames) {\n const treePath = getSkillInstallPath(skillName, primaryAgent, result.isGlobal);\n const tree = await formatDirectoryTree(treePath);\n console.log();\n console.log(chalk.cyan(`Skill folder for ${skillName}:`));\n console.log(indentLines(tree, ' '));\n }\n }\n }\n\n console.log();\n const location = isGlobal ? '(global)' : '(local)';\n console.log(chalk.green(`Added ${allSkills.join(', ')} to ${agentFolders.join(' and ')} ${chalk.gray(location)}`));\n\n const promptAgents = hasExplicitAgentFlags ? agents : await getDefaultAgents();\n const commandHints = promptAgents.map(command => `\\`${command}\\``);\n const plural = allSkills.length > 1 ? 'skills' : 'skill';\n console.log(chalk.cyan(`Next: run ${formatList(commandHints)} and ask it to use the downloaded ${plural}`));\n }\n}\n","import fs from 'fs-extra';\nimport path from 'path';\nimport os from 'os';\nimport type { SunConfig, AgentType } from '../types/index';\n\nconst CONFIG_DIR = path.join(os.homedir(), '.sun');\nconst CONFIG_FILE = path.join(CONFIG_DIR, 'config.json');\n\nconst DEFAULT_CONFIG: SunConfig = {\n defaultAgents: [],\n firstRunComplete: false\n};\n\nexport async function ensureConfigDir(): Promise<void> {\n await fs.ensureDir(CONFIG_DIR);\n}\n\nexport async function loadConfig(): Promise<SunConfig> {\n try {\n await ensureConfigDir();\n if (await fs.pathExists(CONFIG_FILE)) {\n const content = await fs.readFile(CONFIG_FILE, 'utf-8');\n return { ...DEFAULT_CONFIG, ...JSON.parse(content) };\n }\n } catch {\n // Config doesn't exist or is invalid, return default\n }\n return { ...DEFAULT_CONFIG };\n}\n\nexport async function saveConfig(config: SunConfig): Promise<void> {\n await ensureConfigDir();\n await fs.writeFile(CONFIG_FILE, JSON.stringify(config, null, 2));\n}\n\nexport async function isFirstRun(): Promise<boolean> {\n const config = await loadConfig();\n return !config.firstRunComplete;\n}\n\nexport async function getDefaultAgents(): Promise<AgentType[]> {\n const config = await loadConfig();\n return config.defaultAgents;\n}\n\nexport async function setDefaultAgents(agents: AgentType[]): Promise<void> {\n const config = await loadConfig();\n config.defaultAgents = agents;\n config.firstRunComplete = true;\n await saveConfig(config);\n}\n\nexport function getConfigPath(): string {\n return CONFIG_FILE;\n}\n","import fs from 'fs-extra';\nimport path from 'path';\nimport os from 'os';\nimport { exec } from 'child_process';\nimport { promisify } from 'util';\nimport { SUPPORTED_AGENTS } from './agents';\nimport type { DetectedAgent, AgentConfig } from '../types/index';\n\nconst execAsync = promisify(exec);\n\n// Agent folder names to search for\nconst AGENT_FOLDER_NAMES = new Set(SUPPORTED_AGENTS.map(a => a.folderName));\n\nexport async function detectAgentsInDirectory(directory: string, isGlobal: boolean): Promise<DetectedAgent[]> {\n const detected: DetectedAgent[] = [];\n\n for (const agent of SUPPORTED_AGENTS) {\n const agentPath = path.join(directory, agent.folderName);\n if (await fs.pathExists(agentPath)) {\n detected.push({\n agent,\n path: agentPath,\n isGlobal\n });\n }\n }\n\n return detected;\n}\n\nexport async function detectLocalAgents(): Promise<DetectedAgent[]> {\n return detectAgentsInDirectory(process.cwd(), false);\n}\n\nexport async function detectGlobalAgents(): Promise<DetectedAgent[]> {\n return detectAgentsInDirectory(os.homedir(), true);\n}\n\n/**\n * Search the entire file system for all agent folders.\n * Uses `find -type d -name` for efficiency.\n */\nexport async function detectAllAgentFolders(): Promise<DetectedAgent[]> {\n const results: DetectedAgent[] = [];\n const homeDir = os.homedir();\n\n // Build find command: find ~ -type d \\( -name \".claude\" -o -name \".codex\" -o -name \".gemini\" \\)\n const namePatterns = SUPPORTED_AGENTS.map(a => `-name \"${a.folderName}\"`).join(' -o ');\n const findCmd = `find \"${homeDir}\" -type d \\\\( ${namePatterns} \\\\) 2>/dev/null`;\n\n try {\n const { stdout } = await execAsync(findCmd, { maxBuffer: 10 * 1024 * 1024 });\n const agentPaths = stdout.trim().split('\\n').filter(Boolean);\n\n for (const agentPath of agentPaths) {\n const folderName = path.basename(agentPath);\n const agent = SUPPORTED_AGENTS.find(a => a.folderName === folderName);\n if (!agent) continue;\n\n const isGlobal = path.dirname(agentPath) === homeDir;\n results.push({\n agent,\n path: agentPath,\n isGlobal\n });\n }\n } catch {\n // find command failed - fall back to simple detection\n const [local, global] = await Promise.all([\n detectLocalAgents(),\n detectGlobalAgents()\n ]);\n return [...local, ...global];\n }\n\n return results;\n}\n\n/**\n * Search the entire file system for agent folders that contain skills.\n * Uses `find` to locate skills directories with content.\n */\nexport async function detectAllSkillsFolders(): Promise<DetectedAgent[]> {\n const allAgents = await detectAllAgentFolders();\n\n // Filter to only those with skills installed\n const withSkills: DetectedAgent[] = [];\n for (const detected of allAgents) {\n const skillsDir = path.join(detected.path, 'skills');\n if (await fs.pathExists(skillsDir)) {\n const entries = await fs.readdir(skillsDir);\n if (entries.length > 0) {\n withSkills.push(detected);\n }\n }\n }\n\n return withSkills;\n}\n\n/**\n * Detect agents in local and global directories only (fast).\n */\nexport async function detectAllAgents(): Promise<DetectedAgent[]> {\n const [local, global] = await Promise.all([\n detectLocalAgents(),\n detectGlobalAgents()\n ]);\n return [...local, ...global];\n}\n\nexport function getAgentPath(agent: AgentConfig, isGlobal: boolean): string {\n const baseDir = isGlobal ? os.homedir() : process.cwd();\n return path.join(baseDir, agent.folderName);\n}\n\nexport function getSkillsPath(agent: AgentConfig, isGlobal: boolean): string {\n return path.join(getAgentPath(agent, isGlobal), 'skills');\n}\n\nexport async function ensureSkillsDirectory(agent: AgentConfig, isGlobal: boolean): Promise<string> {\n const skillsPath = getSkillsPath(agent, isGlobal);\n await fs.ensureDir(skillsPath);\n return skillsPath;\n}\n","import fs from 'fs-extra';\nimport path from 'path';\nimport os from 'os';\nimport { execFileSync } from 'child_process';\nimport AdmZip from 'adm-zip';\nimport { getAgentByFlag } from './agents';\nimport { resolveSkillSource } from './skill-source';\nimport { findSkillDirectories, readSkillMetadata } from './skill-info';\nimport type { AgentType, SkillSource } from '../types/index';\nimport { trackDownload } from '../lib/supabase';\nimport { getShortcutZipUrl } from '../utils/registry.js';\n\n/**\n * Get the destination path for installing a skill.\n * Skill name comes from SKILL.md frontmatter.\n */\nexport function getSkillInstallPath(skillName: string, agentFlag: AgentType, isGlobal: boolean): string {\n const agent = getAgentByFlag(agentFlag);\n if (!agent) {\n throw new Error(`Unknown agent: ${agentFlag}`);\n }\n\n const base = isGlobal ? os.homedir() : process.cwd();\n return path.join(base, agent.folderName, 'skills', skillName);\n}\n\n/**\n * Install a single skill directory to an agent.\n * The skill name is taken from SKILL.md frontmatter (not the folder name).\n * The destination folder will be named after the frontmatter name.\n */\nexport type ConfirmSkillOverride = (params: {\n skillName: string;\n agentFlag: AgentType;\n isGlobal: boolean;\n destPath: string;\n}) => Promise<boolean>;\n\nasync function installSkillDirectory(\n skillDir: string,\n agentFlag: AgentType,\n isGlobal: boolean,\n confirmOverride?: ConfirmSkillOverride\n): Promise<string | null> {\n // Get metadata from SKILL.md frontmatter (name and description are required)\n const metadata = await readSkillMetadata(skillDir);\n if (!metadata) {\n throw new Error(`Invalid skill at \"${skillDir}\": SKILL.md must have name and description in frontmatter`);\n }\n\n const dest = getSkillInstallPath(metadata.name, agentFlag, isGlobal);\n\n if (await fs.pathExists(dest)) {\n if (confirmOverride) {\n const shouldOverwrite = await confirmOverride({\n skillName: metadata.name,\n agentFlag,\n isGlobal,\n destPath: dest\n });\n if (!shouldOverwrite) {\n return null;\n }\n }\n }\n\n // Ensure parent directory exists\n await fs.ensureDir(path.dirname(dest));\n\n // Copy the skill folder (folder will be renamed to match frontmatter name)\n await fs.copy(skillDir, dest, { overwrite: true });\n\n return metadata.name;\n}\n\n/**\n * Install skill(s) from a local path.\n * Checks if path is a skill, otherwise checks direct children for SKILL.md.\n */\nexport async function installFromLocal(\n source: SkillSource,\n agentFlag: AgentType,\n isGlobal: boolean,\n confirmOverride?: ConfirmSkillOverride\n): Promise<string[]> {\n const skillDirs = await findSkillDirectories(source.location);\n\n if (skillDirs.length === 0) {\n throw new Error(`No skills found in \"${source.location}\". A skill must contain a SKILL.md file.`);\n }\n\n const installedSkills: string[] = [];\n for (const skillDir of skillDirs) {\n const skillName = await installSkillDirectory(skillDir, agentFlag, isGlobal, confirmOverride);\n if (skillName) {\n installedSkills.push(skillName);\n }\n }\n\n return installedSkills;\n}\n\n/**\n * Install skill(s) from a zip URL.\n * Downloads zip, extracts, then checks for SKILL.md.\n */\nasync function installFromZip(\n zipUrl: string,\n source: SkillSource,\n agentFlag: AgentType,\n isGlobal: boolean,\n confirmOverride?: ConfirmSkillOverride\n): Promise<string[]> {\n const tempDir = path.join(os.tmpdir(), `sun-install-${Date.now()}`);\n\n try {\n const response = await fetch(zipUrl);\n if (!response.ok) {\n throw new Error(`Failed to download: ${response.statusText}`);\n }\n\n const buffer = Buffer.from(await response.arrayBuffer());\n const zip = new AdmZip(buffer);\n await fs.ensureDir(tempDir);\n zip.extractAllTo(tempDir, true);\n\n // Zip may have a root folder, find the actual content\n const entries = await fs.readdir(tempDir);\n const extractedDir = entries.length === 1 && (await fs.stat(path.join(tempDir, entries[0]))).isDirectory()\n ? path.join(tempDir, entries[0])\n : tempDir;\n\n const skillDirs = await findSkillDirectories(extractedDir);\n if (skillDirs.length === 0) {\n throw new Error(`No skills found in \"${source.originalInput}\". A skill must contain a SKILL.md file.`);\n }\n\n const installedSkills: string[] = [];\n for (const skillDir of skillDirs) {\n const skillName = await installSkillDirectory(skillDir, agentFlag, isGlobal, confirmOverride);\n if (skillName) {\n installedSkills.push(skillName);\n }\n }\n\n return installedSkills;\n } finally {\n await fs.remove(tempDir).catch(() => {});\n }\n}\n\n/**\n * Install skill(s) from GitHub using degit.\n * After downloading, checks if it's a skill or searches direct children for SKILL.md.\n */\nexport async function installFromGithub(\n source: SkillSource,\n agentFlag: AgentType,\n isGlobal: boolean,\n confirmOverride?: ConfirmSkillOverride\n): Promise<string[]> {\n // Create a temp directory to download to\n const tempDir = path.join(os.tmpdir(), `sun-install-${Date.now()}`);\n\n try {\n // Download using degit\n await fs.ensureDir(tempDir);\n try {\n execFileSync('npx', ['degit', source.location, tempDir], {\n stdio: 'pipe'\n });\n } catch (error) {\n const err = error as Error & { stderr?: Buffer };\n const stderr = err.stderr?.toString() || err.message;\n throw new Error(`Failed to download from GitHub: ${stderr}`);\n }\n\n // Find skills in downloaded content (checks itself and direct children)\n const skillDirs = await findSkillDirectories(tempDir);\n\n if (skillDirs.length === 0) {\n throw new Error(`No skills found in \"${source.originalInput}\". A skill must contain a SKILL.md file.`);\n }\n\n // Install each skill found (name comes from SKILL.md frontmatter)\n const installedSkills: string[] = [];\n for (const skillDir of skillDirs) {\n const skillName = await installSkillDirectory(skillDir, agentFlag, isGlobal, confirmOverride);\n if (skillName) {\n installedSkills.push(skillName);\n }\n }\n\n return installedSkills;\n } finally {\n // Clean up temp directory\n await fs.remove(tempDir).catch(() => {});\n }\n}\n\n/**\n * Install skill(s) from any source to an agent.\n * Returns list of installed skill names.\n */\nexport async function installSkill(\n skillInput: string,\n agentFlag: AgentType,\n isGlobal: boolean,\n confirmOverride?: ConfirmSkillOverride\n): Promise<{ skillNames: string[]; source: SkillSource }> {\n const source = await resolveSkillSource(skillInput);\n\n let skillNames: string[];\n\n switch (source.type) {\n case 'local':\n skillNames = await installFromLocal(source, agentFlag, isGlobal, confirmOverride);\n break;\n case 'shortcut': {\n const zipUrl = await getShortcutZipUrl(source.originalInput);\n if (zipUrl) {\n skillNames = await installFromZip(zipUrl, source, agentFlag, isGlobal, confirmOverride);\n } else {\n skillNames = await installFromGithub(source, agentFlag, isGlobal, confirmOverride);\n }\n break;\n }\n case 'github':\n skillNames = await installFromGithub(source, agentFlag, isGlobal, confirmOverride);\n break;\n default:\n throw new Error(`Unknown source type: ${(source as SkillSource).type}`);\n }\n\n if (source.type === 'shortcut') {\n await trackDownload(source.originalInput);\n }\n\n return { skillNames, source };\n}\n\n/**\n * Remove a skill from an agent.\n */\nexport async function removeSkill(\n skillName: string,\n agentFlag: AgentType,\n isGlobal: boolean\n): Promise<boolean> {\n const dest = getSkillInstallPath(skillName, agentFlag, isGlobal);\n\n if (await fs.pathExists(dest)) {\n await fs.remove(dest);\n return true;\n }\n\n return false;\n}\n","import fs from 'fs-extra';\nimport path from 'path';\nimport { isShortcut, getShortcutUrl } from '../utils/registry';\nimport type { SkillSource } from '../types/index';\n\n/**\n * Check if input looks like a GitHub URL or reference.\n * Matches: github.com/user/repo, https://github.com/..., etc.\n */\nexport function isGithubUrl(input: string): boolean {\n return input.includes('github.com');\n}\n\n/**\n * Normalize a GitHub URL to degit format.\n * Converts: https://github.com/user/repo/tree/branch/path -> user/repo/path#branch\n */\nfunction normalizeGithubUrl(url: string): string {\n let location = url.trim();\n\n // Remove git+ prefix (e.g. git+https://...)\n location = location.replace(/^git\\+/, '');\n\n // Ensure URL parsing works even if scheme is missing\n const urlString = /^[a-z]+:\\/\\//i.test(location) ? location : `https://${location}`;\n\n let pathname = '';\n try {\n const parsed = new URL(urlString);\n pathname = parsed.pathname;\n } catch {\n pathname = urlString.replace(/^https?:\\/\\//, '');\n }\n\n // Normalize path segments and strip github.com if present\n pathname = pathname.replace(/^\\/+/, '');\n const parts = pathname.split('/').filter(Boolean);\n if (parts[0] === 'github.com') {\n parts.shift();\n }\n\n if (parts.length < 2) {\n return pathname;\n }\n\n const user = parts[0];\n const repo = parts[1].replace(/\\.git$/, '');\n\n const kind = parts[2];\n if (kind === 'tree' || kind === 'blob' || kind === 'raw') {\n const branch = parts[3] || '';\n let subpath = parts.slice(4).join('/');\n\n // blob/raw URLs point to a file; drop the filename so we pull its directory\n if (kind !== 'tree' && subpath) {\n const subparts = subpath.split('/');\n subparts.pop();\n subpath = subparts.join('/');\n }\n\n if (branch) {\n return subpath ? `${user}/${repo}/${subpath}#${branch}` : `${user}/${repo}#${branch}`;\n }\n }\n\n const extraPath = parts.slice(2).join('/');\n return extraPath ? `${user}/${repo}/${extraPath}` : `${user}/${repo}`;\n}\n\n/**\n * Check if input looks like a local file path.\n * Matches: ./path, ../path, ~/path, /absolute/path\n */\nexport function isLocalPath(input: string): boolean {\n // Check if it starts with path indicators\n if (input.startsWith('./') ||\n input.startsWith('../') ||\n input.startsWith('~/') ||\n input.startsWith('/')) {\n return true;\n }\n\n // Check if it's an existing path on disk\n const resolved = path.resolve(input);\n return fs.pathExistsSync(resolved);\n}\n\n/**\n * Resolve a skill input to its source type and location.\n *\n * Resolution order:\n * 1. Check if it's a registered shortcut (e.g., \"tinker\")\n * 2. Check if it contains \"github.com\" (treat as GitHub URL)\n * 3. Check if it's a valid local path\n * 4. Otherwise, throw error\n */\nexport async function resolveSkillSource(input: string): Promise<SkillSource> {\n // 1. Check shortcuts first\n if (await isShortcut(input)) {\n const degitPath = await getShortcutUrl(input);\n if (!degitPath) {\n throw new Error(`Skill \"${input}\" found in registry but has no degit_path`);\n }\n return {\n type: 'shortcut',\n location: degitPath,\n originalInput: input\n };\n }\n\n // 2. Check if it's a GitHub URL\n if (isGithubUrl(input)) {\n return {\n type: 'github',\n location: normalizeGithubUrl(input),\n originalInput: input\n };\n }\n\n // 3. Check if it's a local path\n if (isLocalPath(input)) {\n // Resolve to absolute path, handling ~\n let location = input;\n if (location.startsWith('~/')) {\n location = path.join(process.env.HOME || '', location.slice(2));\n }\n location = path.resolve(location);\n\n return {\n type: 'local',\n location,\n originalInput: input\n };\n }\n\n // 4. Not found\n throw new Error(`Skill not found: \"${input}\". Expected a shortcut name, GitHub URL, or local path.`);\n}\n\n/**\n * Extract skill name from a source.\n * For GitHub: last path segment\n * For local: folder name\n * For shortcut: the shortcut name itself\n */\nexport function getSkillNameFromSource(source: SkillSource): string {\n if (source.type === 'shortcut') {\n return source.originalInput;\n }\n\n if (source.type === 'local') {\n return path.basename(source.location);\n }\n\n // GitHub: extract from path (e.g., \"user/repo/skills/tinker#main\" -> \"tinker\")\n const parts = source.location.split('/');\n const lastPart = parts[parts.length - 1];\n // Remove branch suffix if present (e.g., \"tinker#main\" -> \"tinker\")\n return lastPart.split('#')[0];\n}\n","const API_URL = 'https://vfbndmrgggrhnlrileqv.supabase.co/functions/v1/skills';\n\nexport interface Skill {\n name: string;\n display_name: string;\n description: string;\n category: string;\n author: string;\n github_url: string | null;\n degit_path: string;\n zip_path: string | null;\n download_count: number;\n}\n\nexport async function fetchSkills(): Promise<Skill[]> {\n const res = await fetch(`${API_URL}/list`);\n if (!res.ok) throw new Error(`Failed to fetch skills: ${res.statusText}`);\n return res.json() as Promise<Skill[]>;\n}\n\nexport async function fetchSkillByName(name: string): Promise<Skill | null> {\n const res = await fetch(`${API_URL}/get?name=${encodeURIComponent(name)}`);\n if (res.status === 404) return null;\n if (!res.ok) throw new Error(`Failed to fetch skill: ${res.statusText}`);\n return res.json() as Promise<Skill>;\n}\n\nexport async function trackDownload(skillName: string): Promise<void> {\n try {\n await fetch(`${API_URL}/track`, {\n method: 'POST',\n headers: { 'Content-Type': 'application/json' },\n body: JSON.stringify({ skill_name: skillName }),\n });\n } catch {\n // Silently fail - don't block installation if tracking fails\n }\n}\n","import { fetchSkills, type Skill } from '../lib/supabase.js';\n\nconst STORAGE_URL = 'https://vfbndmrgggrhnlrileqv.supabase.co/storage/v1/object/public/skill-zips';\n\n// Cache for skill lookups during a session\nlet skillsCache: Skill[] | null = null;\n\nexport async function getSkillsFromRegistry(): Promise<Skill[]> {\n if (!skillsCache) {\n skillsCache = await fetchSkills();\n }\n return skillsCache;\n}\n\nasync function getSkillByName(name: string): Promise<Skill | undefined> {\n const skills = await getSkillsFromRegistry();\n return skills.find(skill => skill.name === name);\n}\n\nexport async function isShortcut(skill: string): Promise<boolean> {\n return (await getSkillByName(skill)) !== undefined;\n}\n\nexport async function getShortcutUrl(skill: string): Promise<string | undefined> {\n return (await getSkillByName(skill))?.degit_path;\n}\n\nexport async function getShortcutZipUrl(skill: string): Promise<string | undefined> {\n const zipPath = (await getSkillByName(skill))?.zip_path;\n return zipPath ? `${STORAGE_URL}/${zipPath}` : undefined;\n}\n\nexport async function listShortcuts(): Promise<string[]> {\n const skills = await getSkillsFromRegistry();\n return skills.map(s => s.name);\n}\n","import fs from 'fs-extra';\nimport path from 'path';\nimport os from 'os';\nimport { SUPPORTED_AGENTS } from './agents';\nimport { computeContentHash } from './skill-hash';\nimport type { SkillMetadata, SkillInstallation, AgentType } from '../types/index';\n\n/**\n * Parse YAML-like frontmatter from SKILL.md content.\n * Frontmatter is delimited by --- at start and end.\n * Handles nested metadata field as key-value pairs.\n */\nfunction parseFrontmatter(content: string): SkillMetadata | null {\n const frontmatterMatch = content.match(/^---\\n([\\s\\S]*?)\\n---/);\n if (!frontmatterMatch) {\n return null;\n }\n\n const lines = frontmatterMatch[1].split('\\n');\n let name = '';\n let description = '';\n let license: string | undefined;\n let compatibility: string | undefined;\n let allowedTools: string | undefined;\n const metadata: Record<string, string> = {};\n\n let inMetadata = false;\n\n for (const line of lines) {\n // Check if we're entering metadata block (indented or explicit)\n if (line.match(/^metadata:\\s*$/)) {\n inMetadata = true;\n continue;\n }\n\n // If line starts with non-whitespace, we're out of metadata block\n if (inMetadata && line.match(/^\\S/)) {\n inMetadata = false;\n }\n\n const colonIndex = line.indexOf(':');\n if (colonIndex > 0) {\n const key = line.slice(0, colonIndex).trim();\n let value = line.slice(colonIndex + 1).trim();\n\n // Remove surrounding quotes if present\n if ((value.startsWith('\"') && value.endsWith('\"')) ||\n (value.startsWith(\"'\") && value.endsWith(\"'\"))) {\n value = value.slice(1, -1);\n }\n\n if (inMetadata) {\n // Nested under metadata\n metadata[key] = value;\n } else {\n // Top-level fields\n switch (key) {\n case 'name':\n name = value;\n break;\n case 'description':\n description = value;\n break;\n case 'license':\n license = value;\n break;\n case 'compatibility':\n compatibility = value;\n break;\n case 'allowed-tools':\n allowedTools = value;\n break;\n }\n }\n }\n }\n\n // name and description are required\n if (!name || !description) {\n return null;\n }\n\n return {\n name,\n description,\n license,\n compatibility,\n metadata: Object.keys(metadata).length > 0 ? metadata : undefined,\n allowedTools\n };\n}\n\n/**\n * Check if a directory is a valid skill.\n * A valid skill must contain a SKILL.md with required frontmatter (name, description).\n */\nexport async function isValidSkillDirectory(dirPath: string): Promise<boolean> {\n const skillMdPath = path.join(dirPath, 'SKILL.md');\n\n if (!await fs.pathExists(skillMdPath)) {\n return false;\n }\n\n try {\n const content = await fs.readFile(skillMdPath, 'utf-8');\n const metadata = parseFrontmatter(content);\n return metadata !== null;\n } catch {\n return false;\n }\n}\n\n/**\n * Find skill directories within a given path by searching recursively for SKILL.md files.\n * A skill is any directory containing a valid SKILL.md file (with name + description).\n */\nexport async function findSkillDirectories(searchPath: string): Promise<string[]> {\n const skills: string[] = [];\n\n // Recursively find all SKILL.md files\n async function searchRecursively(dir: string): Promise<void> {\n try {\n const entries = await fs.readdir(dir, { withFileTypes: true });\n\n for (const entry of entries) {\n const fullPath = path.join(dir, entry.name);\n\n if (entry.isFile() && entry.name === 'SKILL.md') {\n // Found a SKILL.md - check if it's valid\n if (await isValidSkillDirectory(dir)) {\n skills.push(dir);\n }\n } else if (entry.isDirectory() && !entry.name.startsWith('.git')) {\n // Skip .git directories but recurse into others\n await searchRecursively(fullPath);\n }\n }\n } catch {\n // Permission denied or other error, skip this directory\n }\n }\n\n await searchRecursively(searchPath);\n return skills;\n}\n\n/**\n * Read skill metadata from SKILL.md frontmatter.\n * The canonical skill name comes from the frontmatter, not the folder name.\n */\nexport async function readSkillMetadata(skillPath: string): Promise<SkillMetadata | null> {\n const skillMdPath = path.join(skillPath, 'SKILL.md');\n\n try {\n const content = await fs.readFile(skillMdPath, 'utf-8');\n return parseFrontmatter(content);\n } catch {\n return null;\n }\n}\n\n/**\n * Get the canonical skill name from SKILL.md frontmatter.\n * Returns null if not a valid skill.\n */\nexport async function getSkillName(skillPath: string): Promise<string | null> {\n const metadata = await readSkillMetadata(skillPath);\n return metadata?.name || null;\n}\n\n/**\n * Find all installations of a skill by name across all agents.\n */\nexport async function findSkillInstallations(skillName: string): Promise<SkillInstallation[]> {\n const installations: SkillInstallation[] = [];\n\n // Check both local and global for each agent\n const locations = [\n { base: process.cwd(), isGlobal: false },\n { base: os.homedir(), isGlobal: true }\n ];\n\n for (const { base, isGlobal } of locations) {\n for (const agent of SUPPORTED_AGENTS) {\n const skillPath = path.join(base, agent.folderName, 'skills', skillName);\n\n if (await fs.pathExists(skillPath)) {\n const metadata = await readSkillMetadata(skillPath);\n if (metadata) {\n const contentHash = await computeContentHash(skillPath);\n\n installations.push({\n agent: agent.flag as AgentType,\n path: skillPath,\n isGlobal,\n metadata,\n contentHash\n });\n }\n }\n }\n }\n\n return installations;\n}\n\n/**\n * List all installed skills for a specific agent.\n */\nexport async function listSkillsForAgent(\n agentFolderName: string,\n isGlobal: boolean\n): Promise<string[]> {\n const base = isGlobal ? os.homedir() : process.cwd();\n const skillsDir = path.join(base, agentFolderName, 'skills');\n\n if (!await fs.pathExists(skillsDir)) {\n return [];\n }\n\n const entries = await fs.readdir(skillsDir, { withFileTypes: true });\n const skills: string[] = [];\n\n for (const entry of entries) {\n if (entry.isDirectory()) {\n const skillPath = path.join(skillsDir, entry.name);\n const skillName = await getSkillName(skillPath);\n if (skillName) {\n skills.push(skillName);\n }\n }\n }\n\n return skills;\n}\n\n/**\n * Check if a skill exists in an agent's folder.\n */\nexport async function skillExists(\n skillName: string,\n agentFolderName: string,\n isGlobal: boolean\n): Promise<boolean> {\n const base = isGlobal ? os.homedir() : process.cwd();\n const skillPath = path.join(base, agentFolderName, 'skills', skillName);\n return (await fs.pathExists(skillPath)) && (await isValidSkillDirectory(skillPath));\n}\n","import crypto from 'crypto';\nimport fs from 'fs-extra';\nimport path from 'path';\n\n/**\n * Get all files in a directory recursively, sorted for consistency.\n */\nasync function getAllFiles(dir: string): Promise<string[]> {\n const files: string[] = [];\n\n async function walk(currentDir: string): Promise<void> {\n const entries = await fs.readdir(currentDir, { withFileTypes: true });\n\n for (const entry of entries) {\n const fullPath = path.join(currentDir, entry.name);\n if (entry.isDirectory()) {\n await walk(fullPath);\n } else if (entry.isFile()) {\n files.push(fullPath);\n }\n }\n }\n\n await walk(dir);\n // Sort for consistent ordering across platforms\n return files.sort();\n}\n\n/**\n * Compute a SHA-256 hash of all files in a skill folder.\n * This allows detecting if two skills with the same name have different content.\n *\n * The hash is computed by:\n * 1. Getting all files recursively\n * 2. Sorting them by path for consistency\n * 3. Hashing each file's relative path + content\n * 4. Combining into a final hash\n */\nexport async function computeContentHash(skillPath: string): Promise<string> {\n const files = await getAllFiles(skillPath);\n\n if (files.length === 0) {\n // Empty folder - return hash of empty string\n return crypto.createHash('sha256').update('').digest('hex').slice(0, 12);\n }\n\n const hash = crypto.createHash('sha256');\n\n for (const file of files) {\n // Include relative path in hash (so moving files changes the hash)\n const relativePath = path.relative(skillPath, file);\n hash.update(relativePath);\n\n // Include file content\n const content = await fs.readFile(file);\n hash.update(content);\n }\n\n // Return first 12 chars for readability\n return hash.digest('hex').slice(0, 12);\n}\n","import chalk from 'chalk';\nimport { confirm } from '@inquirer/prompts';\nimport { SUPPORTED_AGENTS, getAgentByFlag } from '../core/agents';\nimport { checkboxExtended } from './checkbox-extended';\nimport type { AgentType } from '../types/index';\n\n/**\n * Show an interactive checkbox UI for selecting default agents.\n *\n * @param currentDefaults - Previously saved defaults (empty on first run)\n * @returns Array of selected agent flags (e.g., ['claude', 'codex'])\n *\n * Behavior:\n * - Shows all supported agent TYPES from SUPPORTED_AGENTS\n * - First run (currentDefaults empty): ALL agents are pre-selected\n * - Subsequent runs: Only previously saved defaults are pre-selected\n * - Must select at least one agent\n */\nexport async function promptAgentSelection(\n currentDefaults: AgentType[] = []\n): Promise<AgentType[]> {\n const isFirstRun = currentDefaults.length === 0;\n\n // Build choices from SUPPORTED_AGENTS constants\n // Show paths so users understand what each agent refers to\n const choices = SUPPORTED_AGENTS.map(agent => ({\n name: `${agent.name} (~/${agent.folderName}/ and ./${agent.folderName}/)`,\n value: agent.flag as AgentType,\n // First run: select ALL agents\n // Otherwise: only select if it was in previous defaults\n checked: isFirstRun ? true : currentDefaults.includes(agent.flag as AgentType)\n }));\n\n const selectedAgents = await checkboxExtended({\n message: 'Select default agents:',\n choices,\n required: true,\n theme: {\n icon: {\n // Make the selection marker stand out a bit more.\n checked: chalk.green('◉'),\n unchecked: chalk.white('◎'),\n cursor: chalk.white('❯')\n },\n style: {\n // Keep active line readable (esp. on dark terminals) and avoid “cyan highlight”.\n highlight: (text: string) => chalk.bold.white(text)\n }\n }\n });\n\n return selectedAgents;\n}\n\nexport async function promptSkillOverride(params: {\n skillName: string;\n agentFlag: AgentType;\n isGlobal: boolean;\n destPath: string;\n}): Promise<boolean> {\n const agent = getAgentByFlag(params.agentFlag);\n const agentLabel = agent ? agent.name : params.agentFlag;\n const locationLabel = params.isGlobal ? 'global' : 'local';\n\n return confirm({\n message: `Skill \"${params.skillName}\" already exists in ${agentLabel} (${locationLabel}) at ${params.destPath}. Override?`,\n default: false\n });\n}\n","import {\n Separator,\n ValidationError,\n createPrompt,\n isDownKey,\n isEnterKey,\n isNumberKey,\n isSpaceKey,\n isTabKey,\n isUpKey,\n makeTheme,\n useKeypress,\n useMemo,\n usePagination,\n usePrefix,\n useState\n} from '@inquirer/core';\nimport { cursorHide } from '@inquirer/ansi';\nimport figures from '@inquirer/figures';\nimport { styleText } from 'node:util';\nimport type { PartialDeep } from '@inquirer/type';\nimport type { Theme, Keybinding } from '@inquirer/core';\n\ntype CheckboxTheme = {\n icon: {\n checked: string;\n unchecked: string;\n cursor: string;\n };\n style: {\n disabledChoice: (text: string) => string;\n renderSelectedChoices: <T>(\n selectedChoices: ReadonlyArray<NormalizedChoice<T>>,\n allChoices: ReadonlyArray<NormalizedChoice<T> | Separator>\n ) => string;\n description: (text: string) => string;\n keysHelpTip: (keys: [key: string, action: string][]) => string | undefined;\n };\n keybindings: ReadonlyArray<Keybinding>;\n};\n\ntype CheckboxShortcuts = {\n all?: string | null;\n invert?: string | null;\n};\n\ntype Choice<Value> = {\n value: Value;\n name?: string;\n checkedName?: string;\n description?: string;\n short?: string;\n disabled?: boolean | string;\n checked?: boolean;\n type?: never;\n};\n\ntype NormalizedChoice<Value> = {\n value: Value;\n name: string;\n checkedName: string;\n description?: string;\n short: string;\n disabled: boolean | string;\n checked: boolean;\n};\n\nfunction isSelectable<Value>(item: NormalizedChoice<Value> | Separator): item is NormalizedChoice<Value> {\n return !Separator.isSeparator(item) && !item.disabled;\n}\n\nfunction isChecked<Value>(item: NormalizedChoice<Value> | Separator): item is NormalizedChoice<Value> {\n return isSelectable(item) && item.checked;\n}\n\nfunction toggle<Value>(item: NormalizedChoice<Value> | Separator): NormalizedChoice<Value> | Separator {\n return isSelectable(item) ? { ...item, checked: !item.checked } : item;\n}\n\nfunction check<Value>(checked: boolean) {\n return function (item: NormalizedChoice<Value> | Separator): NormalizedChoice<Value> | Separator {\n return isSelectable(item) ? { ...item, checked } : item;\n };\n}\n\nfunction normalizeChoices<Value>(\n choices: readonly (string | Separator)[] | readonly (Separator | Choice<Value>)[]\n): Array<NormalizedChoice<Value> | Separator> {\n return choices.map(choice => {\n if (Separator.isSeparator(choice)) return choice;\n\n if (typeof choice === 'string') {\n return {\n value: choice as Value,\n name: choice,\n short: choice,\n checkedName: choice,\n disabled: false,\n checked: false\n };\n }\n\n const name = choice.name ?? String(choice.value);\n const normalizedChoice: NormalizedChoice<Value> = {\n value: choice.value,\n name,\n short: choice.short ?? name,\n checkedName: choice.checkedName ?? name,\n disabled: choice.disabled ?? false,\n checked: choice.checked ?? false\n };\n\n if (choice.description) normalizedChoice.description = choice.description;\n return normalizedChoice;\n });\n}\n\nfunction nextSelectableIndex<Value>(\n items: Array<NormalizedChoice<Value> | Separator>,\n from: number,\n direction: -1 | 1\n): number {\n let next = from;\n do {\n next = (next + direction + items.length) % items.length;\n } while (!isSelectable(items[next]));\n return next;\n}\n\nconst checkboxTheme: Theme<CheckboxTheme> = {\n icon: {\n // Slightly larger/more visible rings by default vs the upstream checkbox prompt.\n checked: styleText('green', figures.circleFilled),\n unchecked: figures.circleDouble,\n cursor: figures.pointer\n },\n style: {\n disabledChoice: text => styleText('dim', `- ${text}`),\n renderSelectedChoices: selectedChoices => selectedChoices.map(choice => choice.short).join(', '),\n description: text => styleText('cyan', text),\n keysHelpTip: keys =>\n keys\n .map(([key, action]) => `${styleText('bold', key)} ${styleText('dim', action)}`)\n .join(styleText('dim', ' • '))\n },\n keybindings: []\n};\n\n/**\n * Checkbox prompt with additional toggle keys:\n * - Space toggles current item\n * - Tab toggles current item\n * - Left/Right arrows toggle current item\n */\nexport const checkboxExtended = createPrompt(<Value>(\n config: {\n message: string;\n prefix?: string;\n pageSize?: number;\n choices: readonly (string | Separator)[] | readonly (Separator | Choice<Value>)[];\n loop?: boolean;\n required?: boolean;\n validate?: (choices: readonly NormalizedChoice<Value>[]) => boolean | string | Promise<string | boolean>;\n theme?: PartialDeep<Theme<CheckboxTheme>>;\n shortcuts?: CheckboxShortcuts;\n },\n done: (value: Value[]) => void\n) => {\n const { pageSize = 7, loop = true, required, validate = () => true } = config;\n const shortcuts = { all: 'a', invert: 'i', ...config.shortcuts };\n\n const theme = makeTheme(checkboxTheme, config.theme);\n const { keybindings } = theme;\n\n const [status, setStatus] = useState<'idle' | 'done'>('idle');\n const prefix = usePrefix({ status, theme });\n const [items, setItems] = useState<Array<NormalizedChoice<Value> | Separator>>(normalizeChoices(config.choices));\n\n const bounds = useMemo(() => {\n const first = items.findIndex(isSelectable);\n const last = items.findLastIndex(isSelectable);\n if (first === -1) {\n throw new ValidationError('[checkbox prompt] No selectable choices. All choices are disabled.');\n }\n return { first, last };\n }, [items]);\n\n const [active, setActive] = useState(bounds.first);\n const [errorMsg, setError] = useState<string | undefined>();\n\n useKeypress(async key => {\n if (isEnterKey(key)) {\n const selection = items.filter(isChecked);\n const isValid = await validate([...selection]);\n if (required && !items.some(isChecked)) {\n setError('At least one choice must be selected');\n } else if (isValid === true) {\n setStatus('done');\n done(selection.map(choice => choice.value));\n } else {\n setError(isValid || 'You must select a valid value');\n }\n return;\n }\n\n if (isUpKey(key, keybindings) || isDownKey(key, keybindings)) {\n if (\n loop ||\n (isUpKey(key, keybindings) && active !== bounds.first) ||\n (isDownKey(key, keybindings) && active !== bounds.last)\n ) {\n const direction: -1 | 1 = isUpKey(key, keybindings) ? -1 : 1;\n setActive(nextSelectableIndex(items, active, direction));\n }\n return;\n }\n\n const isLeftRight = key.name === 'left' || key.name === 'right';\n if (isSpaceKey(key) || isLeftRight) {\n setError(undefined);\n setItems(items.map((choice, i) => (i === active ? toggle(choice) : choice)));\n return;\n }\n\n if (isTabKey(key)) {\n setError(undefined);\n setItems(items.map((choice, i) => (i === active ? toggle(choice) : choice)));\n return;\n }\n\n if (key.name === shortcuts.all) {\n const selectAll = items.some(choice => isSelectable(choice) && !choice.checked);\n setItems(items.map(check(selectAll)));\n return;\n }\n\n if (key.name === shortcuts.invert) {\n setItems(items.map(toggle));\n return;\n }\n\n if (isNumberKey(key)) {\n const selectedIndex = Number(key.name) - 1;\n // Find the nth item (ignoring separators)\n let selectableIndex = -1;\n const position = items.findIndex(item => {\n if (Separator.isSeparator(item)) return false;\n selectableIndex++;\n return selectableIndex === selectedIndex;\n });\n\n const selectedItem = items[position];\n if (selectedItem && isSelectable(selectedItem)) {\n setActive(position);\n setItems(items.map((choice, i) => (i === position ? toggle(choice) : choice)));\n }\n }\n });\n\n const message = theme.style.message(config.message, status);\n let description: string | undefined;\n\n const page = usePagination({\n items,\n active,\n renderItem({ item, isActive }) {\n if (Separator.isSeparator(item)) return ` ${item.separator}`;\n\n if (item.disabled) {\n const disabledLabel = typeof item.disabled === 'string' ? item.disabled : '(disabled)';\n return theme.style.disabledChoice(`${item.name} ${disabledLabel}`);\n }\n\n if (isActive) description = item.description;\n\n const checkbox = item.checked ? theme.icon.checked : theme.icon.unchecked;\n const name = item.checked ? item.checkedName : item.name;\n const color = isActive ? theme.style.highlight : (x: string) => x;\n const cursor = isActive ? theme.icon.cursor : ' ';\n return color(`${cursor}${checkbox} ${name}`);\n },\n pageSize,\n loop\n });\n\n if (status === 'done') {\n const selection = items.filter(isChecked);\n const answer = theme.style.answer(theme.style.renderSelectedChoices(selection, items as any));\n return [prefix, message, answer].filter(Boolean).join(' ');\n }\n\n const keys: Array<[string, string]> = [\n ['↑↓', 'navigate'],\n ['space/tab/←→', 'toggle'],\n ];\n if (shortcuts.all) keys.push([shortcuts.all, 'all']);\n if (shortcuts.invert) keys.push([shortcuts.invert, 'invert']);\n keys.push(['⏎', 'submit']);\n\n const helpLine = theme.style.keysHelpTip(keys);\n\n const lines = [\n [prefix, message].filter(Boolean).join(' '),\n page,\n ' ',\n description ? theme.style.description(description) : '',\n errorMsg ? theme.style.error(errorMsg) : '',\n helpLine\n ]\n .filter(Boolean)\n .join('\\n')\n .trimEnd();\n\n return `${lines}${cursorHide}`;\n});\n\n","import fs from 'fs-extra';\nimport path from 'path';\n\nconst DEFAULT_IGNORES = new Set(['.git', '.DS_Store']);\n\nfunction sortEntries(entries: fs.Dirent[]): fs.Dirent[] {\n return entries.slice().sort((a, b) => {\n const aIsDir = a.isDirectory();\n const bIsDir = b.isDirectory();\n if (aIsDir !== bIsDir) {\n return aIsDir ? -1 : 1;\n }\n return a.name.localeCompare(b.name);\n });\n}\n\nasync function walkTree(\n dir: string,\n prefix: string,\n depth: number,\n maxDepth?: number\n): Promise<string[]> {\n if (maxDepth !== undefined && depth > maxDepth) {\n return [];\n }\n\n let entries: fs.Dirent[];\n try {\n entries = await fs.readdir(dir, { withFileTypes: true });\n } catch {\n return [];\n }\n\n const visibleEntries = sortEntries(entries).filter(entry => !DEFAULT_IGNORES.has(entry.name));\n const lines: string[] = [];\n\n for (let i = 0; i < visibleEntries.length; i++) {\n const entry = visibleEntries[i];\n const isLast = i === visibleEntries.length - 1;\n const connector = isLast ? '\\\\-- ' : '|-- ';\n const line = `${prefix}${connector}${entry.name}`;\n lines.push(line);\n\n if (entry.isDirectory()) {\n const nextPrefix = `${prefix}${isLast ? ' ' : '| '}`;\n const childLines = await walkTree(path.join(dir, entry.name), nextPrefix, depth + 1, maxDepth);\n lines.push(...childLines);\n }\n }\n\n return lines;\n}\n\nexport async function formatDirectoryTree(rootPath: string, maxDepth?: number): Promise<string> {\n const rootName = path.basename(rootPath);\n const lines = [rootName];\n const childLines = await walkTree(rootPath, '', 1, maxDepth);\n lines.push(...childLines);\n return lines.join('\\n');\n}\n\nexport function indentLines(text: string, indent: string): string {\n return text\n .split('\\n')\n .map(line => `${indent}${line}`)\n .join('\\n');\n}\n","import chalk from 'chalk';\nimport ora from 'ora';\nimport { getAgentByFlag, SUPPORTED_AGENTS } from '../core/agents';\nimport { getDefaultAgents } from '../core/config-manager';\nimport { detectLocalAgents } from '../core/agent-detect';\nimport { removeSkill } from '../core/skill-install';\nimport type { AgentType, CommandFlags } from '../types/index';\n\n/**\n * Determine which agents to remove from and whether to target global installs.\n * Uses same logic as add command (except no first-run prompt).\n *\n * Logic:\n * 1. If --global flag is set, always target global\n * 2. If agent flags (--claude, --codex, etc.) are set, use those agents\n * 3. Otherwise use saved default agents (error if none configured)\n *\n * For local vs global:\n * - If --global: always global\n * - Otherwise: check if any configured agents have local folders\n * - If yes: target local\n * - If no local folders exist for configured agents: target global\n */\nasync function resolveTargetAgents(flags: CommandFlags): Promise<{ agents: AgentType[]; isGlobal: boolean }> {\n const forceGlobal = flags.global ?? false;\n\n // Check if any agent flags were explicitly set\n const explicitAgents: AgentType[] = [];\n for (const agent of SUPPORTED_AGENTS) {\n if (flags[agent.flag as keyof CommandFlags]) {\n explicitAgents.push(agent.flag as AgentType);\n }\n }\n\n let targetAgents: AgentType[];\n\n // Determine which agents to target\n if (explicitAgents.length > 0) {\n targetAgents = explicitAgents;\n } else {\n // Use saved defaults (no first-run prompt for remove)\n const defaultAgents = await getDefaultAgents();\n if (defaultAgents.length === 0) {\n throw new Error('No default agents configured. Run \"sun add\" first or use --claude/--codex/--gemini flags.');\n }\n targetAgents = defaultAgents;\n }\n\n // Determine if we should target global or local\n if (forceGlobal) {\n return { agents: targetAgents, isGlobal: true };\n }\n\n // Check if any of the target agents have local folders in current directory\n const localAgents = await detectLocalAgents();\n const localAgentFlags = new Set(localAgents.map(a => a.agent.flag));\n\n const hasLocalFolders = targetAgents.some(agentFlag => localAgentFlags.has(agentFlag));\n\n // If no local folders exist for any configured agent, target global\n const isGlobal = !hasLocalFolders;\n\n return { agents: targetAgents, isGlobal };\n}\n\nexport interface RemoveResult {\n skill: string;\n removedFrom: string[];\n notFoundIn: string[];\n isGlobal: boolean;\n error?: string;\n}\n\n/**\n * Remove skill(s) from agent configuration(s).\n */\nexport async function removeCommand(skills: string[], flags: CommandFlags): Promise<void> {\n // Resolve target agents\n let agents: AgentType[];\n let isGlobal: boolean;\n\n try {\n const resolved = await resolveTargetAgents(flags);\n agents = resolved.agents;\n isGlobal = resolved.isGlobal;\n } catch (error) {\n console.error(chalk.red(error instanceof Error ? error.message : String(error)));\n process.exit(1);\n }\n\n const results: RemoveResult[] = [];\n\n for (const skill of skills) {\n const spinner = ora(`Removing ${skill}...`).start();\n\n const result: RemoveResult = {\n skill,\n removedFrom: [],\n notFoundIn: [],\n isGlobal\n };\n\n try {\n // Remove from each target agent\n for (const agentFlag of agents) {\n const removed = await removeSkill(skill, agentFlag, isGlobal);\n const agentName = getAgentByFlag(agentFlag)!.name;\n\n if (removed) {\n result.removedFrom.push(agentName);\n } else {\n result.notFoundIn.push(agentName);\n }\n }\n\n if (result.removedFrom.length > 0) {\n spinner.succeed(`Removed ${skill} from ${result.removedFrom.join(' and ')}`);\n } else {\n const pathPrefix = isGlobal ? '~/' : './';\n const checkedPaths = agents.map(a => `${pathPrefix}${getAgentByFlag(a)!.folderName}/`);\n spinner.warn(`${skill} not found in configured agents (${checkedPaths.join(', ')})`);\n }\n\n if (result.notFoundIn.length > 0 && result.removedFrom.length > 0) {\n console.log(chalk.gray(` (not found in: ${result.notFoundIn.join(', ')})`));\n }\n } catch (error) {\n const message = error instanceof Error ? error.message : String(error);\n result.error = message;\n spinner.fail(`Failed to remove ${skill}: ${message}`);\n }\n\n results.push(result);\n }\n\n // Print summary if multiple skills\n if (skills.length > 1) {\n const totalRemoved = results.filter(r => r.removedFrom.length > 0).length;\n const totalFailed = results.filter(r => r.error || r.removedFrom.length === 0).length;\n\n console.log();\n if (totalRemoved > 0) {\n console.log(chalk.green(`Removed ${totalRemoved} skill(s)`));\n }\n if (totalFailed > 0) {\n console.log(chalk.yellow(`${totalFailed} skill(s) not found or failed`));\n }\n }\n\n}\n","import chalk from 'chalk';\nimport { SUPPORTED_AGENTS, getSupportedAgentsMessage } from '../core/agents';\nimport { listSkillsForAgent } from '../core/skill-info';\n\ninterface AgentSkills {\n agentName: string;\n folderName: string;\n isGlobal: boolean;\n skills: string[];\n}\n\n/**\n * List all installed skills for each agent.\n */\nexport async function listCommand(): Promise<void> {\n const allAgentSkills: AgentSkills[] = [];\n\n // Check both local and global for each agent\n for (const agent of SUPPORTED_AGENTS) {\n // Local\n const localSkills = await listSkillsForAgent(agent.folderName, false);\n if (localSkills.length > 0) {\n allAgentSkills.push({\n agentName: agent.name,\n folderName: agent.folderName,\n isGlobal: false,\n skills: localSkills\n });\n }\n\n // Global\n const globalSkills = await listSkillsForAgent(agent.folderName, true);\n if (globalSkills.length > 0) {\n allAgentSkills.push({\n agentName: agent.name,\n folderName: agent.folderName,\n isGlobal: true,\n skills: globalSkills\n });\n }\n }\n\n if (allAgentSkills.length === 0) {\n console.log(chalk.yellow('No skills installed.'));\n console.log();\n console.log(chalk.gray(getSupportedAgentsMessage()));\n console.log(chalk.gray('Browse curated skills with \"sun list\"'));\n console.log(chalk.gray('You can add from the library, GitHub URLs, or local paths with \"sun add <skill>\"'));\n return;\n }\n\n // Print skills grouped by agent\n for (const agentSkills of allAgentSkills) {\n const location = agentSkills.isGlobal\n ? `global ~/${agentSkills.folderName}/`\n : `${agentSkills.folderName}/`;\n\n console.log(chalk.cyan(`${agentSkills.agentName} (${location}):`));\n\n for (const skill of agentSkills.skills) {\n console.log(` - ${skill}`);\n }\n\n console.log();\n }\n\n console.log(chalk.gray(getSupportedAgentsMessage()));\n console.log(chalk.gray('Browse curated skills with \"sun list\"'));\n console.log(chalk.gray('Add from the library, GitHub URLs, or local paths with \"sun add <skill>\"'));\n console.log(chalk.gray('Remove with \"sun remove <skill>\"'));\n}\n","import chalk from 'chalk';\nimport { getSkillsFromRegistry } from '../utils/registry';\n\n/**\n * List all available skills from the registry.\n */\nexport async function listRegistryCommand(): Promise<void> {\n const skills = await getSkillsFromRegistry();\n\n if (skills.length === 0) {\n console.log(chalk.yellow('No skills available in the Sundial library.'));\n console.log(chalk.gray('You can still add from GitHub URLs or local paths.'));\n console.log(chalk.gray('Example: sun add github.com/user/skill or sun add ./my-skill'));\n return;\n }\n\n const sorted = [...skills].sort((a, b) => a.name.localeCompare(b.name));\n\n console.log(chalk.cyan(`Available skills from the Sundial library (${sorted.length}):`));\n for (const skill of sorted) {\n const description = skill.description?.trim();\n const author = skill.author?.trim();\n const descriptionText = description ? ` - ${description}` : '';\n const authorText = author ? ` (by ${author})` : '';\n console.log(` - ${skill.name}${chalk.gray(descriptionText + authorText)}`);\n }\n\n console.log();\n console.log(chalk.white('Install from the library with \"sun add <skill>\".'));\n console.log(chalk.white('You can also add from GitHub URLs or local paths.'));\n}\n","import chalk from 'chalk';\nimport path from 'path';\nimport { findSkillInstallations, readSkillMetadata } from '../core/skill-info';\nimport { getAgentByFlag } from '../core/agents';\nimport { detectAllAgents, detectLocalAgents } from '../core/agent-detect';\nimport { getDefaultAgents } from '../core/config-manager';\nimport { showAllAgentFolders, showAllAgentSkillsFolders, showAllSkillFolders } from './show-dev';\nimport { formatDirectoryTree, indentLines } from '../utils/tree';\nimport fs from 'fs-extra';\n\n/**\n * List all skills in a given skills directory path.\n */\nasync function listSkillsInPath(skillsDir: string): Promise<Array<{ name: string; description: string }>> {\n const skills: Array<{ name: string; description: string }> = [];\n\n if (!await fs.pathExists(skillsDir)) {\n return skills;\n }\n\n const entries = await fs.readdir(skillsDir, { withFileTypes: true });\n\n for (const entry of entries) {\n if (entry.isDirectory()) {\n const skillPath = path.join(skillsDir, entry.name);\n const metadata = await readSkillMetadata(skillPath);\n if (metadata) {\n skills.push({\n name: metadata.name,\n description: metadata.description\n });\n }\n }\n }\n\n return skills;\n}\n\n/**\n * Show all agent folders and their installed skills.\n */\nasync function showAllAgents(): Promise<void> {\n const allAgents = await detectAllAgents();\n const defaultAgents = await getDefaultAgents();\n const defaultSet = new Set(defaultAgents);\n const localAgents = await detectLocalAgents();\n const localAgentFlags = new Set(localAgents.map(a => a.agent.flag));\n\n if (allAgents.length === 0) {\n console.log(chalk.yellow('No agent folders found.'));\n console.log(chalk.gray('Agent folders are directories like .claude/, .codex/, .gemini/'));\n return;\n }\n\n console.log(chalk.cyan('Agent Folders & Installed Skills'));\n console.log(chalk.gray('─'.repeat(40)));\n console.log();\n\n for (const detected of allAgents) {\n const { agent, path: agentPath, isGlobal } = detected;\n const locationLabel = isGlobal ? chalk.gray('(global)') : chalk.gray('(local)');\n const isDefault = defaultSet.has(agent.flag as any);\n const hasLocalFolder = localAgentFlags.has(agent.flag);\n\n // Show checkmark if this folder would be affected by sun add/remove:\n // - Local folder: affected if agent is selected\n // - Global folder: affected if agent is selected AND no local folder exists\n const wouldBeAffected = isDefault && (isGlobal ? !hasLocalFolder : true);\n const marker = wouldBeAffected ? chalk.green('✓') : chalk.gray('○');\n\n console.log(`${marker} ${chalk.white.bold(agent.name)} ${locationLabel}`);\n console.log(chalk.gray(` ${agentPath}`));\n\n // List skills in this agent folder\n const skillsDir = path.join(agentPath, 'skills');\n const skills = await listSkillsInPath(skillsDir);\n\n if (skills.length === 0) {\n console.log(chalk.gray(' No skills installed'));\n } else {\n console.log(` Skills (${skills.length}):`);\n for (const skill of skills) {\n console.log(` - ${skill.name} ${chalk.gray(`- ${skill.description}`)}`);\n }\n }\n console.log();\n }\n\n console.log(`${chalk.green('✓')} = affected by sun add/remove in this directory`);\n console.log('Run \"sun config\" to change selected agents.');\n}\n\n/**\n * Show skill details and installation locations.\n * If no skill specified, shows all agent folders and their packages.\n *\n * Secret commands (not in README, documented in DEV.md):\n * - all-agent-folders: Find all agent folders on the system\n * - all-agent-skills-folders: Find all <agent>/skills folders\n * - all-skill-folders: Find all folders with valid SKILL.md\n */\nexport async function showCommand(skillName?: string): Promise<void> {\n // Handle secret dev commands\n if (skillName === 'all-agent-folders') {\n await showAllAgentFolders();\n return;\n }\n\n if (skillName === 'all-agent-skills-folders') {\n await showAllAgentSkillsFolders();\n return;\n }\n\n if (skillName === 'all-skill-folders') {\n await showAllSkillFolders();\n return;\n }\n\n // If no skill specified, show all agents and their packages\n if (!skillName) {\n await showAllAgents();\n return;\n }\n\n const installations = await findSkillInstallations(skillName);\n\n if (installations.length === 0) {\n console.error(chalk.yellow(`Skill \"${skillName}\" is not installed.`));\n process.exit(1);\n }\n\n // Check if there are multiple versions (different content hashes)\n const uniqueHashes = new Set(installations.map(i => i.contentHash));\n const hasMultipleVersions = uniqueHashes.size > 1;\n\n if (hasMultipleVersions) {\n // Multiple versions detected\n console.log(chalk.cyan(`Skill: ${skillName}`));\n console.log(chalk.yellow('Warning: Multiple versions detected'));\n console.log();\n\n // Group by content hash\n const byHash = new Map<string, typeof installations>();\n for (const inst of installations) {\n const existing = byHash.get(inst.contentHash) || [];\n existing.push(inst);\n byHash.set(inst.contentHash, existing);\n }\n\n let versionNum = 1;\n for (const [hash, insts] of byHash) {\n const firstInst = insts[0];\n const locations = insts.map(i => {\n const agent = getAgentByFlag(i.agent)!;\n return i.isGlobal ? `~/${agent.folderName}/` : `${agent.folderName}/`;\n });\n\n console.log(chalk.white(`Version ${versionNum} (${locations.join(', ')}):`));\n console.log(` Description: ${firstInst.metadata.description}`);\n\n if (firstInst.metadata.metadata?.author) {\n console.log(` Author: ${firstInst.metadata.metadata.author}`);\n }\n if (firstInst.metadata.metadata?.version) {\n console.log(` Version: ${firstInst.metadata.metadata.version}`);\n }\n if (firstInst.metadata.license) {\n console.log(` License: ${firstInst.metadata.license}`);\n }\n\n console.log(` Content hash: ${hash}`);\n const tree = await formatDirectoryTree(firstInst.path);\n console.log(' Tree:');\n console.log(indentLines(tree, ' '));\n console.log();\n\n versionNum++;\n }\n } else {\n // Single version across all installations\n const firstInst = installations[0];\n\n console.log(chalk.cyan(`Skill: ${skillName}`));\n console.log(`Description: ${firstInst.metadata.description}`);\n\n if (firstInst.metadata.metadata?.author) {\n console.log(`Author: ${firstInst.metadata.metadata.author}`);\n }\n if (firstInst.metadata.metadata?.version) {\n console.log(`Version: ${firstInst.metadata.metadata.version}`);\n }\n if (firstInst.metadata.license) {\n console.log(`License: ${firstInst.metadata.license}`);\n }\n if (firstInst.metadata.compatibility) {\n console.log(`Compatibility: ${firstInst.metadata.compatibility}`);\n }\n\n console.log();\n console.log('Installed in:');\n for (const inst of installations) {\n const agent = getAgentByFlag(inst.agent)!;\n const base = inst.isGlobal ? `~/${agent.folderName}/` : `${agent.folderName}/`;\n const location = inst.isGlobal ? '(global)' : '(local)';\n console.log(` - ${base}skills/${skillName} ${chalk.gray(location)}`);\n }\n\n const tree = await formatDirectoryTree(firstInst.path);\n console.log();\n console.log('Skill folder:');\n console.log(indentLines(tree, ' '));\n }\n}\n","/**\n * Dev-only show commands for debugging and exploration.\n * These search the entire file system starting from home directory.\n */\n\nimport chalk from 'chalk';\nimport path from 'path';\nimport os from 'os';\nimport fs from 'fs-extra';\nimport { exec } from 'child_process';\nimport { promisify } from 'util';\nimport { SUPPORTED_AGENTS } from '../core/agents';\nimport { readSkillMetadata } from '../core/skill-info';\n\nconst execAsync = promisify(exec);\n\n// Timeout for find commands (60 seconds)\nconst FIND_TIMEOUT = 60000;\n\n/**\n * List skills in a directory, returning name and description.\n */\nasync function listSkillsInDir(skillsDir: string): Promise<Array<{ name: string; description: string }>> {\n const skills: Array<{ name: string; description: string }> = [];\n\n if (!await fs.pathExists(skillsDir)) {\n return skills;\n }\n\n const entries = await fs.readdir(skillsDir, { withFileTypes: true });\n\n for (const entry of entries) {\n if (entry.isDirectory()) {\n const skillPath = path.join(skillsDir, entry.name);\n const metadata = await readSkillMetadata(skillPath);\n if (metadata) {\n skills.push({\n name: metadata.name,\n description: metadata.description\n });\n }\n }\n }\n\n return skills;\n}\n\n/**\n * sun show all-agent-folders\n * Find ALL agent folders (.claude, .codex, .gemini) starting from ~ and show skills in each.\n */\nexport async function showAllAgentFolders(): Promise<void> {\n const homeDir = os.homedir();\n\n // Build find command: find ~ -type d \\( -name \".claude\" -o -name \".codex\" -o -name \".gemini\" \\)\n const namePatterns = SUPPORTED_AGENTS.map(a => `-name \"${a.folderName}\"`).join(' -o ');\n const findCmd = `find \"${homeDir}\" -type d \\\\( ${namePatterns} \\\\)`;\n\n console.log(chalk.cyan('All Agent Folders'));\n console.log(chalk.gray('─'.repeat(40)));\n console.log();\n\n let stdout = '';\n try {\n const result = await execAsync(findCmd, { maxBuffer: 10 * 1024 * 1024, timeout: FIND_TIMEOUT });\n stdout = result.stdout;\n } catch (err: any) {\n // find exits non-zero on permission errors but still produces output\n if (err.stdout) {\n stdout = err.stdout;\n } else {\n console.log(chalk.red('Failed to search for agent folders.'));\n console.log(chalk.gray(String(err)));\n return;\n }\n }\n\n const agentPaths = stdout.trim().split('\\n').filter(Boolean);\n\n if (agentPaths.length === 0) {\n console.log(chalk.yellow('No agent folders found.'));\n return;\n }\n\n for (const agentPath of agentPaths) {\n const folderName = path.basename(agentPath);\n const agent = SUPPORTED_AGENTS.find(a => a.folderName === folderName);\n if (!agent) continue;\n\n console.log(chalk.white.bold(agent.name));\n console.log(chalk.gray(` ${agentPath}`));\n\n // List skills\n const skillsDir = path.join(agentPath, 'skills');\n const skills = await listSkillsInDir(skillsDir);\n\n if (skills.length === 0) {\n console.log(chalk.gray(' No skills installed'));\n } else {\n console.log(` Skills (${skills.length}):`);\n for (const skill of skills) {\n console.log(` - ${skill.name} ${chalk.gray(`- ${skill.description}`)}`);\n }\n }\n console.log();\n }\n}\n\n/**\n * sun show all-agent-skills-folders\n * Find ALL <agent>/skills folders starting from ~ and show skills in each.\n */\nexport async function showAllAgentSkillsFolders(): Promise<void> {\n const homeDir = os.homedir();\n\n // Build find command for skills directories inside agent folders\n // e.g., find ~ -type d \\( -path \"*/.claude/skills\" -o -path \"*/.codex/skills\" -o -path \"*/.gemini/skills\" \\)\n const pathPatterns = SUPPORTED_AGENTS.map(a => `-path \"*/${a.folderName}/skills\"`).join(' -o ');\n const findCmd = `find \"${homeDir}\" -type d \\\\( ${pathPatterns} \\\\)`;\n\n console.log(chalk.cyan('All Agent Skills Folders'));\n console.log(chalk.gray('─'.repeat(40)));\n console.log();\n\n let stdout = '';\n try {\n const result = await execAsync(findCmd, { maxBuffer: 10 * 1024 * 1024, timeout: FIND_TIMEOUT });\n stdout = result.stdout;\n } catch (err: any) {\n if (err.stdout) {\n stdout = err.stdout;\n } else {\n console.log(chalk.red('Failed to search for skills folders.'));\n console.log(chalk.gray(String(err)));\n return;\n }\n }\n\n const skillsDirs = stdout.trim().split('\\n').filter(Boolean);\n\n if (skillsDirs.length === 0) {\n console.log(chalk.yellow('No agent skills folders found.'));\n return;\n }\n\n for (const skillsDir of skillsDirs) {\n // Get agent name from parent folder\n const agentFolder = path.basename(path.dirname(skillsDir));\n const agent = SUPPORTED_AGENTS.find(a => a.folderName === agentFolder);\n\n console.log(chalk.white.bold(agent?.name ?? agentFolder));\n console.log(chalk.gray(` ${skillsDir}`));\n\n // List skills\n const skills = await listSkillsInDir(skillsDir);\n\n if (skills.length === 0) {\n console.log(chalk.gray(' No skills installed'));\n } else {\n console.log(` Skills (${skills.length}):`);\n for (const skill of skills) {\n console.log(` - ${skill.name} ${chalk.gray(`- ${skill.description}`)}`);\n }\n }\n console.log();\n }\n}\n\n/**\n * sun show all-skill-folders\n * Find ALL folders containing a valid SKILL.md (with name/description frontmatter).\n */\nexport async function showAllSkillFolders(): Promise<void> {\n const homeDir = os.homedir();\n\n // Find all SKILL.md files\n const findCmd = `find \"${homeDir}\" -name \"SKILL.md\" -type f`;\n\n console.log(chalk.cyan('All Skill Folders'));\n console.log(chalk.gray('─'.repeat(40)));\n console.log();\n\n let stdout = '';\n try {\n const result = await execAsync(findCmd, { maxBuffer: 10 * 1024 * 1024, timeout: FIND_TIMEOUT });\n stdout = result.stdout;\n } catch (err: any) {\n if (err.stdout) {\n stdout = err.stdout;\n } else {\n console.log(chalk.red('Failed to search for SKILL.md files.'));\n console.log(chalk.gray(String(err)));\n return;\n }\n }\n\n const skillMdPaths = stdout.trim().split('\\n').filter(Boolean);\n\n if (skillMdPaths.length === 0) {\n console.log(chalk.yellow('No SKILL.md files found.'));\n return;\n }\n\n let validCount = 0;\n\n for (const skillMdPath of skillMdPaths) {\n const skillDir = path.dirname(skillMdPath);\n const metadata = await readSkillMetadata(skillDir);\n\n // Only show if it has valid name and description\n if (metadata && metadata.name && metadata.description) {\n validCount++;\n console.log(chalk.white.bold(metadata.name));\n console.log(chalk.gray(` ${skillDir}`));\n console.log(` ${metadata.description}`);\n console.log();\n }\n }\n\n if (validCount === 0) {\n console.log(chalk.yellow('No valid SKILL.md files found (missing name/description frontmatter).'));\n }\n}\n","import chalk from 'chalk';\nimport { getSupportedAgentsMessage, SUPPORTED_AGENTS } from '../core/agents';\nimport { loadConfig, setDefaultAgents, getConfigPath } from '../core/config-manager';\nimport { promptAgentSelection } from '../utils/prompts';\n\n/**\n * Re-open agent selection dialog and update config.\n */\nexport async function configCommand(): Promise<void> {\n const config = await loadConfig();\n\n console.log(chalk.cyan('Sundial CLI Configuration'));\n console.log(chalk.gray(`Config file: ${getConfigPath()}`));\n console.log();\n\n // Show current defaults\n if (config.defaultAgents.length > 0) {\n console.log('Current default agents:');\n for (const agentFlag of config.defaultAgents) {\n const agent = SUPPORTED_AGENTS.find(a => a.flag === agentFlag);\n if (agent) {\n console.log(` - ${agent.name} ${chalk.gray(`(~/${agent.folderName}/ and ./${agent.folderName}/)`)}`);\n }\n }\n console.log();\n }\n\n // Show agent type selection dialog\n const selectedAgents = await promptAgentSelection(config.defaultAgents);\n\n await setDefaultAgents(selectedAgents);\n\n console.log();\n console.log(chalk.green('Configuration saved!'));\n\n // Show new defaults\n console.log('New default agents:');\n for (const agentFlag of selectedAgents) {\n const agent = SUPPORTED_AGENTS.find(a => a.flag === agentFlag);\n if (agent) {\n console.log(` - ${agent.name} ${chalk.gray(`(~/${agent.folderName}/ and ./${agent.folderName}/)`)}`);\n }\n }\n}\n","import fuzzysort from 'fuzzysort';\nimport { COMMANDS } from '../constants';\n\nexport interface FuzzyMatch {\n command: string;\n score: number;\n}\n\n/**\n * Find the closest matching command using fuzzy search.\n * fuzzysort scores: 0 = perfect match, negative = worse match\n */\nexport function findClosestCommand(input: string): FuzzyMatch | null {\n const results = fuzzysort.go(input, COMMANDS as unknown as string[], {\n threshold: -Infinity\n });\n\n if (results.length === 0) {\n return null;\n }\n\n const best = results[0];\n return {\n command: best.target,\n score: best.score\n };\n}\n\n/**\n * Suggest a command if the input is close enough to a valid command.\n * Returns null if no good suggestion (avoids suggesting \"add\" for \"xyz\").\n */\nexport function suggestCommand(input: string): string | null {\n const match = findClosestCommand(input);\n\n if (match && match.score > -100) {\n return match.command;\n }\n return null;\n}\n\nexport function getValidCommands(): string[] {\n return [...COMMANDS];\n}\n"],"mappings":"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","names":["chalk","chalk","fs","path","os","path","fs","os","fs","path","os","fs","path","path","fs","fs","path","os","fs","path","path","fs","os","os","path","fs","isFirstRun","fs","path","chalk","chalk","ora","resolveTargetAgents","chalk","ora","chalk","chalk","chalk","chalk","chalk","path","chalk","path","os","fs","exec","promisify","execAsync","promisify","exec","fs","path","os","chalk","fs","path","chalk","chalk","chalk","require","chalk"]}
package/package.json ADDED
@@ -0,0 +1,48 @@
1
+ {
2
+ "name": "sundial-hub",
3
+ "version": "0.0.1",
4
+ "description": "A CLI to extend your agent's skills",
5
+ "type": "module",
6
+ "main": "dist/index.js",
7
+ "bin": {
8
+ "sun": "./dist/index.js"
9
+ },
10
+ "files": [
11
+ "dist"
12
+ ],
13
+ "scripts": {
14
+ "build": "tsup src/index.ts --format esm --dts --clean",
15
+ "dev": "tsx src/index.ts",
16
+ "test": "./test/run-all.sh"
17
+ },
18
+ "keywords": [
19
+ "cli",
20
+ "agents",
21
+ "skills",
22
+ "claude",
23
+ "codex",
24
+ "gemini"
25
+ ],
26
+ "author": "Belinda Mo <belinda@sundialscientific.com>",
27
+ "license": "MIT",
28
+ "dependencies": {
29
+ "@inquirer/prompts": "^8.2.0",
30
+ "adm-zip": "^0.5.16",
31
+ "chalk": "^5.3.0",
32
+ "commander": "^12.1.0",
33
+ "degit": "^2.8.4",
34
+ "fs-extra": "^11.2.0",
35
+ "fuzzysort": "^3.0.2",
36
+ "inquirer": "^9.3.7",
37
+ "ora": "^8.1.0"
38
+ },
39
+ "devDependencies": {
40
+ "@types/adm-zip": "^0.5.7",
41
+ "@types/fs-extra": "^11.0.4",
42
+ "@types/inquirer": "^9.0.9",
43
+ "@types/node": "^22.10.2",
44
+ "tsup": "^8.5.1",
45
+ "tsx": "^4.19.2",
46
+ "typescript": "^5.7.2"
47
+ }
48
+ }