Script Runner Post Function fire Action

Hello!

I need some help about scripted post function. I want to fire an Action (ex: Sent to Review) as a Post Function another transition (ex: Integrate) if a complicated condition goes true.

I have some questions:

1, Is it possible to fire an Action (transition) as a post function of another transition.

I am writing you the whole situation and my expectation. If anybody has idea how to figure out the solution please answer me.

 

I want to fire automatic transitions on my parent issue depending on sub-task's status, different sub-task types and different statuses. All automatic transition has different condition concern to sub-task's types and statuses and the parent issue is must be in specified status.

Here is what is made:

import com.atlassian.jira.component.ComponentAccessor;
import com.atlassian.jira.user.util.UserManager
import java.util.logging.Logger;
import com.atlassian.jira.bc.issue.IssueService
import com.atlassian.jira.issue.IssueInputParameters

public void doTransition(String statusId, int transitionId) {
	try{
		Thread thread = Thread.start {
			sleep(1000);
	 
			IssueService issueService = ComponentAccessor.getIssueService()
			UserManager userManager = (UserManager)  ComponentAccessor.getUserManager()
			IssueInputParameters issueInputParameters = issueService.newIssueInputParameters();
			issueInputParameters.setStatusId(statusId);
			IssueService.TransitionValidationResult transitionValidationResult = issueService.validateTransition(ComponentAccessor.getJiraAuthenticationContext().getLoggedInUser(), issue.id, transitionId, issueInputParameters);
			
			if (transitionValidationResult.isValid()){
				IssueService.IssueResult transitionResult = issueService.transition(currentUser, transitionValidationResult);
				if (!transitionResult.isValid()) {
					transitionResult.errorCollection.errorMessages.each {log.error "Error Message: $it"}
					transitionResult.errorCollection.errors.each {log.error "Error: $it"}
					transitionResult.errorCollection.reasons.each {log.error "Reason: $it"}
				}
			} else {
				transitionValidationResult.errorCollection.errorMessages.each {log.error "Error Message: $it"}
				transitionValidationResult.errorCollection.errors.each {log.error "Error: $it"}
				transitionValidationResult.errorCollection.reasons.each {log.error "Reason: $it"}
			}
		}
	} catch (Exception e){
		log.error(e.getMessage());
	}
}
def subtasks = issue.getSubTaskObjects();
def cFieldValue = issue.getCustomFieldValue(ComponentAccessor.getCustomFieldManager().getCustomFieldObject("customfield_22200")) // status before trigger
def goToReproduction = false;
def goToProcessing = false;
def goToIntegrating = false;
def goToVerifying = false;
def goToConcluding = false;
for (int i=0; i < subtasks.size(); i++)
{
	def nextIssue = subtasks[i];
    
	if (cFieldValue == 'Categorizing')
	{
		if	(nextIssue.getIssueTypeId() == "13602" && nextIssue.getStatus()?.name != 'New') 
		{
			goToReproduction = true
			break;
		}
	} 
	else if (cFieldValue == 'Reproduction')
	{
		if ((nextIssue.getIssueTypeId() == "13603" || nextIssue.getIssueTypeId() == "13701") && nextIssue.getStatus()?.name != 'New') 
		{
			goToProcessing = true
			break;
		}
	} 
	else if (cFieldValue == 'Processing')
	{
		if ((nextIssue.getIssueTypeId() == "13603" || nextIssue.getIssueTypeId() == "13701") && nextIssue.getStatus()?.name == 'Closed') 
		{
			goToIntegrating = true
			break;
		
		}
	} 
	else if (cFieldValue == 'Integrating')
	{
		if ((nextIssue.getIssueTypeId() == "13507" && nextIssue.getStatus()?.name != 'New')) 
		{
		goToVerifying = true
		break;
		}
	}		
		else 
		{
		
		}
}

if (goToReproduction){
	doTransition("3", 21);
}
if (goToProcessing)
{
	doTransition("4", 31);
}
if (goToIntegrating)
{
	doTransition("5", 41);
}
if (goToVerifying)
{
	doTransition("6", 51);
}
if (goToConcluding)
{
	doTransition("7", 61);
}

Does anybody have better solution then mine, without hack?

 

 

1 answer

As I understand you have several transitions from single status of parent issue and you want automatically select correct one.

For this purpose I usually use respective conditions for transitions. When conditions are well organised user has the only button for transtion.

Bonus: I like to refactor code, here is refactored version of your code:

import com.atlassian.jira.component.ComponentAccessor
import com.atlassian.jira.issue.Issue;
import com.atlassian.jira.user.util.UserManager
import java.util.logging.Logger;
import com.atlassian.jira.bc.issue.IssueService
import com.atlassian.jira.issue.IssueInputParameters

public void doTransition(String statusId, int transitionId) {
    try{
        Thread thread = Thread.start {
            sleep(1000);

            IssueService issueService = ComponentAccessor.getIssueService()
            UserManager userManager = (UserManager)  ComponentAccessor.getUserManager()
            IssueInputParameters issueInputParameters = issueService.newIssueInputParameters();
            issueInputParameters.setStatusId(statusId);
            IssueService.TransitionValidationResult transitionValidationResult = issueService.validateTransition(ComponentAccessor.getJiraAuthenticationContext().getLoggedInUser(), issue.id, transitionId, issueInputParameters);

            if (transitionValidationResult.isValid()){
                IssueService.IssueResult transitionResult = issueService.transition(currentUser, transitionValidationResult);
                if (!transitionResult.isValid()) {
                    transitionResult.errorCollection.errorMessages.each {log.error "Error Message: $it"}
                    transitionResult.errorCollection.errors.each {log.error "Error: $it"}
                    transitionResult.errorCollection.reasons.each {log.error "Reason: $it"}
                }
            } else {
                transitionValidationResult.errorCollection.errorMessages.each {log.error "Error Message: $it"}
                transitionValidationResult.errorCollection.errors.each {log.error "Error: $it"}
                transitionValidationResult.errorCollection.reasons.each {log.error "Reason: $it"}
            }
        }
    } catch (Exception e){
        log.error(e.getMessage());
    }
}

boolean goToConcluding = false;

for(Issue subtask: issue.getSubTaskObjects()) {

    switch (issue.getCustomFieldValue(ComponentAccessor.getCustomFieldManager().getCustomFieldObject("customfield_22200"))) {
        case "Categorizing":
            if (subtask.getIssueTypeId() == "13602" && subtask.getStatusObject()?.getName() != 'New') {
                doTransition("3", 21);
                break;
            }

        case 'Reproduction':
            if ((subtask.getIssueTypeId() == "13603" || subtask.getIssueTypeId() == "13701") && subtask.getStatusObject()?.getName() != 'New') {
                doTransition("4", 31);
                break;
            }

        case 'Processing':
            if ((subtask.getIssueTypeId() == "13603" || subtask.getIssueTypeId() == "13701") && subtask.getStatusObject()?.getName() == 'Closed') {
                doTransition("5", 41);
                break;
            }

        case 'Integrating':
            if ((subtask.getIssueTypeId() == "13507" && subtask.getStatusObject()?.getName() != 'New')) {
                doTransition("6", 51);
                break;
            }
    }
}

if (goToConcluding){
    doTransition("7", 61);
}

Hello Vasiliy!

Thank you very much for your answer and refactoring my code. I am quiet new at scriting, so this things always helps me a lot! smile

Yes, you understand well, I have several transitions from a single status and I want to fire the right one depending on sub-tasks type and status, but this transition I want to occur automatically.

More details about the situation.

I have a simple workflow for the parent ticket with one "hidden" status, named "Triggerd". I real process we don't use this status, this is just to help in automatize our complex workflow. In specified sub-task types, on the right transitions I added a post-function to call Trigger transition in parent ticket. (Trigger transition move to Triggered status). And I want my parent ticket to move toward to the right status is I fire this "triggering" transition in sub-task. I don't want to stay the parent ticket at "Triggered" status.

Easier, I want to automatize selecting and firing the right transition in parent ticket, launched with the specified sub-task transition.

Your solution seems to difficalt for me.

I think that it could be easer to have respective postfunction on sub-task transitions. In this case there is no any need to check sub-task type and status.

Try to reorganise you processes and onle then start writing code. If information about your processes is not secret, I could help you to organase it.

I have never heard about respective post-functions. I will look for some information about it.

My process is not a secret but I think would be easier to contact each other on another platform not to disturb other users. Please contact me through my e-mail. mullnerbianka@gmail.com

Respective is not some type of post-function. I mean appropriate or post-function which do what it should do

I see......

I need to monitor the sub-tasks because in my process it is possible to have more than one sub-task typed for ex. Reproducing and the parent ticket can't go toward to the next Status (ex:Fixing) until all the Reproducing tickets are not closed.

I think that it is better to add a postfunction on close transition:

import com.atlassian.jira.issue.Issue

for(Issue subtask: issue.getParentObject().getSubTaskObjects()){
    if((subtask.getIssueTypeObject().getName().equals("Reproducing")) && (subtask.getResolutionObject()) == null){
        return; //we have at least 1 unresolved Reproducing issue 
    }
}

//Code to trasit parent issue

Suggest an answer

Log in or Join to answer
Community showcase
Sarah Schuster
Posted Jan 29, 2018 in Jira

What are common themes you've seen across successful & failed Jira Software implementations?

Hey everyone! My name is Sarah Schuster, and I'm a Customer Success Manager in Atlassian specializing in Jira Software Cloud. Over the next few weeks I will be posting discussion topics (8 total) to ...

2,739 views 11 18
Join discussion

Atlassian User Groups

Connect with like-minded Atlassian users at free events near you!

Find a group

Connect with like-minded Atlassian users at free events near you!

Find my local user group

Unfortunately there are no AUG chapters near you at the moment.

Start an AUG

You're one step closer to meeting fellow Atlassian users at your local meet up. Learn more about AUGs

Groups near you
Atlassian Team Tour

Join us on the Team Tour

We're bringing product updates and pro tips on teamwork to ten cities around the world.

Save your spot