fix(skill-loader): implement eager loading to resolve empty slash commands

This commit is contained in:
Momentum96 2026-01-12 17:27:54 +09:00
parent f9dca8d877
commit 6bbe69a72a

View File

@ -63,7 +63,7 @@ async function loadSkillFromPath(
): Promise<LoadedSkill | null> { ): Promise<LoadedSkill | null> {
try { try {
const content = await fs.readFile(skillPath, "utf-8") const content = await fs.readFile(skillPath, "utf-8")
const { data } = parseFrontmatter<SkillMetadata>(content) const { data, body } = parseFrontmatter<SkillMetadata>(content)
const frontmatterMcp = parseSkillMcpConfigFromFrontmatter(content) const frontmatterMcp = parseSkillMcpConfigFromFrontmatter(content)
const mcpJsonMcp = await loadMcpJsonFromDir(resolvedPath) const mcpJsonMcp = await loadMcpJsonFromDir(resolvedPath)
const mcpConfig = mcpJsonMcp || frontmatterMcp const mcpConfig = mcpJsonMcp || frontmatterMcp
@ -73,14 +73,7 @@ async function loadSkillFromPath(
const isOpencodeSource = scope === "opencode" || scope === "opencode-project" const isOpencodeSource = scope === "opencode" || scope === "opencode-project"
const formattedDescription = `(${scope} - Skill) ${originalDescription}` const formattedDescription = `(${scope} - Skill) ${originalDescription}`
const lazyContent: LazyContentLoader = { const templateContent = `<skill-instruction>
loaded: false,
content: undefined,
load: async () => {
if (!lazyContent.loaded) {
const fileContent = await fs.readFile(skillPath, "utf-8")
const { body } = parseFrontmatter<SkillMetadata>(fileContent)
lazyContent.content = `<skill-instruction>
Base directory for this skill: ${resolvedPath}/ Base directory for this skill: ${resolvedPath}/
File references (@path) in this skill are relative to this directory. File references (@path) in this skill are relative to this directory.
@ -90,16 +83,17 @@ ${body.trim()}
<user-request> <user-request>
$ARGUMENTS $ARGUMENTS
</user-request>` </user-request>`
lazyContent.loaded = true
} const lazyContent: LazyContentLoader = {
return lazyContent.content! loaded: true,
}, content: templateContent,
load: async () => templateContent,
} }
const definition: CommandDefinition = { const definition: CommandDefinition = {
name: skillName, name: skillName,
description: formattedDescription, description: formattedDescription,
template: "", template: templateContent,
model: sanitizeModelField(data.model, isOpencodeSource ? "opencode" : "claude-code"), model: sanitizeModelField(data.model, isOpencodeSource ? "opencode" : "claude-code"),
agent: data.agent, agent: data.agent,
subtask: data.subtask, subtask: data.subtask,