npm package

commits-to-changelog

Create an unopionated CHANGELOG.md from Git commit history (see Details)

hh lohmann <hh.lohmann@gmail.com>

Changelog

Last 5 changes - see CHANGELOG file for full list and details

Synopsis

CLI without parameters

commits-to-changelog

Parameters

no parameters

Settings

Default settings can be overwritten by key-value pairs in an object as value for a key “commits-to-changelog” in a package.json belonging to the repo for which a CHANGELOG.md should be created, e.g.

// package.json
{
  "version": "...",
  "commits-to-changelog": {
    "headerDefault": "Latest",
    "linesToReadme": 5
  },
  "dependencies": {
    "...": "..."
  }
}

Possible Settings

commitMoveTag

Boolean: Auto-commit CHANGELOG.md and move tag to include CHANGELOG.md in the tag’s range (see Details)

defaultDateToday

Boolean: If commits without tags are allowed (see requireTag): Use current date instead of commit date for grouping commits without tag

filterCommits

Array of RegExp: Filter out commits / commit types if commit message matches a RegExp in the array

filterDefaults

Boolean: Filter out commit types that are rather not relevant for users by matching commit messages against RegExps /^bump version$/i, /^changelog$/i, /^dev:/i, /^[Hh]ousekeeping/i, /^planning/i, /[Rr]efactoring/i, /tests/i

headerDefault

String to use as header for listing commits that do not belong to a defined Git tag

linesToReadme

Number: Write defined number of lines from the start of CHANGELOG.md also to an existing section with heading “Changelog” (or “CHANGELOG” or any preferred case) in README.md

Boolean: Create CHANGELOG.md with reference-style links / link references (see Details)

requireTag

Boolean: Reject creating a Changelog if commits without associated Git tag exist

useDateGroups

Use commit date to group commits (additionally to tags)

useNotes

Boolean: Display also Git notes (if existing)

Returns

no return

Examples

Sample CHANGELOG.md

See the CHANGELOG.md of this project

Sample for optionally writing to a section “Changelog” in README.md

See the section Changelog in this file (cf. details for optional setting linesToReadme under Settings)

Dependencies

none

Installation

CLIs should be installed systemwide (“global”). Strip off the -g parameter or replace it by a -D (as development dependency, -d for Bun) to explicitly restrict to a repo bounded usage.

Pick for your preferred package manager:

  npm i -g commits-to-changelog
  pnpm i -g commits-to-changelog
  bun i -g commits-to-changelog
  # For Yarn you should double check docs for your and / or
  # current Yarn version, newer versions do not treat `i package_name`
  # as an alias for `add ...` and exclude global installations
  yarn add commits-to-changelog

Details

The resulting CHANGELOG.md has the simple structure

# Changelog

## {groupheader} ({date})

- [{commit-subject}][{commit-hash}]
- [{commit-subject}][{commit-hash}]

## {groupheader} ({date})

- [{commit-subject}][{commit-hash}]
- [{commit-subject}][{commit-hash}]

(...)

[{commit-hash}]: {commit-link}
[{commit-hash}]: {commit-link}
[{commit-hash}]: {commit-link}
[{commit-hash}]: {commit-link}

(...)

where # Changelog is the title, a Markdown atx heading (i.e. using “#”) of level 1 with the text “Changelog”, followed by an empty line, and lists of commits that are grouped by

so that the applicable Git tag / package.json version or the headerDefault becomes the {groupheader} that together with the date of the newest commit in the group constitutes a Markdown heading of level 2 under which associated commits are listed as

If your workflow allows commits without tags (see setting requireTag) then you can opt with setting defaultDateToday to use the current date for commits without tags instead the newest commit’s date.

With setting useDateGroups you can additionally group by date, distinguished from tag based grouping by groupheader in italics, e.g.

# Changelog

## {groupheader} ({date})

- [{commit-subject}][{commit-hash}]
- [{commit-subject}][{commit-hash}]

## *{date}*

- [{commit-subject}][{commit-hash}]
- [{commit-subject}][{commit-hash}]

(...)

[{commit-hash}]: {commit-link}
[{commit-hash}]: {commit-link}
[{commit-hash}]: {commit-link}
[{commit-hash}]: {commit-link}

(...)

Git tags do not need to have any special structure or orderings, they could be natural numbers as well as SemVers, ISO dates, CalVer, arbitrary names or any mixture like that used by DokuWiki, they are generally just “tags” in the most verbatim sense, giving the information you may regard as helpful to track changes - the order in the CHANGELOG.md always depends on that of the listed Git commits, not on any tagging scheme. You may choose a scheme that allows to integrate a CHANGELOG.md creation into an overall workflow like setting first a non-labeled SemVer version in package.json and derive release tags from this (see above).

If multiple Git tags exist on the same commit (for whatever reason), then the {groupheader} will be a sorted list of all tags separated by /, e.g. commits like

b6f8f5c (tag: fix-that, tag: feat-this) Fix: ...this...
0c6ec5e Feature: ...that...

will appear in CHANGELOG.md as

## feat-this / fix-that (...date...)

- [Fix: ...that...](...hash...)
- [Feature: ...this...](...hash...)

Git tags may be lightweight or annotated, i.e. the type of a tag has no influence on the resulting CHANGELOG.md.

Besides the existence and characteristics of Git tags, a possible package.json and Git remote defintions the actually resulting CHANGELOG.md can be shaped by Settings.

By default the freshly created CHANGELOG.md will be auto-committed and the latest tag it covers will be moved to the commit connected to the creation of CHANGELOG.md so that the CHANGELOG.md will automatically be a part of that what it describes, e.g. a relase based on the latest tag, so that you will have a history

3ab6fe2 (tag: 3.0.0) changelog
f3c32ba done everything
2bbccfe done that
9a31617 done this

instead of

3ab6fe2 changelog
f3c32ba (tag: 3.0.0) done everything
2bbccfe done that
9a31617 done this

Depending on linesToReadme a README.md with updated section ‘Changelog’ will auto-committed together with CHANGELOG.md.

Use setting commitMoveTag to skip auto-committing / tag moving and do things manually or by other means instead.

Deprecations

Source Code

Prior Work

The (initial) code here is forked from git-to-changelog, an already very good solution, but due to a hardwired search path ‘../../package.json’ - mimicking npm’s way of structuring a node_modules folder - not usable with pnpm, and while fixing this some other little things were changed / improved (see CHANGELOG) and made the initial little fix grow into an own project

License

References

CalVer

CommonMark Spec: ATX headings

Conventional Commits

DokuWiki Changelog

Flowing Code: Commit Message Guidelines

Git commit subject

Git: diff

Git: lightweight vs. annotated tags

Git notes

Git: Working with Remotes: Showing Your Remotes

git-to-changelog

Non-labeled SemVer

Endspacer: './markdown-assets/endspacer.png' missing - see https://hh-lohmann.github.io/html-endspacer
[top]