New in Symplify 5: Generate Rich, Precise and Smart Changelog in Seconds

Found a typo? Edit me
This post is deprecated since March 2021. Its knowledge is old and should not be used.

ChangelogLinker is now deprecated, because it has same features as GitHub pull-request overview with no added value. See this issue in detail. Use lob/generate-changelog or github-changelog-generator instead or better switch to GitHub releases.

ChangelogLinker started as a small tool to complete links to PRs, authors, and versions in Then it started to generate the

Where is now and how to start using it?

Tested on Humans ✅

See pull-request #446 on Shopsys

"If you're not embarrassed by the first version of your product,
you've launched too late."

The first version of any software is how the author(s) think people will use it. It's like trying to see the future of people you've never met. That's why the first version is better done than perfect. The important part is to collect feedback as soon as possible and improve based on it.

Saying that I recommended ChangelogLinker to Shopsys to manage news in their monorepo. In exchange, I got informative and clear feedback with creative ideas on how to solve it from Rostislav Vitek and Petr Heinz. Huge thanks for making this tool better belongs to you guys.

First, install this package:

composer require symplify/changelog-linker --dev

1. Multiple for Smaller Versions

See pull-request #1047

If you have more than 2 major versions, your changelog can be really long and hard to orientate. Some people want to see the news in your version 3, some are still using version 1 and need to upgrade gradually.

I got this inspiration from Symfony, where they have *own CHANGELOG per minor versions:

Good idea to keep files not huge and clear. So Now it's possible to work with each CHANGELOG file separately - just use file path as the first argument of any command:

vendor/bin/changelog-linker link # "" is used
vendor/bin/changelog-linker link
vendor/bin/changelog-linker link

2. Smarter Last Change Detection

See commit

This package generates changelog from merged PRs, that are not mentioned in your yet.

vendor/bin/changelog-linker dump-merges

Before it looks for the highest merged PR ID and added only PRs with higher id. But what if you merge PR with number 1000, but number 990 is still opened due to longer code review?

Now it works with the merged_at instead, so no merged PR is left behind.

See pull-request #1045

This is the best command to start with when you install this package for the first time. can be edited, items removes, shifter above or links duplicated. To keep it fit and slim, you'd have to check this manually with every link. And believe me, if you have 500+ PRs, 50+ contributors and 30+ versions, it's not as fun as you imagine.

That's where "cleanup" rocks:

vendor/bin/changelog-linker cleanup

# again, you can use the file as argument
vendor/bin/changelog-linker cleanup

In Symplify itself it removed 50 dead lines.

4. Improved Category Detection

See pull-request #1064

Thanks to Petr Heinz ❤️️

When you generate a you can use --in-categories option:

vendor/bin/changelog-linker dump-merges --in-categories

It will assign PRs to one of 4 categories: Added, Fixed, Changed and Removed. I didn't make them up, it's a standard taken from

How it works? It uses regex to detect keywords in the pull-request title, e.g.

Added "cleanup" command → Added Remove dead links → Removed Fix ID detection → Fixed

You can see all the regexes in CategoryResolver.

Peter added many keywords, but also showed me a new trick : the \b wrapper:

-private const ADDED_PATTERN = '#(add|added|adds) #i';
+private const ADDED_PATTERN = '#\b(add(s|ed|ing)?)\b#i';

It means, that words need to be standalone. Not part of any other string. Regex \b(is)\b applied to "This island is beautiful" returns ["is"].

A very nice trick that made detection much more precise. Thanks, Peter!

Happy changing!

Have you find this post useful? Do you want more?

Follow me on Twitter, RSS or support me on GitHub Sponsors.