Skip to content

Commit

Permalink
Add scopes option to filter analysis/changelog
Browse files Browse the repository at this point in the history
  • Loading branch information
zzmp committed Nov 28, 2023
1 parent 86301c8 commit e83dc8a
Show file tree
Hide file tree
Showing 8 changed files with 83 additions and 8 deletions.
4 changes: 4 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,10 @@ jobs:
- **release_branches** _(optional)_ - Comma separated list of branches (JavaScript regular expression accepted) that will generate the release tags. Other branches and pull-requests generate versions postfixed with the commit hash and do not generate any repository tag. Examples: `master` or `.*` or `release.*,hotfix.*,master`... (default: `master,main`).
- **pre_release_branches** _(optional)_ - Comma separated list of branches (JavaScript regular expression accepted) that will generate the pre-release tags.

#### Filter commits

- **scopes** _(optional)_ - Comma separated list of scopes (JavaScript regular expression accepted) to consider when tagging, and to include in the changelog. If this option is specified, then commits with scopes not matching this list will not be analyzed nor included in the changelog.

#### Customize the tag

- **default_bump** _(optional)_ - Which type of bump to use when [none is explicitly provided](#bumping) when commiting to a release branch (default: `patch`). You can also set `false` to avoid generating a new tag when none is explicitly provided. Can be `patch, minor or major`.
Expand Down
3 changes: 3 additions & 0 deletions action.yml
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,9 @@ inputs:
pre_release_branches:
description: "Comma separated list of branches (bash reg exp accepted) that will generate pre-release tags."
required: false
scopes:
description: "Comma separated list of scopes (bash reg exp accepted) to analyze and to include in the changelog."
required: false
commit_sha:
description: "The commit SHA value to add the tag. If specified, it uses this value instead GITHUB_SHA. It could be useful when a previous step merged a branch into github.ref."
required: false
Expand Down
1 change: 1 addition & 0 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@
"@semantic-release/commit-analyzer": "^8.0.1",
"@semantic-release/release-notes-generator": "^9.0.1",
"conventional-changelog-conventionalcommits": "^4.6.1",
"conventional-commits-parser": "^3.2.0",
"semver": "^7.3.5"
},
"devDependencies": {
Expand Down
18 changes: 18 additions & 0 deletions src/action.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import * as core from '@actions/core';
import { sync as parser } from 'conventional-commits-parser';
import { gte, inc, parse, ReleaseType, SemVer, valid } from 'semver';
import { analyzeCommits } from '@semantic-release/commit-analyzer';
import { generateNotes } from '@semantic-release/release-notes-generator';
Expand All @@ -24,6 +25,7 @@ export default async function main() {
const customTag = core.getInput('custom_tag');
const releaseBranches = core.getInput('release_branches');
const preReleaseBranches = core.getInput('pre_release_branches');
const scopes = core.getInput('scopes');
const appendToPreReleaseTag = core.getInput('append_to_pre_release_tag');
const createAnnotatedTag = /true/i.test(
core.getInput('create_annotated_tag')
Expand Down Expand Up @@ -123,6 +125,22 @@ export default async function main() {

commits = await getCommits(previousTag.commit.sha, commitRef);

if (scopes.length) {
const isInScope = (scope: string) =>
scopes.split(',').some((includedScope) => scope.match(includedScope));
commits = commits.filter((commit) => {
const scope = parser(commit.message).scope;
if (scope) {
const isInScopes = scopes
.split(',')
.some((includedScope) => scope.match(includedScope));
return isInScopes;
} else {
return false;
}
});
}

let bump = await analyzeCommits(
{
releaseRules: mappedReleaseRules
Expand Down
42 changes: 42 additions & 0 deletions tests/action.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -215,6 +215,48 @@ describe('github-tag-action', () => {
);
expect(mockSetFailed).not.toBeCalled();
});

it('does skip commits not included in scopes', async () => {
/*
* Given
*/
setInput('scopes', 'yes');
const commits = [
{ message: 'fix(YES): 1ne', hash: null },
{ message: 'feat(NO): 2wo', hash: null },
];
jest
.spyOn(utils, 'getCommits')
.mockImplementation(async (sha) => commits);

const validTags = [
{
name: 'v1.2.3',
commit: { sha: '012345', url: '' },
zipball_url: '',
tarball_url: 'string',
node_id: 'string',
},
];
jest
.spyOn(utils, 'getValidTags')
.mockImplementation(async () => validTags);

/*
* When
*/
await action();

/*
* Then
*/
expect(mockCreateTag).toHaveBeenCalledWith(
'v1.2.4',
expect.any(Boolean),
expect.any(String)
);
expect(mockSetFailed).not.toBeCalled();
});
});

describe('release branches', () => {
Expand Down
18 changes: 10 additions & 8 deletions tests/helper.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,12 @@ export function setCommitSha(sha: string) {
process.env['GITHUB_SHA'] = sha;
}

export function setInput(key: string, value: string) {
process.env[`INPUT_${key.toUpperCase()}`] = value;
export function setInput(key: string, value: string | undefined) {
if (value) {
process.env[`INPUT_${key.toUpperCase()}`] = value;
} else {
delete process.env[`INPUT_${key.toUpperCase()}`];
}
}

export function setInputs(map: { [key: string]: string }) {
Expand All @@ -34,12 +38,10 @@ export function loadDefaultInputs() {
const actionJson = yaml.load(actionYaml) as {
inputs: { [key: string]: { default?: string } };
};
const defaultInputs = Object.keys(actionJson['inputs'])
.filter((key) => actionJson['inputs'][key].default)
.reduce(
(obj, key) => ({ ...obj, [key]: actionJson['inputs'][key].default }),
{}
);
const defaultInputs = Object.keys(actionJson['inputs']).reduce(
(obj, key) => ({ ...obj, [key]: actionJson['inputs'][key].default }),
{}
);
setInputs(defaultInputs);
}

Expand Down
4 changes: 4 additions & 0 deletions types/semantic.d.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
/// <reference types="semver" />

declare module 'conventional-commits-parser' {
export function sync(message: string): { scope?: string };
}

declare module '@semantic-release/commit-analyzer' {
export function analyzeCommits(
config: {
Expand Down

0 comments on commit e83dc8a

Please sign in to comment.