| 120 | } |
| 121 | |
| 122 | function parseSkillFrontmatter(content, fallbackName) { |
| 123 | const match = content.match(/^---\s*\n([\s\S]*?)\n---\s*\n([\s\S]*)$/) |
| 124 | if (!match) return { name: fallbackName, description: '', body: content.trim(), source: 'file' } |
| 125 | const meta = {} |
| 126 | for (const line of match[1].split('\n')) { |
| 127 | const kv = line.match(/^(\w+):\s*(.+)$/) |
| 128 | if (kv) meta[kv[1]] = kv[2].trim() |
| 129 | } |
| 130 | return { |
| 131 | name: meta.name || fallbackName, |
| 132 | description: meta.description || '', |
| 133 | body: match[2].trim(), |
| 134 | source: 'file', |
| 135 | } |
| 136 | } |
| 137 | |
| 138 | function resolveSkillPrompt(prompt) { |
| 139 | const m = prompt.match(/^\/(\S+)\s*(.*)$/s) |