{"record":{"id":"4083afb157ea6feb","repo":"larksuite/cli","slug":"build-embeds-no-base-skill-content","errorCode":null,"errorMessage":"build embeds no base skill content","messagePattern":"build embeds no base skill content","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/skillpolicy/resolver.go","lineNumber":39,"sourceCode":"// conflict can be attributed to specific owners. Mirrors\n// cmdpolicy.PluginRule.\ntype PluginSkill struct {\n\tPluginName    string\n\tSkillsOverlay *platform.SkillsOverlay\n}\n\n// ErrMultipleSkillsOverlays reports that more than one plugin tried to\n// customize skill content. Mirrors cmdpolicy.ErrMultipleRestricts: only\n// one owner is allowed so independent plugins cannot silently overwrite\n// each other's skill tree.\nvar ErrMultipleSkillsOverlays = errors.New(\"multiple plugins customized skills; only one plugin may own skill content\")\n\n// ErrNoBaseSkillContent reports that Allow or Remove was requested against an\n// empty base tree. This most often means an external wrapper main omitted\n// cmd.SetEmbeddedSkillContent; exposing a sentinel lets the command layer give\n// the integrator that specific recovery action instead of blaming a skill-name\n// typo.\nvar ErrNoBaseSkillContent = errors.New(\"build embeds no base skill content\")\n\n// ErrInvalidHostBase reports that the wrapper-provided base skill tree is\n// malformed. It is distinct from a plugin's replacement Base so diagnostics\n// can direct the integrator to the correct owner.\nvar ErrInvalidHostBase = errors.New(\"host embedded skill content is invalid\")\n\n// ErrUnsatisfiedSkillDependency reports that a skill retained by the final\n// composed manifest declares another skill that the manifest does not retain.\n// The resolver never widens Allow or overrides Remove to repair this: an\n// incomplete distribution is a build-integrity error.\nvar ErrUnsatisfiedSkillDependency = errors.New(\"composed skill tree has an unsatisfied required skill\")\n\n// Resolution is the build-local result of composing embedded skill assets.\n// Content serves `skills list`/`read`; References projects canonical\n// CLI-authored pointers onto that same tree.\ntype Resolution struct {\n\tContent    fs.FS\n\tReferences *skillref.Resolver","sourceCodeStart":21,"sourceCodeEnd":57,"githubUrl":"https://github.com/larksuite/cli/blob/7fd6ef3c07182257ce776cdc5a614e122d5bd4b3/internal/skillpolicy/resolver.go#L21-L57","documentation":"ErrNoBaseSkillContent reports that Allow or Remove skill operations were requested against an empty base skill tree — most often because an external wrapper main never called cmd.SetEmbeddedSkillContent. It is a public sentinel so the command layer (cmd/platform_guards.go) can attach a specific recovery hint telling the integrator to embed base content instead of blaming a skill-name typo.","triggerScenarios":"A plugin spec with non-empty Allow or Remove lists is resolved while the embedded base skill tree is empty (len(lower.skills) == 0) because cmd.SetEmbeddedSkillContent was not called before Execute.","commonSituations":"Third-party wrapper mains that assemble the CLI without the standard embedded assets; builds where the embed directive was removed or the assets directory is empty; tests constructing the command with plugin skill filters but no base content.","solutions":["Call cmd.SetEmbeddedSkillContent with the embedded skill FS in your wrapper main before Execute.","Ensure EmbeddedSkills.Base is non-empty if you supply content explicitly.","If no skill filtering is intended, remove the Allow/Remove entries from the plugin spec."],"exampleFix":"// before: wrapper main\nfunc main() { cmd.Execute() }\n// after\nfunc main() {\n    cmd.SetEmbeddedSkillContent(skillsFS)\n    cmd.Execute()\n}","handlingStrategy":"try-catch","validationCode":"// before registering plugin Allow/Remove specs:\nif embeddedSkillFS == nil {\n    return errors.New(\"call cmd.SetEmbeddedSkillContent before Execute\")\n}","typeGuard":"if errors.Is(err, skillpolicy.ErrNoBaseSkillContent) {\n    // integrator-level problem: embed content, not a skill-name typo\n}","tryCatchPattern":"if err := execute(); err != nil {\n    if errors.Is(err, skillpolicy.ErrNoBaseSkillContent) {\n        // follow the hint: call cmd.SetEmbeddedSkillContent before Execute\n    }\n}","preventionTips":["Always call cmd.SetEmbeddedSkillContent in wrapper mains before Execute.","Verify EmbeddedSkills.Base is non-empty in build smoke tests.","Only set Allow/Remove when base content is guaranteed to exist."],"tags":["go","skills","embed","plugin","build-integrity"],"backgroundTag":"missing-embedded-content","analyzedSha":"7fd6ef3c07182257ce776cdc5a614e122d5bd4b3","analyzedAt":"2026-09-04T21:17:44.649Z","contentChangedAt":"2026-09-04T21:17:44.649Z","schemaVersion":2},"datasetVersion":"2026-09-12T02:17:10.037Z"}