Add spec for .well-known URI - #254
Conversation
Distilled from Cloudflare's Agent Skills Discovery RFC. Covers the `index.json` format, `$schema` versioning, URL resolution, SHA-256 digest verification, archive distribution (`.tar.gz`/`.zip`), HTTP requirements, and client implementation steps. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
.well-known/agent-skills/ discovery.well-known URI
Add guidance for clients to warn the user when encountering an unrecognized `type` value in skill entries, both in the format description and client implementation steps. Add a "Prompt injection" bullet to security considerations, noting that skill content is loaded into agent context and can alter agent behavior. Reword the "Trust" bullet to focus on why trusted origins matter (skills run in agent context with access to the user's environment) and reorder security considerations: Trust, Prompt injection, Script execution, Digest verification, Archive safety. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
|
Is the digest adding much here? In terms of integrity, it's likely from the same trust domain as the skills themselves so someone tampering the skill can likely tamper the index as well. For caching, would it not be better to just rely on standard HTTP caching? The presence of the digest adds friction to using this: you can't just put a bunch of static files in the |
It's possible to host the index on one domain and the skill artifacts on a CDN. In that case, the integrity hashes add an extra layer of security. See also cloudflare/agent-skills-discovery-rfc#2.
I do think people should leverage standard HTTP caching, particularly for the index! Being able to completely avoid additional GETs for each (cached) skill artifact is a minor benefit. A larger benefit is being able to check if any skills have been updated with a single GET (and to have that baked into the format rather than hope people implement HTTP caching correctly). But I think an even bigger motivator is consistency of skill bundles — if there are multiple skills that should be updated in lockstep, then you have a race condition where:
The integrity hashes allow the client to detect this scenario and retry. See also cloudflare/agent-skills-discovery-rfc#3. |
By the way, I created a GitHub Action for this: https://github.com/jonathanhefner/agentskills-build-for-well-known If this PR is merged, I intend to transfer the repo to the |
|
Fair points! I wonder if immutable/versioned skills would be a better solve for the consistency issue (less work for clients, avoid potentially many retries for a rolling deployment trying to find an index consistent with skills). Not sure if it's much of an issue. |
…stall (zeroclaw-labs#4853) Add support for installing skills via the Agent Skills `.well-known` discovery standard (agentskills/agentskills#254). When a user runs `zeroclaw skills install https://example.com`, the installer detects bare domain URLs and fetches `/.well-known/agent-skills/index.json` to discover and install available skills. - Add `--from-well-known` flag to `skills install` for explicit opt-in - Auto-detect bare domain URLs (https://host with no path) as candidates - Parse index.json with `{"skills": [{name, description, url}, ...]}` - Install each listed skill via git clone or zip download - Apply the same security audit as all other install paths - Add unit tests for URL detection, URL construction, and JSON parsing
Add /.well-known/agent-skills/index.json and per-skill download endpoints, implementing the Cloudflare Agent Skills Discovery RFC (being adopted into the spec via agentskills/agentskills#254). Any spec-compliant agent can now discover and install skills from AgentSkillDepot by fetching the well-known index — zero custom integration needed. - GET /.well-known/agent-skills/index.json — lists all public skills with name, type, description, url, and sha256 digest - GET /.well-known/agent-skills/:slug.tar.gz — direct skill download with R2 streaming and download count tracking - Add sha256_digest column to skill_versions for spec compliance - Wire route into main Hono app Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
* docs: reposition from Claude-only to open Agent Skills standard Update all user-facing copy and docs to reflect that AgentSkillDepot is a publisher platform for the open Agent Skills standard (agentskills.io), not a Claude-only registry. The standard is now implemented by 30+ agents including Claude Code, Cursor, GitHub Copilot, OpenAI Codex, Gemini CLI, and more. Changes across 8 files: - README.md: hero, description, requirements section - package.json: description field - base-skill/skillhub/SKILL.md: description + body + skill-creator ref - landing.tsx: title, meta, h1, lead, value props - install.tsx: requirements, lead, install comment - email.ts: "Claude agent" → "agent" in claim emails - package.py: error message for missing skill-creator - plan-archive.md: context paragraph + skill description Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * feat(well-known): implement Agent Skills Discovery spec endpoint Add /.well-known/agent-skills/index.json and per-skill download endpoints, implementing the Cloudflare Agent Skills Discovery RFC (being adopted into the spec via agentskills/agentskills#254). Any spec-compliant agent can now discover and install skills from AgentSkillDepot by fetching the well-known index — zero custom integration needed. - GET /.well-known/agent-skills/index.json — lists all public skills with name, type, description, url, and sha256 digest - GET /.well-known/agent-skills/:slug.tar.gz — direct skill download with R2 streaming and download count tracking - Add sha256_digest column to skill_versions for spec compliance - Wire route into main Hono app Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(well-known): spec compliance — SHA-256 digest, ZIP format, CORS Three fixes to align the .well-known endpoint with PR #254: 1. Digest: publish.ts now stores `sha256:${hex}` in sha256_digest column at publish time. The content_hash was already SHA-256 — this just adds the spec-required prefix format. 2. Archive format: serve as .zip (not .tar.gz) since our .skill files are ZIP archives. Content-Type set to application/zip. Spec says clients determine format from Content-Type header. 3. CORS: add cors({ origin: "*" }) middleware to all .well-known routes per spec recommendation for browser-based clients. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(ci): correct R2 binding name + add api-changelog entry - Fix SKILL_BUCKET → SKILLS_BUCKET typo in well-known.ts - Add .well-known + cross-vendor changelog entry for CI gate Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
* docs: reposition from Claude-only to open Agent Skills standard Update all user-facing copy and docs to reflect that AgentSkillDepot is a publisher platform for the open Agent Skills standard (agentskills.io), not a Claude-only registry. The standard is now implemented by 30+ agents including Claude Code, Cursor, GitHub Copilot, OpenAI Codex, Gemini CLI, and more. Changes across 8 files: - README.md: hero, description, requirements section - package.json: description field - base-skill/skillhub/SKILL.md: description + body + skill-creator ref - landing.tsx: title, meta, h1, lead, value props - install.tsx: requirements, lead, install comment - email.ts: "Claude agent" → "agent" in claim emails - package.py: error message for missing skill-creator - plan-archive.md: context paragraph + skill description Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * feat(well-known): implement Agent Skills Discovery spec endpoint Add /.well-known/agent-skills/index.json and per-skill download endpoints, implementing the Cloudflare Agent Skills Discovery RFC (being adopted into the spec via agentskills/agentskills#254). Any spec-compliant agent can now discover and install skills from AgentSkillDepot by fetching the well-known index — zero custom integration needed. - GET /.well-known/agent-skills/index.json — lists all public skills with name, type, description, url, and sha256 digest - GET /.well-known/agent-skills/:slug.tar.gz — direct skill download with R2 streaming and download count tracking - Add sha256_digest column to skill_versions for spec compliance - Wire route into main Hono app Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(well-known): spec compliance — SHA-256 digest, ZIP format, CORS Three fixes to align the .well-known endpoint with PR #254: 1. Digest: publish.ts now stores `sha256:${hex}` in sha256_digest column at publish time. The content_hash was already SHA-256 — this just adds the spec-required prefix format. 2. Archive format: serve as .zip (not .tar.gz) since our .skill files are ZIP archives. Content-Type set to application/zip. Spec says clients determine format from Content-Type header. 3. CORS: add cors({ origin: "*" }) middleware to all .well-known routes per spec recommendation for browser-based clients. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(ci): correct R2 binding name + add api-changelog entry - Fix SKILL_BUCKET → SKILLS_BUCKET typo in well-known.ts - Add .well-known + cross-vendor changelog entry for CI gate Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: remove remaining Claude-only references from all pages Update _layout.tsx OG description, claim.tsx, skill.tsx, dashboard.tsx, install.tsx, and landing.tsx — replace "Claude session", "inside Claude", "your Claude agent" with agent-agnostic language. Claude Code is still mentioned where appropriate as one of many supported agents in a list. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
* docs: reposition from Claude-only to open Agent Skills standard Update all user-facing copy and docs to reflect that AgentSkillDepot is a publisher platform for the open Agent Skills standard (agentskills.io), not a Claude-only registry. The standard is now implemented by 30+ agents including Claude Code, Cursor, GitHub Copilot, OpenAI Codex, Gemini CLI, and more. Changes across 8 files: - README.md: hero, description, requirements section - package.json: description field - base-skill/skillhub/SKILL.md: description + body + skill-creator ref - landing.tsx: title, meta, h1, lead, value props - install.tsx: requirements, lead, install comment - email.ts: "Claude agent" → "agent" in claim emails - package.py: error message for missing skill-creator - plan-archive.md: context paragraph + skill description Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * feat(well-known): implement Agent Skills Discovery spec endpoint Add /.well-known/agent-skills/index.json and per-skill download endpoints, implementing the Cloudflare Agent Skills Discovery RFC (being adopted into the spec via agentskills/agentskills#254). Any spec-compliant agent can now discover and install skills from AgentSkillDepot by fetching the well-known index — zero custom integration needed. - GET /.well-known/agent-skills/index.json — lists all public skills with name, type, description, url, and sha256 digest - GET /.well-known/agent-skills/:slug.tar.gz — direct skill download with R2 streaming and download count tracking - Add sha256_digest column to skill_versions for spec compliance - Wire route into main Hono app Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(well-known): spec compliance — SHA-256 digest, ZIP format, CORS Three fixes to align the .well-known endpoint with PR #254: 1. Digest: publish.ts now stores `sha256:${hex}` in sha256_digest column at publish time. The content_hash was already SHA-256 — this just adds the spec-required prefix format. 2. Archive format: serve as .zip (not .tar.gz) since our .skill files are ZIP archives. Content-Type set to application/zip. Spec says clients determine format from Content-Type header. 3. CORS: add cors({ origin: "*" }) middleware to all .well-known routes per spec recommendation for browser-based clients. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix(ci): correct R2 binding name + add api-changelog entry - Fix SKILL_BUCKET → SKILLS_BUCKET typo in well-known.ts - Add .well-known + cross-vendor changelog entry for CI gate Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: remove remaining Claude-only references from all pages Update _layout.tsx OG description, claim.tsx, skill.tsx, dashboard.tsx, install.tsx, and landing.tsx — replace "Claude session", "inside Claude", "your Claude agent" with agent-agnostic language. Claude Code is still mentioned where appropriate as one of many supported agents in a list. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * docs: add ClawHavoc security hardening implementation plan Based on deep analysis of the ClawHavoc supply-chain attack against ClawHub (1,184 malicious skills, 335 distributing AMOS malware). Five enhancements planned for a follow-up PR: 1. Typosquat detection (Levenshtein distance check on slugs) 2. New exfiltration rules (password-archives, memory manipulation, fake prerequisites) 3. Version-diff-aware scanning (catch "clean v1, malware v1.0.1") 4. New-publisher rate limiting (5 skills/week for first 7 days) 5. GitHub account linking for publishers (schema + verification) See docs/clawhavoc-hardening-plan.md for full spec with integration points, verification steps, and file paths. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Those seems to have made some assumptions:
To my mind, I agree skills are instructions - in the same way that all released software packages are instructions. These are just prose vs code. |
…45641) ## Summary This PR makes `fetchAgentSkills.mjs` a spec-compliant client of the [agent-skills `.well-known` URI spec](agentskills/agentskills#254), and updates the script to match the current release structure in [`supabase/agent-skills`](https://github.com/supabase/agent-skills). --- ## 1. Spec-compliant URL resolution and digest verification `fetchAgentSkills.mjs` acts as a client consuming the `.well-known` discovery index. The [agent-skills `.well-known` spec](agentskills/agentskills#254) is explicit on two points: **URL resolution** — skill artifact URLs in `index.json` must be resolved per [RFC 3986 §5.2.2](https://datatracker.ietf.org/doc/html/rfc3986#section-5.2.2) using the index URL as the base URI: > "The `url` field specifies where to fetch the skill artifact. URLs are resolved per RFC 3986 Section 5 using the index URL as the base URI." This means `skill.url` can be relative (`supabase.tar.gz`), path-absolute (`/.well-known/agent-skills/supabase.tar.gz`), or fully absolute (e.g. a CDN URL like `https://cdn.example.com/supabase.tar.gz`). The previous implementation extracted a filename with `.split('/').pop()` which happened to work for bare relative URLs but was not doing RFC 3986 resolution. **Digest verification** — clients must verify artifact integrity before use: > "Clients **must** verify downloaded content against the `digest` in the index. A mismatch indicates the content is corrupted or tampered with — clients **must not** use unverified content." The updated script uses `new URL(skill.url, githubReleaseIndexUrl)` for compliant resolution, verifies each artifact's SHA-256 digest from the in-memory buffer before any disk writes, and only writes to `public/.well-known/agent-skills/` once all digests pass. **Acknowledged overhead**: since Supabase owns both the publisher ([`scripts/build-release.ts`](https://github.com/supabase/agent-skills/blob/main/scripts/build-release.ts) in `supabase/agent-skills`) and this consumer, the practical risk of non-compliant URL handling is currently low — the publisher always emits bare relative filenames. However, being spec-compliant here gives us full flexibility to change how skills are packaged or hosted in `supabase/agent-skills` in the future (e.g. moving artifacts to a CDN) without needing to update this script. --- ## 2. Semver release tags #44878 referenced `supabase/agent-skills#66` (date+SHA tags). [supabase/agent-skills#77](supabase/agent-skills#77) has since merged, moving releases to semver tags managed by Release Please. `/releases/latest` works for both formats — no code change needed, just a rebase. --------- Co-authored-by: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>
…45641) ## Summary This PR makes `fetchAgentSkills.mjs` a spec-compliant client of the [agent-skills `.well-known` URI spec](agentskills/agentskills#254), and updates the script to match the current release structure in [`supabase/agent-skills`](https://github.com/supabase/agent-skills). --- ## 1. Spec-compliant URL resolution and digest verification `fetchAgentSkills.mjs` acts as a client consuming the `.well-known` discovery index. The [agent-skills `.well-known` spec](agentskills/agentskills#254) is explicit on two points: **URL resolution** — skill artifact URLs in `index.json` must be resolved per [RFC 3986 §5.2.2](https://datatracker.ietf.org/doc/html/rfc3986#section-5.2.2) using the index URL as the base URI: > "The `url` field specifies where to fetch the skill artifact. URLs are resolved per RFC 3986 Section 5 using the index URL as the base URI." This means `skill.url` can be relative (`supabase.tar.gz`), path-absolute (`/.well-known/agent-skills/supabase.tar.gz`), or fully absolute (e.g. a CDN URL like `https://cdn.example.com/supabase.tar.gz`). The previous implementation extracted a filename with `.split('/').pop()` which happened to work for bare relative URLs but was not doing RFC 3986 resolution. **Digest verification** — clients must verify artifact integrity before use: > "Clients **must** verify downloaded content against the `digest` in the index. A mismatch indicates the content is corrupted or tampered with — clients **must not** use unverified content." The updated script uses `new URL(skill.url, githubReleaseIndexUrl)` for compliant resolution, verifies each artifact's SHA-256 digest from the in-memory buffer before any disk writes, and only writes to `public/.well-known/agent-skills/` once all digests pass. **Acknowledged overhead**: since Supabase owns both the publisher ([`scripts/build-release.ts`](https://github.com/supabase/agent-skills/blob/main/scripts/build-release.ts) in `supabase/agent-skills`) and this consumer, the practical risk of non-compliant URL handling is currently low — the publisher always emits bare relative filenames. However, being spec-compliant here gives us full flexibility to change how skills are packaged or hosted in `supabase/agent-skills` in the future (e.g. moving artifacts to a CDN) without needing to update this script. --- ## 2. Semver release tags #44878 referenced `supabase/agent-skills#66` (date+SHA tags). [supabase/agent-skills#77](supabase/agent-skills#77) has since merged, moving releases to semver tags managed by Release Please. `/releases/latest` works for both formats — no code change needed, just a rebase. --------- Co-authored-by: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>
|
@petemounce @xtfer @Rodriguespn
Version pinning is done by digest + artifact URL. Entries in Note, however, that servers are not required to host older versions of skills. The spec simply allows for it. |
|
Curious if there is any movement on this proposal. You have my vote! As far as pinning, this is git, can't you just pin to the commit? I'm not sure I understand the concern. |
|
Apologies for the late reply @jonathanhefner.
Agreed that servers shouldn't be required to host older versions — but I think there's a gap in the discovery layer, and as @petemounce noted, rollback and regression reproduction are real use cases worth supporting. Artifact URLs can be anything (a CDN, a GitHub release asset, etc.), so I have no objection there. The missing piece is: to install or rollback to a specific version, a client needs the Concrete example: I have Supabase agent skills My proposal doesn't enforce publishers to host older // versions.json
{
"latest": "0.2.0",
"versions": ["0.1.0", "0.1.1", "0.2.0"]
}This gives clients a standard way to rollback, A/B test, or reproduce regressions as Pete mentioned. Would love to hear your thoughts. |
|
@schneidergithub commit pinning works when the artifact is git-addressed, and as a publisher that's what we do ourselves, our index URLs point at immutable commit hashes rather than main. But the spec deliberately allows artifact URLs that aren't git at all (CDNs, release assets), and even where they are, the thing a rollback actually needs isn't the artifact, it's the pair of artifact URL plus expected digest for the version you're going back to, and that pair only exists in an index snapshot. Which I think is @Rodriguespn's point, and from the consumer side I can confirm the gap is real: the consumer we run at TomeVault re-fetches indexes and digest-compares on every pass, so we know the moment a skill's content changes, but when it does there's no standard way to ask the publisher what it changed from. We work around it by keeping our own history of (URL, digest) pairs per skill, which works because we were already watching, but it does nothing for a fresh client that wants v0.1.6 of something it has never seen. One suggestion on the shape proposed in #380: versioned snapshots only carry trust weight if a client can rely on them not changing. A /v0.1.6/index.json path is just another mutable URL unless the spec says snapshots MUST be immutable once published, and a publisher who can rewrite history under a version label defeats the regression-reproduction case @petemounce raised. The cheap fix is for versions.json to carry the digest of each snapshot index alongside the version string, then the version list is the only thing the client has to take on trust, and a rewritten snapshot is detectable rather than silent. That also keeps @jonathanhefner's line intact: servers still aren't required to host old versions, the ones that choose to just can't quietly edit them. |
|
@olijboyd in practical terms, I think one cannot mandate a server comply with a must in a spec with only the spec. The server owner can silently mutate what they serve even if the spec says not to. I'd hazard that's contributory to how come ecosystems centralise their package management. The owner organisation starts to gain reputation for being a trustworthy spec-compliant host. In a decentralised scenario, that trust is easy to assert, (much) harder to verify. |
Totally agree with @petemounce on this. The spec can state that "snapshots MUST be immutable once published," but then there is no mechanism to enforce this in the decentralized scenario described in this spec. For that reason, my proposal deliberately states that the versioning model is built on trust that the publisher won't change a snapshot. |
|
@petemounce @Rodriguespn fair, you've changed my mind. You can't make a server honour a MUST, and the external record I floated earlier doesn't get round that, it just moves the trust from the publisher onto whoever keeps the record. From where we sit that's us, we already re-fetch indexes and digest-compare every pass, so we'd see a snapshot change under a version label. That only works because we were watching though, and a client showing up cold has no reason to take our word for it over the publisher's. What I'd want is a record the client can check for itself instead of taking it on trust from us, and that's the part that isn't ours to assert. We're not there, what we run today is the weaker private version. I don't think it belongs in this PR anyway, which is about discovery and the snapshot shape, and per-snapshot digests in versions.json are still worth doing for whoever was there from the start. Mostly I wanted to walk back my earlier comment, a side database doesn't solve this for anyone but the person who already owns the database. |
I think this would be done via client-side lock files and version control, similar to how it's done with, e.g., As mentioned, the lock file would record the old URL (and digest), and could be checked into version control. Rolling back could be done the same as reverting a change to Essentially, the lock file contains the snapshot of |
This only covers the cases where the client already knows where the skills are hosted (they were installed before in that project or when the client needs to rollback to a version that has been installed in that project), but it ignores case where the client has never seen a specific agent skills version (A/B testing, evals pipeline, etc...). Again, my point is not to enforce the agent skill providers to list their versions, but to include in the spec as a recommended practice so clients can easily discover skills the same way we currently discover npm or cargo packages. PS: This discussion is about versioning and this PR is to write a spec for agent skills discoverability under a |
|
The We ship the second layer today as a DSSE sidecar ( Disclosure: written with AI assistance, human-reviewed. |
|
Coming back to this, because I think the gap this thread landed on is now closeable. You all agreed the hard part: in a decentralised setup you can't make a publisher honour a "MUST", so a versioned snapshot is only as good as the publisher's word, and as @petemounce said, that trust is easy to assert and much harder to verify. I agreed at the time that the fix wasn't ours to assert and that we weren't there yet. We're there now. If an independent party re-fetches the index, digest-compares every pass, and signs what it actually saw at each version, then a client showing up cold has a record it can check for itself against a published key, without taking the publisher's word or mine. A rewritten snapshot stops being silent and becomes detectable by anyone, which is the property the "MUST" was reaching for. It doesn't ask publishers to host old versions or change anything in this PR, it just sits alongside as an independent witness. I've been running this at 180k+ skills, signed and served so a cold client can pull one and verify it. It composes cleanly with the digest already in the proposal (transport integrity, rooted in the publisher's domain) and with a publisher-signed sidecar like @mm-aiva's contextlock (publisher provenance). Three independent layers, none weakening the others. I'd like to help make the independent-witness piece real without adding anything to this PR, so I'd value your read on whether that's the right way to close the gap you've been circling here. |
|
The last few comments have converged on a three-layer shape: transport integrity rooted in domain + TLS (this PR's digest), publisher provenance in a signed sidecar (@mm-aiva), independent verification (@olijboyd). That layering matches what we've been running in production, so rather than propose anything new I'd like to offer two shipped implementations as prior art for whatever informative text this PR ends up carrying. GuideCheck (guidecheck.org) is a skill-provenance is the bundle-side integrity half: MANIFEST.yaml with per-resource sha256 traveling inside the bundle, and as of 5.1.0 an optional The two compose today, not hypothetically: skillprovenance.dev publishes its own GuideCheck guide at If it would help, I'm happy to draft a short informative paragraph naming the independently-verifying layers and where each roots its trust (domain, publisher key, verifier key). A couple of sentences of non-normative text, no new spec surface. Disclosure: drafted with AI assistance, human-reviewed, per the contributing guidelines. |
See accompanying proposal issue here: #255
Skill distribution is one of the most-discussed gaps in the spec (#27, #81, #210, #243). Today, distributing skills means sharing files ad hoc — cloning repos, copying directories, or bundling them in platform-specific packages.
This PR adds a standardized distribution mechanism: a publisher hosts an
index.jsonat a well-known URL (RFC 8615) that enumerates available skills. Clients fetch the index, download skill artifacts, and verify their integrity.How it works
Publishers serve a discovery index at
/.well-known/agent-skills/index.json:{ "$schema": "https://schemas.agentskills.io/discovery/0.2.0/schema.json", "skills": [ { "name": "code-review", "type": "skill-md", "description": "Review code for bugs, security issues, and best practices.", "url": "/.well-known/agent-skills/code-review/SKILL.md", "digest": "sha256:c4d5e6f7..." }, { "name": "wrangler", "type": "archive", "description": "Deploy and manage Cloudflare Workers projects.", "url": "/.well-known/agent-skills/wrangler.tar.gz", "digest": "sha256:a1b2c3d4..." } ] }Skills are distributed as either a single
SKILL.mdfile (type: "skill-md") or a bundled archive (type: "archive") for skills with scripts, references, and assets. Each entry includes a SHA-256 digest for integrity verification and caching. URLs can be relative, path-absolute, or fully qualified, so skills can be hosted anywhere (e.g., on a CDN).The spec also covers archive safety (path traversal, symlink, decompression bomb protections), HTTP requirements, client implementation steps, and security considerations for script execution.
Provenance
Based on Cloudflare's Agent Skills Discovery RFC, incorporating changes from a proposed revision that the RFC authors have tentatively approved.
Preview: https://agent-skills-jh-well-known-uri.mintlify.app/well-known-uri