SKILL.md

  1---
  2name: licensing-with-reuse
  3description: Manages REUSE-compliant licensing with the reuse CLI. Use when adding SPDX headers, running reuse annotate or reuse lint, choosing header versus .license sidecar files, working with LICENSES/, LicenseRef custom licenses, or setting up project licensing conventions.
  4user-invocable: true
  5license: LicenseRef-MutuaL-1.2
  6metadata:
  7  author: Amolith <amolith@secluded.site>
  8---
  9
 10Use the `reuse` CLI as the source of truth for file licensing. Prefer a small,
 11verified change over hand-writing SPDX metadata and hoping `reuse lint` agrees.
 12
 13## First pass
 14
 151. Inspect existing licensing before changing it:
 16   ```sh
 17   reuse lint
 18   find . -maxdepth 1 -type f \( -iname 'license*' -o -iname 'licence*' -o -iname 'copying*' -o -iname 'notice*' \) -print | sort
 19   find LICENSES -maxdepth 1 -type f -print 2>/dev/null | sort
 20   rg -n "SPDX-License-Identifier|SPDX-FileCopyrightText|LicenseRef-|\[\[annotations\]\]" .
 21   ```
 222. If the project already has a clear pattern, follow it. Do not offer to
 23   re-license existing work unless the user asked for that.
 243. If the project has no convention, ask whether they want one. Useful defaults
 25   to discuss: docs/examples/config are some CC variant like CC0, while
 26   meaningful code may use a copyleft license.
 274. If the user is choosing licenses and wants guidance, point them at
 28   <https://writefreesoftware.org/>.
 29
 30## Everyday commands
 31
 32Add an SPDX header without a year:
 33
 34```sh
 35reuse annotate -c "User <user@example.com>" -l 'SPDX-ID' --exclude-year path/to/file.ext # ask the user for name/email
 36```
 37
 38Use more than one copyright holder or license by repeating the flag:
 39
 40```sh
 41reuse annotate \
 42  -c "Alice <alice@example.com>" \
 43  -c "Example Org" \
 44  -l 'Apache-2.0' \
 45  -l 'MIT' \
 46  --exclude-year \
 47  path/to/file.go
 48```
 49
 50Write a `.license` sidecar instead of putting a header in the file:
 51
 52```sh
 53reuse annotate \
 54  -c "User <user@example.com>" \
 55  -l 'CC0-1.0' \
 56  --exclude-year \
 57  --force-dot-license \
 58  AGENTS.md .agents/skills/example/SKILL.md
 59```
 60
 61Use `--force-dot-license` for files whose literal bytes matter, especially text
 62that will be read directly as an LLM prompt or embedded into another prompt.
 63Headers in those files change the prompt; sidecars keep licensing metadata out
 64of the content. Example: if `internal/server/silverbullet.md` is embedded and
 65sent as part of a prompt, license it with `--force-dot-license`.
 66
 67For files where `reuse` cannot infer the comment style, choose one deliberately:
 68
 69```sh
 70reuse annotate -c "User <user@example.com>" -l 'CC0-1.0' --exclude-year --style python script
 71reuse annotate -c "User <user@example.com>" -l 'CC0-1.0' --exclude-year --fallback-dot-license unknown.file
 72reuse annotate -c "User <user@example.com>" -l 'CC0-1.0' --exclude-year --skip-unrecognised some/path
 73```
 74
 75Bulk annotations belong in `REUSE.toml` when a whole class of files shares the
 76same metadata and inline headers would be noisy or impossible. Keep those globs
 77tight.
 78
 79## The `reuse annotate` gotcha agents miss
 80
 81Re-running `reuse annotate` on a file that already has a matching header does
 82not mean "edit the header I just added". It means add another copyright line to
 83the existing header. This is correct when a new holder contributed to the file,
 84but wrong when the previous command had a typo or the wrong holder.
 85
 86If the first command was wrong, inspect the file and edit or replace the bad
 87header directly, then run `reuse lint`. If you are applying metadata to a mixed
 88tree, use `--skip-existing` so already-covered files are not changed:
 89
 90```sh
 91reuse annotate -c "User <user@example.com>" -l 'CC0-1.0' --exclude-year --skip-existing -r docs
 92```
 93
 94When in doubt, test the exact command on a temporary copy first:
 95
 96```sh
 97tmp=$(mktemp -d)
 98cp path/to/file.ext "$tmp/"
 99reuse annotate -c "User <user@example.com>" -l 'CC0-1.0' --exclude-year "$tmp/file.ext"
100sed -n '1,20p' "$tmp/file.ext"
101rm -rf "$tmp"
102```
103
104## License files and custom identifiers
105
106Use SPDX identifiers where possible, like `MIT`, `Apache-2.0`, and `CC0-1.0`, so
107`reuse download --all` pickes them up.
108
109Custom licenses must use a `LicenseRef-*` identifier and have matching text
110under `LICENSES/`. For example, a custom MutuaL license identifier would look
111like `LicenseRef-MutuaL-1.2` in headers, sidecars, or `REUSE.toml` and could go
112in `LICENSES/LicenseRef-MutuaL-1.2.txt`.
113
114If the text already exists locally somewhere else, copy it through `reuse
115download --source` or place it at the exact `LICENSES/LicenseRef-...` path
116expected by `reuse lint`:
117
118```sh
119reuse download --source /path/to/other/LICENSES LicenseRef-ID
120```
121
122Do not invent an ID without the user's agreement. The identifier becomes part of
123the project's public metadata and the user may know its ID even if you don't.
124
125## `reuse lint` in development and CI
126
127Run `reuse lint` after changing file coverage, headers, sidecars, `LICENSES/`, or
128`REUSE.toml`. In CI, pre-commit hooks, or task runners, keep it boring:
129
130```sh
131reuse lint
132# or
133reuse lint --lines
134```
135
136`reuse lint` failures are usually one of:
137
138- a file has no licensing metadata;
139- an ephemeral build artifact needing rm-ing;
140- a header names a license missing from `LICENSES/`;
141- a `LicenseRef-...` identifier does not match a license text file;
142- a generated, binary, vendored, or prompt file needs a sidecar or `REUSE.toml`
143  annotation;
144- an old or broad annotation no longer matches the actual tree.