| name | intentional-commits |
|---|---|
| description | Produce a clean, intentional, and reviewable commit history with stable, logically scoped commits |
Use this skill when the user wants help creating, cleaning up, reviewing, or enforcing commit history quality.
This skill applies to:
- writing commit subjects
- writing commit descriptions
- deciding whether changes should be split across multiple commits
- reviewing a branch for commit hygiene
- preparing a branch for merge or PR review
Produce a clean, intentional, and highly reviewable commit history. Each commit should represent a stable, logical unit of progress with clear intent.
- Work in small, deliberate steps. Avoid large or mixed-purpose commits.
- Each commit must leave the application in a stable, working state.
- Each commit should represent one clear unit of progress.
- Separate refactors from behavior changes whenever possible.
- Do not introduce temporary or broken states between commits.
- Use plain English, no prefixes.
- Use present tense.
- Be concise but specific about what changed.
- Avoid vague subjects like
update,cleanup,misc fixes, orrefactor code.
Examples:
Introduce PreviewRequest model and persistence structurePersist product association on preview requestsRename preview acknowledgement endpoint for clarity
- Keep it concise and skimmable.
- Clearly explain what changed.
- Clearly explain why it changed.
- Clearly explain how it moves the overall work forward.
- Use short paragraphs or bullets when helpful.
- Avoid filler or repeating the subject line without adding meaning.
Template:
<What changed>
<Why it changed>
<How this moves the work forward>
- A reviewer should be able to understand and validate each commit in isolation.
- Commits should build logically on one another.
- Avoid end-of-branch cleanup commits when the cleanup belongs in an earlier commit.
- Make dependencies between commits obvious.
- Prefer commits that can be reviewed in a few minutes.
- Split preparatory compatibility fixes from behavior changes whenever the preparatory work can stand on its own.
- If a change introduces a schema bridge, accessor, rename shim, null-safety guard, or legacy-data fallback, presume that belongs in its own commit unless the app would be broken without merging it with the behavior change.
- If a single file contains multiple concerns, do not use the shared file as a reason to compress the history. Use partial staging, temporary reverts, or a short intermediate edit to keep commit boundaries clean.
- Prefer this sequence when applicable:
- Normalize or bridge existing schema/code shape.
- Change persistence or core behavior.
- Add read-path hardening or compatibility fallback for legacy data.
- Add regression tests.
Reject or split commits that combine:
- a compatibility/accessor shim with the feature that starts depending on it
- a persisted identity change with unrelated report/export hardening
- legacy-data null handling with the main write-path behavior change
- tests with unrelated refactors or cleanup
- multiple reviewer questions hidden inside one “it all supports the same bugfix” commit
If a bugfix requires all of the following:
- introducing a compatibility accessor because the code uses one field name but the database still stores another
- changing writes to persist a real foreign key instead of looking records up indirectly
- making a report tolerate legacy rows that still do not have the new foreign key
- adding regression tests
then prefer four commits:
- Normalize the existing schema or model shape.
- Change the write path or core behavior.
- Harden reads or reports for legacy data.
- Add regression coverage.
Do not collapse these into one “fix bug X” commit just because they all contribute to the same outcome. A reviewer should be able to answer one main question per commit.
- Prefer dedicated commits for refactors.
- Keep renames, moves, and structural cleanup separate from behavior changes when possible.
- If a refactor and behavior change must be combined, explicitly call both out in the description.
- Do not hide behavior changes inside broad refactors.
Before committing, classify each hunk into one of these buckets:
- compatibility or schema bridge
- core behavior change
- compatibility hardening or fallback
- regression coverage
If a commit would mix buckets, stop and try to split it. Only keep buckets together when a separate commit would leave the app broken or misleading.
When a split is possible but awkward because changes share a file, prefer the more reviewable history over convenience.
- Never leave the application in a broken state between commits.
- Never commit partially wired work that cannot reasonably run or be reviewed.
- Use scaffolding, feature flags, adapters, or no-op implementations when needed to preserve stability.
- Favor incremental transitions over big-bang rewrites.
- Reject commits that combine unrelated concerns.
- Reject commits that leave the app in a broken or partially implemented state.
- Reject vague commit subjects.
- Require descriptions for all non-trivial commits.
- Split commits automatically when multiple distinct concerns are detected.
- Rewrite commit subjects and descriptions when they are unclear, weak, or non-reviewable.
- Do not create
cleanupcommits if the cleanup belongs with the original change. - Do not create
wipcommits. - Do not create commits whose intent cannot be understood without external explanation.
- Does this commit represent a single clear idea?
- Is the application stable after this commit?
- Can a reviewer understand why this exists without extra context?
- Is anything unrelated included that should be split out?
- Is the subject clear, specific, and free of prefixes?
- Does the description explain what changed, why, and how it moves the work forward?
- Review the full commit history before finishing.
- Reorder, squash, split, or rewrite commits to improve clarity.
- Ensure the final history reads like a step-by-step narrative of the work.
Source: https://gist.github.com/justenh/d0022c9fc48a3a7fbb557d5dce6f72c8