Issue 596/include only assigned (#817)
* Add new 'include-only-assigned' option If set, only issues containing assignees will be processed * Test new flag * Update code comment * Update src/classes/issues-processor.ts Co-authored-by: Francesco Renzi <rentziass@github.com> * Update index.js with typo fix Co-authored-by: Francesco Renzi <rentziass@github.com>
This commit is contained in:
parent
33e37032bb
commit
3e4418e47e
|
@ -51,5 +51,6 @@ export const DefaultProcessorOptions: IIssuesProcessorOptions = Object.freeze({
|
||||||
ignoreIssueUpdates: undefined,
|
ignoreIssueUpdates: undefined,
|
||||||
ignorePrUpdates: undefined,
|
ignorePrUpdates: undefined,
|
||||||
exemptDraftPr: false,
|
exemptDraftPr: false,
|
||||||
closeIssueReason: ''
|
closeIssueReason: '',
|
||||||
|
includeOnlyAssigned: false
|
||||||
});
|
});
|
||||||
|
|
|
@ -2352,3 +2352,69 @@ test('processing a pull request to be stale with the "stalePrMessage" option set
|
||||||
expect(processor.closedIssues).toHaveLength(0);
|
expect(processor.closedIssues).toHaveLength(0);
|
||||||
expect(processor.statistics?.addedPullRequestsCommentsCount).toStrictEqual(0);
|
expect(processor.statistics?.addedPullRequestsCommentsCount).toStrictEqual(0);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
test('processing an issue with the "includeOnlyAssigned" option and nonempty assignee list will stale the issue', async () => {
|
||||||
|
const issueDate = new Date();
|
||||||
|
issueDate.setDate(issueDate.getDate() - 2);
|
||||||
|
|
||||||
|
const opts: IIssuesProcessorOptions = {
|
||||||
|
...DefaultProcessorOptions,
|
||||||
|
staleIssueLabel: 'This issue is stale',
|
||||||
|
includeOnlyAssigned: true
|
||||||
|
};
|
||||||
|
|
||||||
|
const TestIssueList: Issue[] = [
|
||||||
|
generateIssue(
|
||||||
|
opts,
|
||||||
|
1,
|
||||||
|
'An issue with no label',
|
||||||
|
issueDate.toDateString(),
|
||||||
|
issueDate.toDateString(),
|
||||||
|
false,
|
||||||
|
[],
|
||||||
|
false,
|
||||||
|
false,
|
||||||
|
undefined,
|
||||||
|
['assignee1']
|
||||||
|
)
|
||||||
|
];
|
||||||
|
const processor = new IssuesProcessorMock(
|
||||||
|
opts,
|
||||||
|
async p => (p === 1 ? TestIssueList : []),
|
||||||
|
async () => [],
|
||||||
|
async () => new Date().toDateString()
|
||||||
|
);
|
||||||
|
|
||||||
|
// process our fake issue list
|
||||||
|
await processor.processIssues(1);
|
||||||
|
|
||||||
|
expect(processor.staleIssues).toHaveLength(1);
|
||||||
|
expect(processor.closedIssues).toHaveLength(0);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('processing an issue with the "includeOnlyAssigned" option set and no assignees will not stale the issue', async () => {
|
||||||
|
const issueDate = new Date();
|
||||||
|
issueDate.setDate(issueDate.getDate() - 2);
|
||||||
|
|
||||||
|
const opts: IIssuesProcessorOptions = {
|
||||||
|
...DefaultProcessorOptions,
|
||||||
|
staleIssueLabel: 'This issue is stale',
|
||||||
|
includeOnlyAssigned: true
|
||||||
|
};
|
||||||
|
|
||||||
|
const TestIssueList: Issue[] = [
|
||||||
|
generateIssue(opts, 1, 'An issue with no label', issueDate.toDateString())
|
||||||
|
];
|
||||||
|
const processor = new IssuesProcessorMock(
|
||||||
|
opts,
|
||||||
|
async p => (p === 1 ? TestIssueList : []),
|
||||||
|
async () => [],
|
||||||
|
async () => new Date().toDateString()
|
||||||
|
);
|
||||||
|
|
||||||
|
// process our fake issue list
|
||||||
|
await processor.processIssues(1);
|
||||||
|
|
||||||
|
expect(processor.staleIssues).toHaveLength(0);
|
||||||
|
expect(processor.closedIssues).toHaveLength(0);
|
||||||
|
});
|
||||||
|
|
|
@ -476,6 +476,11 @@ class IssuesProcessor {
|
||||||
IssuesProcessor._endIssueProcessing(issue);
|
IssuesProcessor._endIssueProcessing(issue);
|
||||||
return; // Don't process locked issues
|
return; // Don't process locked issues
|
||||||
}
|
}
|
||||||
|
if (this._isIncludeOnlyAssigned(issue)) {
|
||||||
|
issueLogger.info(`Skipping this $$type because its assignees list is empty`);
|
||||||
|
IssuesProcessor._endIssueProcessing(issue);
|
||||||
|
return; // If the issue has an 'include-only-assigned' option set, process only issues with nonempty assignees list
|
||||||
|
}
|
||||||
const onlyLabels = words_to_list_1.wordsToList(this._getOnlyLabels(issue));
|
const onlyLabels = words_to_list_1.wordsToList(this._getOnlyLabels(issue));
|
||||||
if (onlyLabels.length > 0) {
|
if (onlyLabels.length > 0) {
|
||||||
issueLogger.info(`The option ${issueLogger.createOptionLink(option_1.Option.OnlyLabels)} was specified to only process issues and pull requests with all those labels (${logger_service_1.LoggerService.cyan(onlyLabels.length)})`);
|
issueLogger.info(`The option ${issueLogger.createOptionLink(option_1.Option.OnlyLabels)} was specified to only process issues and pull requests with all those labels (${logger_service_1.LoggerService.cyan(onlyLabels.length)})`);
|
||||||
|
@ -988,6 +993,9 @@ class IssuesProcessor {
|
||||||
}
|
}
|
||||||
return this.options.onlyLabels;
|
return this.options.onlyLabels;
|
||||||
}
|
}
|
||||||
|
_isIncludeOnlyAssigned(issue) {
|
||||||
|
return this.options.includeOnlyAssigned && !issue.hasAssignees;
|
||||||
|
}
|
||||||
_getAnyOfLabels(issue) {
|
_getAnyOfLabels(issue) {
|
||||||
if (issue.isPullRequest) {
|
if (issue.isPullRequest) {
|
||||||
if (this.options.anyOfPrLabels !== '') {
|
if (this.options.anyOfPrLabels !== '') {
|
||||||
|
@ -2207,7 +2215,8 @@ function _getAndValidateArgs() {
|
||||||
ignoreIssueUpdates: _toOptionalBoolean('ignore-issue-updates'),
|
ignoreIssueUpdates: _toOptionalBoolean('ignore-issue-updates'),
|
||||||
ignorePrUpdates: _toOptionalBoolean('ignore-pr-updates'),
|
ignorePrUpdates: _toOptionalBoolean('ignore-pr-updates'),
|
||||||
exemptDraftPr: core.getInput('exempt-draft-pr') === 'true',
|
exemptDraftPr: core.getInput('exempt-draft-pr') === 'true',
|
||||||
closeIssueReason: core.getInput('close-issue-reason')
|
closeIssueReason: core.getInput('close-issue-reason'),
|
||||||
|
includeOnlyAssigned: core.getInput('include-only-assigned') === 'true'
|
||||||
};
|
};
|
||||||
for (const numberInput of [
|
for (const numberInput of [
|
||||||
'days-before-stale',
|
'days-before-stale',
|
||||||
|
|
|
@ -62,7 +62,8 @@ describe('Issue', (): void => {
|
||||||
ignoreIssueUpdates: undefined,
|
ignoreIssueUpdates: undefined,
|
||||||
ignorePrUpdates: undefined,
|
ignorePrUpdates: undefined,
|
||||||
exemptDraftPr: false,
|
exemptDraftPr: false,
|
||||||
closeIssueReason: ''
|
closeIssueReason: '',
|
||||||
|
includeOnlyAssigned: false
|
||||||
};
|
};
|
||||||
issueInterface = {
|
issueInterface = {
|
||||||
title: 'dummy-title',
|
title: 'dummy-title',
|
||||||
|
|
|
@ -221,6 +221,14 @@ export class IssuesProcessor {
|
||||||
return; // Don't process locked issues
|
return; // Don't process locked issues
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (this._isIncludeOnlyAssigned(issue)) {
|
||||||
|
issueLogger.info(
|
||||||
|
`Skipping this $$type because its assignees list is empty`
|
||||||
|
);
|
||||||
|
IssuesProcessor._endIssueProcessing(issue);
|
||||||
|
return; // If the issue has an 'include-only-assigned' option set, process only issues with nonempty assignees list
|
||||||
|
}
|
||||||
|
|
||||||
const onlyLabels: string[] = wordsToList(this._getOnlyLabels(issue));
|
const onlyLabels: string[] = wordsToList(this._getOnlyLabels(issue));
|
||||||
|
|
||||||
if (onlyLabels.length > 0) {
|
if (onlyLabels.length > 0) {
|
||||||
|
@ -1012,6 +1020,10 @@ export class IssuesProcessor {
|
||||||
return this.options.onlyLabels;
|
return this.options.onlyLabels;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private _isIncludeOnlyAssigned(issue: Issue): boolean {
|
||||||
|
return this.options.includeOnlyAssigned && !issue.hasAssignees;
|
||||||
|
}
|
||||||
|
|
||||||
private _getAnyOfLabels(issue: Issue): string {
|
private _getAnyOfLabels(issue: Issue): string {
|
||||||
if (issue.isPullRequest) {
|
if (issue.isPullRequest) {
|
||||||
if (this.options.anyOfPrLabels !== '') {
|
if (this.options.anyOfPrLabels !== '') {
|
||||||
|
|
|
@ -52,4 +52,5 @@ export interface IIssuesProcessorOptions {
|
||||||
ignorePrUpdates: boolean | undefined;
|
ignorePrUpdates: boolean | undefined;
|
||||||
exemptDraftPr: boolean;
|
exemptDraftPr: boolean;
|
||||||
closeIssueReason: string;
|
closeIssueReason: string;
|
||||||
|
includeOnlyAssigned: boolean;
|
||||||
}
|
}
|
||||||
|
|
|
@ -88,7 +88,8 @@ function _getAndValidateArgs(): IIssuesProcessorOptions {
|
||||||
ignoreIssueUpdates: _toOptionalBoolean('ignore-issue-updates'),
|
ignoreIssueUpdates: _toOptionalBoolean('ignore-issue-updates'),
|
||||||
ignorePrUpdates: _toOptionalBoolean('ignore-pr-updates'),
|
ignorePrUpdates: _toOptionalBoolean('ignore-pr-updates'),
|
||||||
exemptDraftPr: core.getInput('exempt-draft-pr') === 'true',
|
exemptDraftPr: core.getInput('exempt-draft-pr') === 'true',
|
||||||
closeIssueReason: core.getInput('close-issue-reason')
|
closeIssueReason: core.getInput('close-issue-reason'),
|
||||||
|
includeOnlyAssigned: core.getInput('include-only-assigned') === 'true'
|
||||||
};
|
};
|
||||||
|
|
||||||
for (const numberInput of [
|
for (const numberInput of [
|
||||||
|
|
Loading…
Reference in New Issue