This repository has some handy instructions on contributing to my open-source projects.
I do not outright ban the use of LLMs in contributions to my projects. However (and note that this applies to bug reports, pull requests, security notices, discussions, and anything else):
- If you use LLMs, I expect you to not only meet but exceed the quality standards that hold for other contributors. It's a burden to evaluate whether LLM-related contributions are even worth the time to read (they usually aren't), and you need to make up for this in the quality of your own work.
- You must understand everything you submit. There is absolutely no
excuse for submitting any code, documentation, or discussion comment
that you do not personally understand and can explain (yourself -
not asking an LLM to generate an explanation).
- With human contributions, there is some leeway in terms of "I found this workaround, I don't understand why it works, but it might be helpful". With LLMs, this leeway does not exist; it's an incredible drag to sort through LLM-generated bad ideas and hypotheticals.
- Your work must not degrade the development and contribution experience for other people who don't use LLMs. Do not introduce code that will be a nuisance to maintain by hand, on the assumption that everyone else will be using LLMs too.
- By submitting work, you are certifying that you hold the sole copyright to that work and that you have the sole authority to release it under the license of the project you are contributing to. Mentioning that an LLM was involved does not absolve you of this legal responsibility. If the use of an LLM means you are unable to legally attest that you own the full copyright to your contribution, then you cannot use that LLM.
Most of my projects include automated linters to improve code quality.
Run them locally with make lint. Typically this will do the
following:
- Check for no byte-compiler warnings.
- Run Checkdoc.
- Check for no lines longer than 79 characters. Why 79?
- Check that the code is indented correctly.
- Update the table of contents in the README. Please install markdown-toc for this to work!
The linters are run automatically against your pull request by GitHub Actions. All pull requests must pass CI before being merged.
One reason the CI can fail even though make lint worked for you is
that your code doesn't work in an older version of Emacs. CircleCI
runs the linters against every supported version of Emacs. You can do
the same by installing Docker and running
make docker VERSION=25.3 (or equivalently for whatever version is of
interest). That will put you in a shell with the project source code
and all dependencies automatically installed in a sandbox.
We write documentation. Every symbol, public or private, needs a
docstring which is enough to fully understand the behavior without
inspecting the source code. Every public symbol (the ones without --
in their name) needs furthermore to be explained in the README.
We also write changelogs (in most projects; unfortunately
straight.el doesn't have one yet). The changelog is kept in
CHANGELOG.md.
The idea of the changelog is to document user-visible changes to the project in a user-readable way (unlike the commit history, which is much more detailed and hard to read).
Here is a changelog in progress:
## Unreleased
### Enhancements
* In `read-file-name`, when a default is provided (for example in the
`dired-do-rename` command), we actually use it as the initial
contents of the minibuffer, which allows you to have convenient
access to the default filename when that default file does not exist
([#25]).
* We now bind `minibuffer-completing-file-name` during
`read-file-name`, in conformance with the standard Emacs interface
([#30]).
## Bugs fixed
* You can now use the undo system in the minibuffer. Previously,
trying to do so would break Selectrum ([#31]).
[#25]: https://github.com/raxod502/selectrum/pull/25
[#30]: https://github.com/raxod502/selectrum/issues/30
[#31]: https://github.com/raxod502/selectrum/issues/31Notice:
- There's a section called
Unreleasedwhere all the info goes. When I make a release, I relabel the section with the name of the release and copy it into the GitHub release. After the release, we add in a newUnreleasedsection at the top. - We have sub-sections for the different types of changes. There
aren't any strict rules about which sub-sections should be used, but
here are some suggestions:
Breaking changes,Added,Enhancements,Deprecated,Removed,Bugs fixed,Performance. - Each change goes in a new bullet point, and includes a link to the
relevant issue(s) or pull request(s) in parentheses. The link
anchors go at the bottom of the
Unreleasedsection, in alphabetical order.
What to include in the changelog: Any user-visible changes since the last release. Changes to the implementation of an internal function don't qualify, unless they fix a bug or improve performance significantly. Also, if you fix a bug that was introduced since the last release, there's no need to document that. The audience of a changelog should be assumed to be running the last release.
Example changelogs: