skilllib 1.3.0 → 1.6.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -15,7 +15,7 @@ and every agent you use can see them.
15
15
  npx skilllib
16
16
  ```
17
17
 
18
- <img src="docs/screenshot-project.svg" alt="skilllib: Places on the left, a repo's skills with their issues and uses, and the selected skill's fixes and actions below" width="100%">
18
+ <img src="docs/design/repo.svg" alt="skilllib: Places on the left, a repo's skills with their issues and uses, and the selected skill's fixes and actions below" width="100%">
19
19
 
20
20
  </div>
21
21
 
@@ -46,13 +46,14 @@ Most agents can't turn off a global skill for just one repo. Claude Code can, bu
46
46
  - **📚 Your skills: one versioned library.** Every skill has a single master copy in `~/.skilllib/library`, and each change becomes a new version.
47
47
  - **📦 Per-repo installs, pinned like dependencies.** Each repo lists its skills and versions in `skilllib.json`. `sync` reproduces them exactly, and `update` moves to the newest.
48
48
  - **🤝 One copy, every agent.** skilllib puts one real copy in the repo and links it into whichever folders your other agents read.
49
- - **🧹 Health: one list of what to fix.** Global skills you haven't decided about, skills loaded twice, updates, broken links, each with its fix. For a global skill: move it to the repos that need it, keep it global, or delete it. Usage numbers and descriptions help you decide.
49
+ - **🧹 Health: one list of what to fix.** Global skills you haven't decided about, skills loaded twice, duplicate copies, updates, broken links, each with its fix. For a global skill: move it to the repos that need it, keep it global, or delete it. Usage numbers and descriptions help you decide.
50
50
  - **✓ Global on purpose.** Some skills belong everywhere. Mark them once and skilllib stops warning about them.
51
51
  - **🔎 See everything in a repo:**
52
52
  - where each skill comes from (the repo, your library, global, a plugin, claude.ai…)
53
53
  - which agents load it
54
54
  - whether it's committed to git or gitignored
55
55
  - how often it was used
56
+ - **💬 Talk to your agents about your skills.** Ask Claude Code, Cursor or Codex "which skills can you use here, and where do they come from?" or "which of my skills should this repo use?". They answer with skilllib.
56
57
  - **✦ Ask an agent.** Copy a ready-made prompt with all of that data, and let Claude Code, Cursor or Codex tell you what to keep, move or delete.
57
58
  - **🛟 Nothing is lost.** Every removal goes to a backup you can restore with one key.
58
59
 
@@ -130,13 +131,14 @@ What skilllib flags:
130
131
  | Issue | Fixes |
131
132
  |---|---|
132
133
  | **Loaded twice** (also global, or also in a plugin) | Keep the repo's copy and stop loading it globally, or keep it global |
133
- | **Same name as a plugin skill** | Remove the repo's copy, or turn the plugin off with `/plugin` |
134
+ | **Same name as a plugin skill** | Remove the repo's copy, or turn the plugin off in this repo only (`.claude/settings.local.json`) |
134
135
  | **Folder missing** · **Not in your library** | Restore it · copy it back into your library |
135
136
  | **Update to vN** · **Edited here** | Update · save the edits as a new version, or discard them |
136
137
  | ***Agent* can't see it** | Link it for every agent (links only; nothing is copied or moved) |
137
138
  | **Differs from library** · **Not tracked** · **Only in this repo** | Update your library from it, or replace it · track it · import it |
138
139
  | **Unused 30 days** | Remove it from the repo |
139
140
  | **Broken link** · **Not reviewed** (global) | Remove the link · move it to repos, keep it global on purpose, or delete it |
141
+ | ***Agent* can't see it** (global) | Link it into that agent's global folder, e.g. a Codex skill in `~/.agents/skills` or `~/.codex/skills` gets a link in `~/.claude/skills` |
140
142
 
141
143
  ### Adding and removing skills
142
144
 
@@ -144,7 +146,7 @@ What skilllib flags:
144
146
  - **Adding** copies the newest version into the fewest folders your agents read, and records it in `skilllib.json`. Agents pick it up in their next session. The layout matches `npx skills`' symlink option: the real copy lives in `.agents/skills`, which nearly every agent reads, and Claude Code gets a link.
145
147
  - Claude Code (with or without Cursor): `.claude/skills/<name>`.
146
148
  - Cursor, Codex or Zed without Claude Code: `.agents/skills/<name>`.
147
- - Claude Code plus Codex or Zed: the copy goes in `.agents/skills`, with a link in `.claude/skills`. Claude Code only reads `.claude/skills`, and Codex and Zed only read `.agents/skills`.
149
+ - Claude Code plus Codex or Zed: the copy goes in `.agents/skills`, with a link in `.claude/skills`. Claude Code only reads `.claude/skills`, and Codex and Zed don't read it.
148
150
  - **Remove from repo** deletes that copy and its links; your library keeps it. An untracked copy goes to Settings › Backups instead. If you edited a tracked skill here, skilllib asks first.
149
151
  - **The repo's own skills are never deleted by skilllib.** You can copy them into your library, or link them so every agent sees them.
150
152
  - **Git-tracked folders:** if the repo commits the folder a link would go into (common for `.agents/skills`), skilllib asks once and remembers your answer.
@@ -168,7 +170,7 @@ Edit a skill once in **Your skills** (Enter → *Edit SKILL.md*). Every repo tha
168
170
 
169
171
  ### Global skills
170
172
 
171
- <img src="docs/screenshot-global.svg" alt="Global: everything that loads in every repo, with skills installed together folded into one group and actions for the whole group" width="100%">
173
+ <img src="docs/design/global.svg" alt="Global: everything that loads in every repo, with skills installed together folded into one group and actions for the whole group" width="100%">
172
174
 
173
175
  **Global** lists everything that loads in every repo. Each of your global skills you haven't decided about is flagged **Not reviewed**, with three choices:
174
176
 
@@ -176,6 +178,8 @@ Edit a skill once in **Your skills** (Enter → *Edit SKILL.md*). Every repo tha
176
178
  - **Keep it global on purpose**: skilllib stops warning about it (also `skilllib global keep <name>`). The mark only records your decision; to undo it, pick **Stop marking it as global on purpose**.
177
179
  - **Delete it**: it goes to Settings › Backups.
178
180
 
181
+ When some of your agents can't see a global skill, the flag says so (**Not reviewed · Claude Code can't see it**). This happens, for example, with a Codex skill in `~/.agents/skills` or `~/.codex/skills`, which Claude Code doesn't read. Then a fourth choice appears: **Link it for Claude Code** adds a link in `~/.claude/skills`, and nothing is copied or moved. Moving it to repos works for every agent too. For a skill you keep global on purpose, the link is the ★ fix.
182
+
179
183
  Vendor skills (plugins, claude.ai, Cursor built-ins) are managed at their source: `/plugin` in Claude Code, or claude.ai's settings.
180
184
 
181
185
  **Replacing a plugin with library skills:** on a plugin's skill or group, **Replace *plugin* with library skills…** copies all its skills into your library (grouped under the plugin), adds them to the repos you tick, and uninstalls the plugin (`claude plugin uninstall`, keeping its saved data; Settings › Backups reinstalls it). A plugin can't be half removed, so it's all its skills at once; the confirmation says what else it brings (commands, agents, hooks, MCP servers) that goes too. If the `claude` command isn't available, skilllib turns the plugin off instead and tells you to finish with `/plugin uninstall`. Plugins synced from claude.ai can't be removed from here: skilllib copies their skills and tells you to remove the plugin on claude.ai.
@@ -195,23 +199,43 @@ Paste it into Claude Code, Cursor or Codex. You get back **keep global / move to
195
199
 
196
200
  It's in every skill's actions, in a repo's **⋯** menu (all its skills), and at the top of Global (all your global skills).
197
201
 
202
+ ### Ask your agents about skills
203
+
204
+ Run this once:
205
+
206
+ ```bash
207
+ skilllib agent-skill install
208
+ ```
209
+
210
+ This installs a small `skilllib` skill that tells your agents how to use skilllib. It goes where your agents look, in every repo: `~/.claude/skills` for Claude Code and Cursor, with a link in `~/.agents/skills` for Codex and Zed. This is the one skill that should be global, because it's about every repo. Health offers the same install, and upgrading skilllib keeps the skill up to date.
211
+
212
+ Then, in any repo, you can ask:
213
+
214
+ - *Which skills can you use in this repo?*
215
+ - *Where does each one come from?*
216
+ - *Which skills from my library would you add to this project?*
217
+ - *Is anything out of date? Update it.*
218
+
219
+ The agent runs `skilllib status --json`, `skilllib list --json` and similar commands, reads the repo, and answers. It asks before it adds or removes anything. `skilllib agent-skill remove` uninstalls it.
220
+
198
221
  ### Duplicates
199
222
 
200
- The same skill often reaches your agents more than once: a copy in `.claude/skills` *and* in `.agents/skills`, a global copy *and* a repo copy, a plugin *and* your skill. skilllib keeps **one real copy per skill, plus only the links your agents need**. `skilllib doctor` lists each case, and `skilllib tidy` fixes the folder ones.
223
+ The same skill often reaches your agents more than once: a copy in `.claude/skills` *and* in `.agents/skills`, a global copy *and* a repo copy, a plugin *and* your skill. skilllib keeps **one real copy per skill, plus only the links your agents need**. **Health** lists each case on the skill it's about, with its fix. From the command line, `skilllib doctor` lists them and `skilllib tidy` fixes the folder ones.
201
224
 
202
225
  | What it finds | What it does |
203
226
  |---|---|
204
227
  | Identical copies in several folders | Keeps one and turns the others into links. In a repo, it keeps the committed copy. Globally, it keeps the one in `~/.agents/skills`. |
205
228
  | Links no agent you use needs | Removes them. It keeps links that `skilllib.json` records, because teammates may use other agents. |
206
- | **Copies that differ** | Shows which agent runs which copy (e.g. Claude Code and Cursor run `.claude`, Codex runs `.agents`), and lets you pick the one to keep. |
207
- | A Claude Code plugin with the same skill | Your skill wins. skilllib copies all the plugin's skills into Your skills, then removes the plugin or turns it off (`claude plugin uninstall` / `disable`). If the plugin also brings MCP servers, hooks, agents or commands, turning it off is the default. |
229
+ | **Copies that differ** | Shows which agent runs which copy (e.g. Claude Code and Cursor run `.claude`, Codex runs `.agents`), and lets you pick the one to keep. It's your call, so **Fix all** never does it. |
230
+ | A Claude Code plugin with the same skill | Your skill wins. skilllib copies all the plugin's skills into Your skills, then removes the plugin or turns it off (`claude plugin uninstall` / `disable`). If the plugin also brings MCP servers, hooks, agents or commands, turning it off is the default. When the overlap is in one repo, you can instead turn the plugin off only there, or remove your copy from that repo. A plugin that a repo's own `.claude/settings.json` turns on counts only in that repo. |
208
231
  | A Cursor plugin with the same skill | Reported only. Turn the plugin off in Cursor. |
209
- | A repo copy of a skill you keep global | The repo copy is the extra one. Claude Code runs the global copy anyway. |
232
+ | A repo copy of a skill you keep global | The repo copy is the extra one: remove it, or stop loading the skill globally after all. Claude Code runs the global copy anyway. |
233
+ | A repo's own skill that also loads globally | Stop loading it globally. The repo's copy is the team's, so skilllib never offers to remove it. |
210
234
 
211
235
  - **It never moves a real copy.** `skilllib.json` is shared, so a move for your agents could break a teammate's.
212
236
  - **It never adds links.** That's `skilllib link`, or a skill's *can't see it* fix.
213
- - **It leaves committed files alone** unless you pass `--allow-git`.
214
- - **Cursor lists a skill once** even when it reaches it through several folders (tested September 2026). It lists a plugin's copy and your copy separately.
237
+ - **It leaves committed files alone** unless you say so: Health asks first, and `skilllib tidy` needs `--allow-git`.
238
+ - **Cursor lists a skill once** even when it reaches it through several folders (tested September 2026). It runs the copy from the first of `.cursor`, `.claude`, `.codex`, `.grok`, `.agents` (seen in its app bundle, October 2026). It lists a plugin's copy and your copy separately.
215
239
 
216
240
  ### Backups
217
241
 
@@ -219,6 +243,7 @@ skilllib never really deletes anything you can't get back. What it removes goes
219
243
  - removed library skills and untracked copies go to `~/.skilllib/trash`
220
244
  - removed global skills go to `~/.skilllib/global-backup`
221
245
  - copies replaced by a link go to `~/.skilllib/tidy-backup`
246
+ - edits `skilllib doctor` discards go to `~/.skilllib/edit-backup`
222
247
  - removed plugins are listed too; restoring one reinstalls it
223
248
 
224
249
  ---
@@ -230,21 +255,26 @@ A skill is a folder with a `SKILL.md`. These are all the places your agents load
230
255
  | Where | Examples | Who sees it |
231
256
  |---|---|---|
232
257
  | **The repo** | `.claude/skills`, `.agents/skills`, `.cursor/skills`, `.codex/skills` | Agents working in that repo |
233
- | **Global folders** | `~/.claude/skills`, `~/.agents/skills` (`npx skills add` installs here), `~/.cursor/skills` | **Every repo** |
234
- | **Vendors** | Claude Code plugins (`/plugin`), claude.ai skills, Claude Code's bundled commands, Cursor built-ins and marketplace, Codex system skills | Every repo; only the vendor can remove them |
258
+ | **Subfolders** (monorepos) | `packages/web/.claude/skills`, `packages/api/.agents/skills` | Agents working in that folder. `skilllib status` lists them; skilllib never links, tracks or tidies them, since that would make them load repo-wide |
259
+ | **Global folders** | `~/.claude/skills`, `~/.agents/skills` (`npx skills add` installs here), `~/.codex/skills`, `~/.cursor/skills` | **Every repo** |
260
+ | **Vendors** | Claude Code plugins (`/plugin`), claude.ai skills, Claude Code's bundled commands, Cursor built-ins and marketplace, Codex system skills and `/etc/codex/skills` (admin) | Every repo (a repo's `.claude/settings.json` can turn a plugin on or off just there); only the vendor can remove them |
235
261
  | **Your skills** | `~/.skilllib/library` | Nobody, until you add a skill to a repo |
236
262
 
237
263
  ### ✻ Claude Code · [docs](https://code.claude.com/docs/en/skills)
238
264
 
239
265
  - **Where it looks.** When names collide, the first one listed wins:
240
266
  1. enterprise (managed settings)
241
- 2. `~/.claude/skills`
242
- 3. `.claude/skills`
243
- 4. nested `<subfolder>/.claude/skills`
244
- 5. plugins (as `/plugin:skill`)
245
- 6. bundled
267
+ 2. `~/.claude/skills` (`CLAUDE_CONFIG_DIR` moves it)
268
+ 3. `.claude/skills`, in the folder you start in and each parent up to the repo root
269
+ 4. claude.ai skills, from `~/.claude/skills/synced` (then they run only as `/anthropic-skills:name`)
270
+
271
+ Some skills load next to these under their own name instead of competing:
272
+ - nested `<subfolder>/.claude/skills`, once Claude touches a file there (as `/subfolder:skill`)
273
+ - plugins (as `/plugin:skill`)
274
+ - folders passed with `--add-dir`
246
275
 
247
- It also reads claude.ai skills from `~/.claude/skills/synced` and folders passed with `--add-dir`. It **doesn't read `.agents/skills`** (verified).
276
+ Your skill replaces a bundled command with the same name. Only direct child folders count, and links to skill folders work.
277
+ - It **doesn't read `.agents/skills`** (verified in its binary, October 2026). `claude import cursor` copies skills from there once; skilllib links them instead, so there is still one copy.
248
278
  - **How it uses them.** Descriptions are always in context; the full `SKILL.md` loads on `/name` or when Claude decides it's relevant.
249
279
  - `disable-model-invocation: true`: only you can run it.
250
280
  - `user-invocable: false`: only Claude can.
@@ -255,14 +285,21 @@ A skill is a folder with a `SKILL.md`. These are all the places your agents load
255
285
  - **Where it looks.**
256
286
  - Project: `.agents/skills` and `.cursor/skills`, including nested ones, which apply only to files inside them.
257
287
  - Your home folder: `~/.agents/skills` and `~/.cursor/skills`.
258
- - For compatibility: `.claude/skills`, `.codex/skills`, `~/.claude/skills` and `~/.codex/skills`.
259
- - Also marketplace plugins and Cursor's built-ins. Cloud Agents only see `~/.cursor/skills`.
288
+ - For compatibility: `.claude/skills`, `.codex/skills`, `.grok/skills` and the same three in your home folder. The setting **Include Third-Party Plugins, Skills, and Other Configs** (on by default) turns these on, and it also imports your enabled Claude Code plugins. It always uses your home folder: `CLAUDE_CONFIG_DIR` and `CODEX_HOME` don't apply. skilllib leaves `.grok/skills` alone: it's Grok's folder, and skilllib can't tell what Grok needs.
289
+ - Also marketplace plugins and Cursor's built-ins (`~/.cursor/skills-cursor`). Cloud Agents only see `~/.cursor/skills`.
290
+ - It finds every `SKILL.md` up to 10 folders deep. It skips dot folders, `node_modules`, `dist` and `build`, and Codex's bundled skill names (like `skill-creator`) under `.codex/skills`.
260
291
  - **How it uses them.** Descriptions decide relevance, and the full content loads on use; `/` runs one. `paths:` globs limit a skill to matching files, and `disable-model-invocation: true` makes it manual.
261
- - **Limits.** There's no per-project switch for global skills. Its docs don't say how it handles one skill reached through two folders.
292
+ - **Same name in several folders.** It loads the skill once, from the first of `.cursor`, `.claude`, `.codex`, `.grok`, `.agents` (project before home folder). The claude.ai copies in `~/.claude/skills/synced` count as a different skill.
293
+ - **Limits.** There's no per-project switch for global skills.
262
294
 
263
295
  ### ◎ Codex · [docs](https://learn.chatgpt.com/docs/build-skills)
264
296
 
265
- - **Where it looks.** `.agents/skills` in the working folder, its parents and the repo root; then `~/.agents/skills`; `/etc/codex/skills` (admin); and OpenAI's bundled skills. It **doesn't read `.claude/skills`**.
297
+ - **Where it looks.**
298
+ - Project: `.agents/skills` in the working folder, its parents up to the repo root, and `.codex/skills`.
299
+ - Your home folder: `~/.agents/skills`, and `~/.codex/skills` (`$CODEX_HOME/skills`). Codex's docs no longer list `~/.codex/skills`, but Codex still reads it for backward compatibility, and its built-in skill installer puts skills there (verified in its source, October 2026).
300
+ - Also `/etc/codex/skills` (admin) and OpenAI's bundled skills in `~/.codex/skills/.system`.
301
+ - It finds a `SKILL.md` up to 6 folders deep and skips dot folders. skilllib only lists direct children (`<folder>/<name>/SKILL.md`), which is where Codex's installer puts them.
302
+ - It **doesn't read `.claude/skills`**, so Claude Code and Codex share no folder.
266
303
  - **How it uses them.** Names and descriptions come first (about 2% of context); `SKILL.md` loads when used, and `$` picks one.
267
304
  - Same-name skills aren't merged.
268
305
  - `policy.allow_implicit_invocation: false` in `agents/openai.yaml` keeps a skill manual.
@@ -270,7 +307,7 @@ A skill is a folder with a `SKILL.md`. These are all the places your agents load
270
307
 
271
308
  ### ℤ Zed · [docs](https://zed.dev/docs/ai/skills)
272
309
 
273
- - **Where it looks.** `<worktree>/.agents/skills` (trusted worktrees only) and `~/.agents/skills`. Only direct child folders count, and on a name collision the project's skill wins.
310
+ - **Where it looks.** `<worktree>/.agents/skills` (trusted worktrees only) and `~/.agents/skills`, nothing else (verified in its source, October 2026). Only direct child folders count, and on a name collision the project's skill wins.
274
311
  - **How it uses them.** The agent sees a catalog of names and descriptions; `/` or `@skill` runs one. Changes apply without a restart.
275
312
 
276
313
  ---
@@ -301,10 +338,26 @@ skilllib new <name> [desc] create a skill
301
338
  skilllib usage [--days N] which skills Claude Code used
302
339
  skilllib doctor [--fix] find (and fix) problems
303
340
  skilllib restore [name] put back something skilllib moved out
341
+ skilllib agent-skill [install|remove] teach your agents to use skilllib
304
342
  skilllib --version
305
343
  ```
306
344
 
307
- Flags: `--force` (overwrite local edits), `--allow-tracked` (link into git-tracked folders), `--days N`. For `tidy`: `--dry-run` (preview), `--allow-git` (also change committed files), `<name> --keep <folder>` (the copy that wins when copies differ).
345
+ Flags: `--force` (overwrite local edits), `--allow-tracked` (link into git-tracked folders), `--days N`, `--json`. For `tidy`: `--dry-run` (preview), `--allow-git` (also change committed files), `<name> --keep <folder>` (the copy that wins when copies differ).
346
+
347
+ **`--json`** prints one line of JSON on stdout, for scripts and agents. Messages and warnings go to stderr. It works with `status`, `list`, `show`, `projects`, `outdated`, `usage`, `doctor`, `add`, `remove`, `sync`, `update`, `import` and `agent-skill`. The output is shaped to keep agents fast and cheap:
348
+
349
+ - **`status --json`** answers everything about the repo in one call:
350
+ - the repo's skills, with their source, version, state and git state
351
+ - the global skills, grouped by where they come from
352
+ - every problem skilllib found here, with its fix
353
+ - how often Claude Code used each skill here
354
+ - the repo's top-level files
355
+
356
+ Skills that share every attribute are grouped, and attributes at their usual value are left out.
357
+ - **`list --json`**: inside a repo, the library skills the repo already has (names only), and the others with the first sentence of their description.
358
+ - **`add`, `remove`, `sync` and `update`** list each change and the folders it wrote to, so there's nothing left to check.
359
+
360
+ The `skilllib` skill runs `status` and `list` as it loads (in Claude Code), so an agent usually answers "which skills can you use here?" in one step.
308
361
 
309
362
  ## Files
310
363
 
@@ -314,11 +367,12 @@ Flags: `--force` (overwrite local edits), `--allow-tracked` (link into git-track
314
367
  | `~/.skilllib/library/` | Your skills (master copies). Worth putting under git. |
315
368
  | `~/.skilllib/store/` | Every version of every skill, immutable |
316
369
  | `~/.skilllib/config.json` | Your agents, project folders, hidden projects, skills you keep global |
317
- | `~/.skilllib/trash/`, `global-backup/`, `tidy-backup/` | Everything skilllib removed, restorable from Settings › Backups |
370
+ | `~/.skilllib/trash/`, `global-backup/`, `tidy-backup/`, `edit-backup/` | Everything skilllib removed, restorable from Settings › Backups |
318
371
  | `~/.skilllib/plugin-backup.json` | Plugins skilllib uninstalled, so Settings › Backups can reinstall them |
319
372
  | `~/.skilllib/review-prompt.md` | The last review prompt you copied |
373
+ | `~/.claude/skills/skilllib/` | The skill that lets your agents use skilllib (`agent-skill install`) |
320
374
 
321
- Environment variables: `SKILLLIB_HOME` moves `~/.skilllib`, `$VISUAL` / `$EDITOR` set the editor, and `CLAUDE_CONFIG_DIR` is honored.
375
+ Environment variables: `SKILLLIB_HOME` moves `~/.skilllib`, `$VISUAL` / `$EDITOR` set the editor, and `CLAUDE_CONFIG_DIR` and `CODEX_HOME` are honored.
322
376
 
323
377
  ## FAQ
324
378
 
@@ -341,14 +395,17 @@ Environment variables: `SKILLLIB_HOME` moves `~/.skilllib`, `$VISUAL` / `$EDITOR
341
395
  pnpm install
342
396
  pnpm test && pnpm type-check && pnpm build # tests run on bun
343
397
  pnpm dev # run from source
398
+ pnpm design # render the TUI screens in docs/design
344
399
  npm link # use your checkout as `skilllib`
345
400
  ```
346
401
 
402
+ How the TUI is designed, and why: [docs/DESIGN.md](docs/DESIGN.md).
403
+
347
404
  **Releasing:**
348
405
  1. Bump `version` in `package.json` and merge to `main`.
349
406
  2. Tag and push:
350
407
  ```bash
351
- git tag v1.3.0 && git push --tags
408
+ git tag v1.6.0 && git push --tags
352
409
  ```
353
410
 
354
411
  CI then tests on Linux, macOS and Windows, publishes to npm through [trusted publishing](https://docs.npmjs.com/trusted-publishers) (no token; provenance is automatic), and creates a GitHub release.