Documentation
¶
Overview ¶
Package skills parses and prepares skill references for agent.SkillPreparer.
A reference has the form <git-url>[@<ref>][#<sub/dir>], for example
https://github.com/acme/skills#skills/tdd https://github.com/acme/my-plugin@v1.2.0 git@github.com:acme/my-plugin@v1.2.0
Index ¶
Constants ¶
This section is empty.
Variables ¶
var RefreshAlways = RefreshPolicy{/* contains filtered or unexported fields */}
RefreshAlways refreshes an existing clone on every Prepare call.
var RefreshNever = RefreshPolicy{/* contains filtered or unexported fields */}
RefreshNever never refreshes an existing clone.
Functions ¶
This section is empty.
Types ¶
type Manager ¶
type Manager struct {
// Git runs a git subcommand in dir (or outside any repository when dir
// is empty) and returns its combined output. Tests replace it with a
// fake that copies a fixture directory instead of cloning over the
// network.
Git func(ctx context.Context, dir string, args ...string) (string, error)
// Now overrides the clock (tests).
Now func() time.Time
// SkillsOnly restricts the layout step to the SKILL.md and skills/
// shapes: Prepare never returns a repository's own directory, even when
// it is itself a Claude Code plugin, and always returns a generated
// wrapper holding only skills/ and the manifest the wrapper needs. No
// hooks, MCP servers, agents or commands from the repository come
// through, even when it has them. Set it before the manager is used; it
// is not safe to change concurrently with Prepare the way the refresh
// policy is.
SkillsOnly bool
// contains filtered or unexported fields
}
Manager implements agent.SkillPreparer: it clones skill references on demand, refreshes them under a caller-controlled policy, and hands their resolved target directory to the layout step that builds (or reuses) the plugin directory claude is pointed at.
Manager caches exclusively under the directory passed to NewManager; it reads no environment variable to choose where that is.
func NewManager ¶
NewManager returns a Manager that caches clones and generated wrapper plugins under cacheDir. A nil logger uses slog.Default(). The refresh policy starts at RefreshNever; call SetRefresh to change it.
func (*Manager) Prepare ¶
Prepare implements agent.SkillPreparer: it ensures every reference is cloned (and refreshed, under the current policy) and returns their plugin directories in the same order, ready to pass to claude via --plugin-dir.
func (*Manager) SetRefresh ¶
func (m *Manager) SetRefresh(p RefreshPolicy)
SetRefresh changes the refresh policy a running Manager uses. It is safe to call concurrently with Prepare; a Prepare call that starts after SetRefresh returns uses the new policy.
type Ref ¶
Ref is a parsed skill reference: a git URL, an optional ref (branch, tag or commit) and an optional sub-directory within the repository.
func Parse ¶
Parse splits a skill reference of the form <git-url>[@<ref>][#<sub/dir>] into its URL, ref and sub-directory.
A trailing "@ref" is only taken as a ref when it comes after the last "/" or ":" of the remaining string, so scp-style URLs such as git@host:org/repo and git@host:org/repo@v1 still parse correctly.
Parse rejects an empty URL and a sub-directory that is absolute or that, once cleaned, climbs above its root (for example #../x or #a/../../x).
type RefreshPolicy ¶
type RefreshPolicy struct {
// contains filtered or unexported fields
}
RefreshPolicy controls when Prepare refreshes an existing clone before using it. A clone that does not exist yet is always cloned, whatever the policy in force.
func ParseRefresh ¶
func ParseRefresh(s string) (RefreshPolicy, error)
ParseRefresh parses a refresh-policy configuration string: "never", "always", or a Go duration such as "1h". Any other string, including the empty string, is rejected.
func RefreshEvery ¶
func RefreshEvery(d time.Duration) RefreshPolicy
RefreshEvery returns a policy that refreshes an existing clone only when its last refresh is older than d.