You've already forked goreleaser
							
							
				mirror of
				https://github.com/goreleaser/goreleaser.git
				synced 2025-10-30 23:58:09 +02:00 
			
		
		
		
	feat: changelog group improvements (#3203)
This changes the changelog grouping feature a bit: it evaluates the groups in the order they are declared in the config file, but renders them following their `order` attribute. This allows to have better filters, for instance, you might want to have dependabot commits in another section, which does not need a high priority in the changelog output, but does when evaluating, as it might share the words with other groups: in goreleaser's case, the `feat` prefix. Giving that Go's regex seems to don't allow negative look-aheads (which would help in this particular case), this seems like a good quality of life improvement. Signed-off-by: Carlos A Becker <caarlos0@users.noreply.github.com>
This commit is contained in:
		
				
					committed by
					
						 GitHub
						GitHub
					
				
			
			
				
	
			
			
			
						parent
						
							83e40717de
						
					
				
				
					commit
					b3fcc54a32
				
			| @@ -52,17 +52,21 @@ changelog: | ||||
|     - Merge branch | ||||
|     - go mod tidy | ||||
|   groups: | ||||
|     - title: 'New Features and updates' | ||||
|     - title: Dependency updates | ||||
|       regexp: "^.*feat\\(deps\\)*:+.*$" | ||||
|       order: 300 | ||||
|     - title: 'New Features' | ||||
|       regexp: "^.*feat[(\\w)]*:+.*$" | ||||
|       order: 0 | ||||
|       order: 100 | ||||
|     - title: 'Bug fixes' | ||||
|       regexp: "^.*fix[(\\w)]*:+.*$" | ||||
|       order: 10 | ||||
|       order: 200 | ||||
|     - title: 'Documentation updates' | ||||
|       regexp: "^.*docs[(\\w)]*:+.*$" | ||||
|       order: 20 | ||||
|       order: 400 | ||||
|     - title: Other work | ||||
|       order: 999 | ||||
|       order: 9999 | ||||
|  | ||||
|  | ||||
|  | ||||
| dockers: | ||||
|   | ||||
| @@ -95,6 +95,12 @@ func (Pipe) Run(ctx *context.Context) error { | ||||
| 	return os.WriteFile(path, []byte(ctx.ReleaseNotes), 0o644) //nolint: gosec | ||||
| } | ||||
|  | ||||
| type changelogGroup struct { | ||||
| 	title   string | ||||
| 	entries []string | ||||
| 	order   int | ||||
| } | ||||
|  | ||||
| func formatChangelog(ctx *context.Context, entries []string) (string, error) { | ||||
| 	newLine := "\n" | ||||
| 	if ctx.TokenType == context.TokenTypeGitLab || ctx.TokenType == context.TokenTypeGitea { | ||||
| @@ -115,14 +121,15 @@ func formatChangelog(ctx *context.Context, entries []string) (string, error) { | ||||
| 	} | ||||
|  | ||||
| 	log.Debug("grouping entries") | ||||
| 	groups := ctx.Config.Changelog.Groups | ||||
|  | ||||
| 	sort.Slice(groups, func(i, j int) bool { return groups[i].Order < groups[j].Order }) | ||||
| 	for _, group := range groups { | ||||
| 		items := make([]string, 0) | ||||
| 	var groups []changelogGroup | ||||
| 	for _, group := range ctx.Config.Changelog.Groups { | ||||
| 		item := changelogGroup{ | ||||
| 			title: group.Title, | ||||
| 			order: group.Order, | ||||
| 		} | ||||
| 		if group.Regexp == "" { | ||||
| 			// If no regexp is provided, we purge all strikethrough entries and add remaining entries to the list | ||||
| 			items = filterAndPrefixItems(entries) | ||||
| 			item.entries = filterAndPrefixItems(entries) | ||||
| 			// clear array | ||||
| 			entries = nil | ||||
| 		} else { | ||||
| @@ -133,18 +140,22 @@ func formatChangelog(ctx *context.Context, entries []string) (string, error) { | ||||
| 			for i, entry := range entries { | ||||
| 				match := regex.MatchString(entry) | ||||
| 				if match { | ||||
| 					items = append(items, li+entry) | ||||
| 					item.entries = append(item.entries, li+entry) | ||||
| 					// Striking out the matched entry | ||||
| 					entries[i] = "" | ||||
| 				} | ||||
| 			} | ||||
| 		} | ||||
| 		if len(items) > 0 { | ||||
| 			result = append(result, fmt.Sprintf("### %s", group.Title)) | ||||
| 			result = append(result, items...) | ||||
| 		} | ||||
| 		groups = append(groups, item) | ||||
| 	} | ||||
|  | ||||
| 	sort.Slice(groups, func(i, j int) bool { return groups[i].order < groups[j].order }) | ||||
| 	for _, group := range groups { | ||||
| 		if len(group.entries) > 0 { | ||||
| 			result = append(result, fmt.Sprintf("### %s", group.title)) | ||||
| 			result = append(result, group.entries...) | ||||
| 		} | ||||
| 	} | ||||
| 	return strings.Join(result, newLine), nil | ||||
| } | ||||
|  | ||||
|   | ||||
| @@ -619,6 +619,7 @@ func TestGroup(t *testing.T) { | ||||
| 	testlib.GitCommit(t, "added feature 1") | ||||
| 	testlib.GitCommit(t, "fixed bug 2") | ||||
| 	testlib.GitCommit(t, "ignored: whatever") | ||||
| 	testlib.GitCommit(t, "feat(deps): update foobar [bot]") | ||||
| 	testlib.GitCommit(t, "fix: whatever") | ||||
| 	testlib.GitCommit(t, "docs: whatever") | ||||
| 	testlib.GitCommit(t, "chore: something about cArs we dont need") | ||||
| @@ -630,6 +631,11 @@ func TestGroup(t *testing.T) { | ||||
| 		Dist: folder, | ||||
| 		Changelog: config.Changelog{ | ||||
| 			Groups: []config.ChangeLogGroup{ | ||||
| 				{ | ||||
| 					Title:  "Bots", | ||||
| 					Regexp: ".*bot.*", | ||||
| 					Order:  900, | ||||
| 				}, | ||||
| 				{ | ||||
| 					Title:  "Features", | ||||
| 					Regexp: "^.*feat[(\\w)]*:+.*$", | ||||
| @@ -655,6 +661,7 @@ func TestGroup(t *testing.T) { | ||||
| 	ctx.Git.CurrentTag = "v0.0.2" | ||||
| 	require.NoError(t, Pipe{}.Run(ctx)) | ||||
| 	require.Contains(t, ctx.ReleaseNotes, "## Changelog") | ||||
| 	require.Contains(t, ctx.ReleaseNotes, "### Bots") | ||||
| 	require.Contains(t, ctx.ReleaseNotes, "### Features") | ||||
| 	require.Contains(t, ctx.ReleaseNotes, "### Bug Fixes") | ||||
| 	require.NotContains(t, ctx.ReleaseNotes, "### Catch nothing") | ||||
|   | ||||
		Reference in New Issue
	
	Block a user