You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Public session-scoped skill provider API (lazy list/read callbacks) #2831
Today the SDK can only load Agent Skills from the local filesystem (skill_directories / skillDirectories). Applications whose skills live somewhere else have to write every SKILL.md to disk before the session starts. Examples of "somewhere else":
Writing the files to disk up front causes several problems:
Everything is fetched eagerly. Skills are designed for progressive disclosure: the model sees only names and descriptions until it activates a skill. Writing files to disk means downloading every skill's full content at session start, including skills that are never used.
Content goes stale. Files written at startup can't reflect a source that changes during a long-lived session, and invalidating or refreshing them means rewriting the filesystem.
Content can't be verified at activation. An application that wants to check content when the skill actually loads, for example against an expected digest or size, has no hook. Once a file is on disk, it can change between listing and activation.
Sessions aren't isolated. Multi-session hosts must create and clean up a separate directory tree per session to keep one session's skills out of another's.
The host needs extra write access. Environments with read-only or restricted filesystems must grant write access just to stage skills.
The source is invisible. Skills from different sources are indistinguishable once copied to disk, so name collisions and provenance are hard to handle.
Proposed solution
Add a public, session-scoped skill provider option to session configuration in every SDK language. The host supplies callbacks instead of files:
classSkillProvider(Protocol):
asyncdeflist_skills(self) ->list[SkillDescriptor]:
"""Return metadata only (name, description, optional frontmatter). No content."""asyncdefread_skill(self, name: str) ->str|bytes:
"""Return the full SKILL.md. Called lazily, only when the skill is activated."""session=awaitclient.create_session(
SessionConfig(skill_provider=MyProvider(), ...)
)
(TypeScript and .NET would expose the equivalent skillProvider option.)
Requested semantics
Lazy content.list returns metadata only; read is called only when the model or user activates that skill.
Session scope. A provider is bound to one session and is never shared with or visible to another session.
Async and cancellable. Both callbacks are async, honor cancellation, and run under a documented timeout.
Failure stays local. A list or read error makes the affected skill (or catalog) unavailable and surfaces a typed error or event. It does not fail the session or turn.
Works alongside skill_directories. The provider and directories can be used together, with documented precedence or name-collision rules.
Lifecycle. The provider is released when the session closes or disconnects. Resuming a session either re-binds a provider or documents that the host must supply one again.
Documented limits. Maximum catalog size, description length and SKILL.md size are documented so hosts can enforce the same bounds.
Capability detection. Hosts can detect whether the connected CLI/runtime supports providers (for example a capability flag or version check), so they can fall back to skill_directories on older runtimes.
Optional provenance. A descriptor can carry an origin label, so the UI and model can tell skills from different sources apart.
Why this belongs in the SDK
The CLI's JSON-RPC surface appears to already have provider-style skill callbacks (list/read). The main gap seems to be a stable, documented, public SDK API over that surface. Without one, consumers either write files to disk (with the problems above) or depend on unpublished protocol details that can break between releases.
Relevance to the MCP Skills extension
The MCP Skills extension (io.modelcontextprotocol/skills, SEP-2640, Final) standardizes how MCP servers serve Agent Skills. Its model matches the provider proposed here, which makes a provider API the natural way for SDK hosts to support MCP-served skills without writing files to disk:
MCP Skills extension
Skill provider
skills/list returns metadata only: complete frontmatter plus a file manifest with SHA-256 digest and size, and no content
list_skills() returns descriptors only
Content is read separately with resources/read, and reading does not itself activate a skill
read_skill() is called lazily, only on activation
"The host routes the read through its skill-loading path, which verifies the content and applies any required user approval before loading it into model context"
The read callback is the host's hook to check digest and size and apply approval before content reaches the model. Writing files to disk up front removes that hook.
Skill identity is the originating server identity plus the URI. Names are labels, not unique, and hosts must preserve server identity
Descriptors need a stable identity or origin plus collision rules (semantics 5 and 9)
List results carry ttlMs and cacheScope
Hosts need a way to refresh the catalog during a session (semantic 10)
SKILL.md may reference supporting files resolved against the skill's root directory
The provider needs to serve supporting files, not only SKILL.md (semantic 11)
The extension notes that SDK and host support is still being implemented (see the client support matrix). A public provider API would let any Copilot SDK host bridge an MCP Skills server to a session with a thin adapter that maps skills/list to list and resources/read to read, and would make the SDK a natural entry in that matrix.
Additional semantics implied by the extension
Catalog refresh. A host can tell the session that its catalog changed (or the runtime re-calls list after a host-supplied TTL), so updated or withdrawn skills don't stay visible for the rest of a long session.
Supporting files.read can fetch files relative to a skill's root (for example read_skill_file(name, "references/checklist.md")), so multi-file skills work without writing anything to disk.
Acceptance criteria
Public skill_provider / skillProvider session option in the Python, TypeScript and .NET SDKs
Lazy read verified: no content is requested during listing
Per-session isolation and cleanup on session close
Errors are isolated to skills, not sessions
Capability detection for older runtimes
Documentation and a sample, for example a provider backed by an MCP Skills server or an in-memory dictionary
Supporting-file reads and catalog refresh, so an MCP Skills extension server can be bridged without writing files to disk
Activity