Close an Epic when all the Issues Under that Epic are Closed

Overview

Transition an epic to Closed using a post function on the Closed workflow step which fires when all child issues are closed.

Example

I work in a software project using epics to organise the tasks. I want to close an epic when all tasks are complete, so I do not have to do this manually. I can use this script as a post function to close an epic when the last child issue has been completed.

Good to Know

  • By changing the issueLinkName, the script can be used to transition the source issue in linked relationships different from epics.
  • The Close action must have the transition screen associated with it in order to set the resolution.
  • By default, this script will have the resolution Done but it can be configured.

Requirements

Jira Software Jira Software (7.7 - 8.6)

    
import com.atlassian.jira.component.ComponentAccessor import com.atlassian.jira.workflow.TransitionOptions // the name of the action you want to move the issue to final actionName = 'Close' //Name of the resolution children issues should have final resolutionName = 'Done' // the name of the issue link final issueLinkName = 'Epic-Story Link' def workflow = ComponentAccessor.workflowManager.getWorkflow(issue) def actionId = workflow.allActions.findByName(actionName)?.id def linkManager = ComponentAccessor.issueLinkManager def epicIssue = linkManager.getInwardLinks(issue.id).find { it.issueLinkType.name == issueLinkName }?.sourceObject if (!epicIssue) { return } // Find all the linked - with the "Epic-Story Link" link - issues that their status is not the same as resolutionName def linkedIssues = linkManager .getOutwardLinks(epicIssue.id) .findAll { it.issueLinkType.name == issueLinkName } *.destinationObject?.findAll { it.resolution?.name != resolutionName } // If there are still open linked issues (except the one in transition) - then do nothing if (linkedIssues - issue) { return } def issueService = ComponentAccessor.issueService def inputParameters = issueService.newIssueInputParameters() inputParameters.setComment('This Epic closed automatically because all the issues in this Epic are closed.') inputParameters.setSkipScreenCheck(true) def transitionOptions = new TransitionOptions.Builder() .skipConditions() .skipPermissions() .skipValidators() .build() def loggedInUser = ComponentAccessor.jiraAuthenticationContext.loggedInUser def transitionValidationResult = issueService.validateTransition(loggedInUser, epicIssue.id, actionId, inputParameters, transitionOptions) assert transitionValidationResult.isValid(): transitionValidationResult.errorCollection def result = issueService.transition(loggedInUser, transitionValidationResult) assert result.isValid(): result.errorCollection
Discovered an issue? Report it here

Suggested for you