Configuration
git-cliff configuration file supports TOML (preferred) and YAML formats.
The configuration file is read from $HOME/git-cliff/cliff.toml
if the file exists. This location depends on the platform, for example:
- on Linux:
/home/<user>/.config/git-cliff/cliff.toml
- on Windows:
C:\Users\<user>\AppData\Roaming\git-cliff\cliff.toml
- on macOS:
/Users/<user>/Library/Application Support/git-cliff/cliff.toml
See cliff.toml for the default configuration values.
changelog
This section contains the configuration options for changelog generation.
[changelog]
header = "Changelog"
body = """
{% for group, commits in commits | group_by(attribute="group") %}
### {{ group | upper_first }}
{% for commit in commits %}
- {{ commit.message | upper_first }}
{% endfor %}
{% endfor %}
"""
trim = true
footer = "<!-- generated by git-cliff -->"
header
Header text that will be added to the beginning of the changelog.
body
Body template that represents a single release in the changelog.
See templating for more detail.
trim
If set to true
, leading and trailing whitespace are removed from the body
.
It is useful for adding indentation to the template for readability, as shown in the example.
footer
Footer text that will be added to the end of the changelog.
git
This section contains the parsing and git related configuration options.
[git]
conventional_commits = true
filter_unconventional = true
split_commits = false
commit_parsers = [
{ message = "^feat", group = "Features"},
{ message = "^fix", group = "Bug Fixes"},
{ message = "^doc", group = "Documentation"},
{ message = "^perf", group = "Performance"},
{ message = "^refactor", group = "Refactor"},
{ message = "^style", group = "Styling"},
{ message = "^test", group = "Testing"},
]
protect_breaking_commits = false
filter_commits = false
tag_pattern = "v[0-9]*"
skip_tags = "v0.1.0-beta.1"
ignore_tags = ""
topo_order = false
sort_commits = "oldest"
link_parsers = [
{ pattern = "#(\\d+)", href = "https://github.com/orhun/git-cliff/issues/$1"},
{ pattern = "RFC(\\d+)", text = "ietf-rfc$1", href = "https://datatracker.ietf.org/doc/html/rfc$1"},
]
limit_commits = 42
conventional_commits
If set to true
, commits are parsed according to the Conventional Commits specifications.
The Conventional Commits specification is a lightweight convention on top of commit messages. It provides an easy set of rules for creating an explicit commit history; which makes it easier to write automated tools on top of. This convention dovetails with SemVer, by describing the features, fixes, and breaking changes made in commit messages.
The commit message should be structured as follows:
<type>[optional scope]: <description>
[optional body]
[optional footer(s)]
e.g. feat(parser): add ability to parse arrays
filter_unconventional
If set to true
, commits that are not conventional are excluded. This option can be used to generate changelogs with conventional and unconventional commits mixed together. For example:
conventional_commits = true
filter_unconventional = false
commit_parsers = [
{ message = ".*", group = "Other", default_scope = "other"},
]
With the configuration above, conventional commits are parsed as usual and unconventional commits will be also included in the changelog as "Other".
To completely exclude unconventional commits from the changelog:
# default behaviour
conventional_commits = true
filter_unconventional = true
To include any type of commit in the changelog without parsing:
conventional_commits = false
filter_unconventional = false
split_commits
This flag violates "conventional commits". It should remain off by default if conventional commits is to be respected.
If set to true
, each line of a commit is processed individually, as if it were its own commit message. This may cause
a commit to appear multiple times in a changelog, once for each match.
conventional_commits = true
filter_unconventional = true
split_commits = true
commit_parsers = [
{ message = "^feat", group = "Features"},
]
With the configuration above, lines are parsed as conventional commits and unconventional lines are omitted.
If filter_unconventional = false
, every line will be processes as an unconventional commit, resulting in each line of
a commit being treated as a changelog entry.
commit_preprocessors
An array of commit preprocessors for manipulating the commit messages before parsing/grouping them. These regex-based preprocessors can be used for removing or selecting certain parts of the commit message/body to be used in the following processes.
Examples:
{ pattern = "foo", replace = "bar"}
- Replace text.
{ pattern = 'Merged PR #[0-9]: (.*)', replace = "$1"}
- Remove prefix.
{ pattern = " +", replace = " "}
- Replace multiple spaces with a single space.
{ pattern = "\\(#([0-9]+)\\)", replace = "([#${1}](https://github.com/orhun/git-cliff/issues/${1}))"}
- Replace the issue number with the link.
{ pattern = "https://github.com/[^ ]/issues/([0-9]+)", replace = "[Issue #${1}]"}
- Replace the issue link with the number.
{ pattern = "Merge pull request #([0-9]+) from [^ ]+", replace = "PR # [${1}](https://github.com/orhun/git-cliff/pull/${1}):"}
- Hyperlink PR references from merge commits.
{ pattern = "https://github.com/orhun/git-cliff/commit/([a-f0-9]{7})[a-f0-9]*", replace = "commit # [${1}](${0})"}
- Hyperlink commit links, with short commit hash as description.
{ pattern = "([ \\n])(([a-f0-9]{7})[a-f0-9]*)", replace = "${1}commit # [${3}](https://github.com/orhun/git-cliff/commit/${2})"}
- Hyperlink bare commit hashes like "abcd1234" in commit logs, with short commit hash as description.
Custom OS commands can also be used for modifying the commit messages:
{ pattern = "foo", replace_command = "pandoc -t commonmark"}
This is useful when you want to filter/encode messages using external commands. In the example above, pandoc is used to convert each commit message that matches the given pattern
to the CommonMark format.
A more fun example would be reversing each commit message:
{ pattern = '.*', replace_command = 'rev | xargs echo "reversed: $@"' }
$COMMIT_SHA
environment variable is set during execution of the command so you can do fancier things like reading the commit itself:
{ pattern = '.*', replace_command = 'git show -s --format=%B $COMMIT_SHA' }
commit_parsers
An array of commit parsers for determining the commit groups by using regex.
Examples:
{ message = "^feat", group = "Features"}
- Group the commit as "Features" if the commit message (description) starts with "feat".
{ body = ".*security", group = "Security"}
- Group the commit as "Security" if the commit body contains "security".
{ message = '^fix\((.*)\)', group = 'Fix (${1})' }
- Use the matched scope value from the commit message in the group name.
{ message = ".*deprecated", body = ".*deprecated", group = "Deprecation"}
- Group the commit as "Deprecation" if the commit body and message contains "deprecated".
{ message = "^revert", skip = true}
- Skip processing the commit if the commit message (description) starts with "revert".
{ message = "^doc", group = "Documentation", default_scope = "other"},
- If the commit starts with "doc", group the commit as "Documentation" and set the default scope to "other". (e.g.
docs: xyz
will be processed asdocs(other): xyz
)
- If the commit starts with "doc", group the commit as "Documentation" and set the default scope to "other". (e.g.
{ message = "(www)", scope = "Application"}
- If the commit contains "(www)", override the scope with "Application". Scoping order is: scope specification, conventional commit's scope and default scope.
protect_breaking_commits
If set to true
, any breaking changes will be protected against being skipped
due to any commit parser.
filter_commits
If set to true
, commits that are not matched by commit_parsers
are filtered out.
tag_pattern
A glob pattern for matching the git tags.
e.g. It processes the same tags as the output of the following git command:
git tag --list 'v[0-9]*'
skip_tags
A regex for skip processing the matched tags.
ignore_tags
A regex for ignore processing the matched tags.
While skip_tags
drop commits from the changelog, ignore_tags
include ignored commits into the next tag.
topo_order
If set to true
, tags are processed in topological order instead of chronological.
This can also be achieved by using the --topo-order
command line flag.
sort_commits
Sort the commits inside sections by specified order.
Possible values:
oldest
newest
This can also be achieved by specifying the --sort
command line argument.
link_parsers
An array of link parsers for extracting external references, and turning them into URLs, using regex.
Examples:
{ pattern = "#(\\d+)", href = "https://github.com/orhun/git-cliff/issues/$1"}
- Extract all GitLab issues and PRs and generate URLs linking to them. The link text will be the matching pattern.
{ pattern = "RFC(\\d+)", text = "ietf-rfc$1", href = "https://datatracker.ietf.org/doc/html/rfc$1"}
,- Extract mentions of IETF RFCs and generate URLs linking to them. It also rewrites the text as "ietf-rfc...".
limit_commits
limit_commits
is a optional positive integer number that limits the number of included commits in the generated changelog.
limit_commits
is not part of the default configuration.
Environment Configuration Overrides
It's possible to use environment variables to override configuration elements. If an environment variable matches a configuration element, the variable's value will be used instead of the element's.
Format:
[PREFIX]__[CONFIG SECTION]__[FIELD NAME]
Examples
To override the footer
element:
export GIT_CLIFF__CHANGELOG__FOOTER="<!-- footer from env -->"
To override the ignore_tags
element:
export GIT_CLIFF__GIT__IGNORE_TAGS="v[0-9]+.[0-9]+.[0-9]+-rc[0-9]+"