Cleaning up Inactive Workflow Schemes and Workflows

As an administrator of many different Jira Server/Data Center environments, I try to keep my environment tidy. One of the tasks I most dread is having to clean up discarded Workflow Schemes and Workflows. You know the ones that hide in the Inactive pool. You delete one and then you have to scroll back to the bottom, open the Inactive marker again and delete another one. This can be such a painful process, that many administrators often ignore it, collecting a pile of detritus over time.

To help with this, I wrote the following Groovy script that will clean up all inactive Workflow Schemes and then all of the remaining inactive Workflows. This script was tested with ScriptRunner for Jira. However, it is likely to be able to run with any Groovy script console since it uses just the Jira API.

One last word before I hand you the script. It will delete everything that is marked as inactive. Use this script with extreme caution. You might want to make sure you back up your database before your first run. 

I take no responsibility for what happens when you use this script. I make it available for my fellow admins who have suffered long enough with manually cleaning up their old, discarded, dust-gathering artifacts

/***
** Author: Derek Fields - derek.fields@rightstar.com
**
** Delete all inactive workflow schemes and workflows. Use with EXTREME CAUTION
***/
import com.atlassian.jira.component.ComponentAccessor;
import com.atlassian.jira.bc.workflow.WorkflowSchemeService;
import com.atlassian.jira.workflow.WorkflowSchemeManager;
import com.atlassian.jira.workflow.WorkflowManager;
import com.atlassian.jira.workflow.WorkflowScheme;

import groovy.transform.Field;

@Field WorkflowManager workflowManager = ComponentAccessor.getWorkflowManager()
@Field WorkflowSchemeService workflowSchemeService = ComponentAccessor.getComponent(WorkflowSchemeService);
@Field WorkflowSchemeManager workflowSchemeManager = ComponentAccessor.getWorkflowSchemeManager();

// Delete all inactive Workflow Schemes
def deleteInactiveWorkflowSchemes() {
    def currentUser = ComponentAccessor.getJiraAuthenticationContext().getLoggedInUser(); 
    Collection<WorkflowScheme> inactiveWorkflowSchemes = workflowSchemeManager.getAssignableSchemes()
        .findAll{! workflowSchemeService.isActive((WorkflowScheme) it)}
    log.warn("Deleted ${inactiveWorkflowSchemes.size()} inactive workflow schemes");
    inactiveWorkflowSchemes.each{workflowSchemeService.deleteWorkflowScheme(currentUser, it)}
}

// Delete all inactive Workflows
def deleteInactiveWorkflows() {
    def active_workflows = workflowManager.getActiveWorkflows()
    def all_workflows = workflowManager.getWorkflows()

    def inactiveWorkflows = all_workflows.findAll{!(it in active_workflows)}
    inactiveWorkflows.each{workflowManager.deleteWorkflow(it)}
    log.warn("Deleted ${inactiveWorkflows.size()} inactive workflows");
}

// First delete the inactive schemes, then delete the inactive workflows
deleteInactiveWorkflowSchemes();
deleteInactiveWorkflows();

4 comments

Taranjeet Singh
Community Leader
Community Leader
Community Leaders are connectors, ambassadors, and mentors. On the online community, they serve as thought leaders, product experts, and moderators.
May 18, 2022

Thanks for sharing this Groovy Script, @C_ Derek Fields ! It could be very useful if we need to clean up inactive Workflow Schemes and Workflows in an automated manner.

Srikar Namala July 7, 2022

Hi @C_ Derek Fields 

When i run the script, below is the error...

 

2022-07-07 23:27:48,665 WARN [runner.ScriptBindingsManager]: Deleted 0 inactive workflow schemes 2022-07-07 23:27:48,686 ERROR [common.UserScriptEndpoint]: ************************************************************************************* 2022-07-07 23:27:48,687 ERROR [common.UserScriptEndpoint]: Script console script failed: com.atlassian.jira.workflow.WorkflowException: The workflow is assigned to workflow schemes at com.atlassian.jira.workflow.OSWorkflowManager.deleteWorkflow(OSWorkflowManager.java:469) at com.atlassian.jira.workflow.WorkflowManager$deleteWorkflow$4.call(Unknown Source) at Script246$_deleteInactiveWorkflows_closure4.doCall(Script246.groovy:31) at Script246.deleteInactiveWorkflows(Script246.groovy:31) at Script246.run(Script246.groovy:37)

 

Please help.

 

Thanks

Srikar

C_ Derek Fields
Rising Star
Rising Star
Rising Stars are recognized for providing high-quality answers to other users. Rising Stars receive a certificate of achievement and are on the path to becoming Community Leaders.
July 8, 2022

@Srikar Namala - I'm not sure why you are having the problem. I added some error handling to the script. My initial thought is that you lack appropriate permissions.

Try this version

 

/***
** Author: Derek Fields - derek.fields@rightstar.com
**
** Delete all inactive workflow schemes and workflows. Use with EXTREME CAUTION
***/
import com.atlassian.jira.component.ComponentAccessor;
import com.atlassian.jira.bc.workflow.WorkflowSchemeService;
import com.atlassian.jira.workflow.WorkflowSchemeManager;
import com.atlassian.jira.workflow.WorkflowManager;
import com.atlassian.jira.workflow.WorkflowScheme;
import com.atlassian.jira.workflow.WorkflowException;

import groovy.transform.Field;

@Field WorkflowManager workflowManager = ComponentAccessor.getWorkflowManager()
@Field WorkflowSchemeService workflowSchemeService = ComponentAccessor.getComponent(WorkflowSchemeService);
@Field WorkflowSchemeManager workflowSchemeManager = ComponentAccessor.getWorkflowSchemeManager();

// Delete all inactive Workflow Schemes
def deleteInactiveWorkflowSchemes() {
    def currentUser = ComponentAccessor.getJiraAuthenticationContext().getLoggedInUser();
    Collection<WorkflowScheme> inactiveWorkflowSchemes = workflowSchemeManager.getAssignableSchemes()
        .findAll{! workflowSchemeService.isActive((WorkflowScheme) it)}
    log.warn("Deleted ${inactiveWorkflowSchemes.size()} inactive workflow schemes");
    inactiveWorkflowSchemes.each{workflowSchemeService.deleteWorkflowScheme(currentUser, it)}
}

// Delete all inactive Workflows
def deleteInactiveWorkflows() {
    def active_workflows = workflowManager.getActiveWorkflows()
    def all_workflows = workflowManager.getWorkflows()

    def inactiveWorkflows = all_workflows.findAll{!(it in active_workflows)}
    def counter = 0;
    inactiveWorkflows.each{
        try {
            workflowManager.deleteWorkflow(it);
            counter++;
        } catch (WorkflowException e) {
            log.error("Unable to delete ${it.getDisplayName()}")
            log.error("${e.getMessage()}");
        }
    }
    log.warn("Deleted $counter inactive workflows");
}

// First delete the inactive schemes, then delete the inactive workflows
deleteInactiveWorkflowSchemes();
deleteInactiveWorkflows();
Tad Foster
Contributor
November 15, 2022

Hurray Derek!

Thanks for posting this! I was also running into similar errors that Srikar had, and then I found that what was happening is some workflows were assigned to non-published schemes (i.e. Draft workflow), and those are found in the inactive workflows list, but do not have an associated Delete button. Once I went through these particular workflows and either discarded the draft from non-published workflow or associated the workflow to a project just to get it out of the inactive list. I was able to run you script error free.

Reference: 

https://confluence.atlassian.com/jirakb/unable-to-delete-inactive-workflow-726368983.html

Thank you,

Tad

Like Sergiienko Volodymyr likes this

Comment

Log in or Sign up to comment
TAGS
AUG Leaders

Atlassian Community Events