feat: build index.json for .well-known/agent-skills in release pipeline#77
Merged
Conversation
Replaces the inline bash tar loop with a TypeScript build script that produces both skill tarballs and a discovery index.json conforming to the agent-skills discovery spec (RFC v0.2.0). Applies improvements identified in code review of #66: - Deterministic archives: zero timestamps/uid/gid so digests only change when content changes (requires GNU tar; falls back to BSD tar with a warning on macOS) - Exclude patterns: .gitignore-style walk skips .DS_Store, .vscode, etc. - Auto-detect skill-md vs archive: single-file skills emit type "skill-md" and copy SKILL.md directly instead of creating a tarball - Relative URLs in index.json: portable across serving paths - Validate both name and description frontmatter fields Co-Authored-By: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>
…ote to README Co-Authored-By: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>
48cb45b to
67ec55d
Compare
gregnr
requested changes
May 9, 2026
gregnr
reviewed
May 9, 2026
Replace shell-out to system tar/gzip binaries with the tar npm package. Drops the custom file-walker, exclude-pattern matching, GNU tar detection, and BSD tar fallback — none of which are needed in a clean CI checkout. Determinism is preserved via portable: true and mtime: new Date(0). Always emits type: "archive" for all skills, removing the isSingleFile branch since the spec recommendation is not a hard requirement. Renames release-please.yml to release.yml. Co-Authored-By: Claude Sonnet 4.6 (1M context) <noreply@anthropic.com>
gregnr
approved these changes
May 11, 2026
Rodriguespn
added a commit
to supabase/supabase
that referenced
this pull request
May 15, 2026
…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>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Supersedes #66. The release pipeline has been consolidated under Release Please (see #75), which already triggers on every skill change via conventional commits. A separate date+SHA release job is no longer needed —
index.jsonis now built and uploaded as part of the same Release Please event.Closes AI-704
What changed
Replaces the inline bash
tarloop inrelease-please.ymlwith a TypeScript build script (scripts/build-release.ts) that produces both skill tarballs and aindex.jsondiscovery index conforming to the agent-skills.well-knownURI spec (schema v0.2.0). Renames the workflow file torelease.yml.tarnpm library withportable: trueandmtime: new Date(0)so digests only change when content changes; no dependency on system tar binariesarchivetype — every skill produces a.tar.gzand emitstype: "archive"in the index; the spec'sskill-mdrecommendation is ashould, not amustindex.jsonuses relative URLs (e.g.supabase.tar.gz) so the serving path is fully controlled by the consumer (supabase/supabase#45641)nameanddescription— frontmatter validation now covers both required fieldsRelease assets per semver tag