reg 'Custom Script Post Function'

Rupa Jain December 20, 2016

Hi,

I am using the following 'Custome Script Post Function' on 'Create' transition and is the first post-function and does not seem to work. It is checking for the issue type of a ticket, based on the issuetype a Custom field(select list) needs to be set up to a certain value 'XYZ':

import com.atlassian.jira.component.ComponentAccessor;
import com.atlassian.jira.issue.CustomFieldManager;
import com.atlassian.jira.issue.Issue
import com.atlassian.jira.issue.fields.CustomField

CustomFieldManager customFieldManager = ComponentAccessor.getCustomFieldManager();
def customerPriority = issue.getCustomFieldValue(customFieldManager.getCustomFieldObject("customfield_12345"));

if(issue.issueTypeObject.name == "ABC")
{
issue.setCustomFieldValue(customerPriority,'XYZ')
}
issue.store();


Any suggestions as to what might be wrong with the above code?

Thanks,

Rupa

3 answers

2 votes
Jonny Carter
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.
December 23, 2016

So, for cases where updating the issue attributes isn't working, it's a good idea to try using the IssueService to perform the update. Per the note in the ScriptRunner docs, you normally need to update issue attributes before it gets stored in the database.

 

You can only use this method to update issue attributes if your script post-function comes before the standard function Update change history for an issue and store the issue in the database. If you need your function to run after that, you have to use a more complex method.

 

 

This can be a little trickier with the create transition, as its post-functions are different from other workflow transitions.

To use the IssueService in this case, try something like this:

import com.atlassian.jira.bc.issue.IssueService
import com.atlassian.jira.component.ComponentAccessor
import com.atlassian.jira.event.type.EventDispatchOption
import com.atlassian.jira.issue.IssueInputParametersImpl
if (issue.issueTypeObject.name == "ABC") {
    def customFieldManager = ComponentAccessor.getCustomFieldManager()
    def customField = customFieldManager.getCustomFieldObject("customfield_12345")
    def issueService = ComponentAccessor.getIssueService()
    def user = ComponentAccessor.getJiraAuthenticationContext().getLoggedInUser()
    def issueInputParams = new IssueInputParametersImpl().addCustomFieldValue(customField.id, "XYZ")
    IssueService.UpdateValidationResult updateValidationResult =  issueService.validateUpdate(user, issue.id, issueInputParams)
    if (!updateValidationResult.isValid()) {
        log.error("Validation errors while updating issue: ${updateValidationResult.errorCollection}")
        return
    }
    else {
        def updateResult = issueService.update(user, updateValidationResult, EventDispatchOption.ISSUE_UPDATED, false)
        if (!updateResult.isValid()) {
            log.error("Update failed: ${updateResult.errorCollection}")
        }
    }
}

For this example, I've set it to dispatch an IssueUpdated event, but not to send mail on the update. You may adjust those parameters, depending on your needs.

1 vote
Vasiliy Zverev
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.
December 21, 2016

Your code seems to be correct. Is it placed after create issue postfunction?

Rupa Jain December 21, 2016

Yes tried placing it after the create issue post function, but still does not work.

Vasiliy Zverev
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.
December 21, 2016

Try this code. Main idea - an Option object should be used to update value

import com.atlassian.jira.component.ComponentAccessor;
import com.atlassian.jira.issue.CustomFieldManager;

import com.atlassian.jira.issue.customfields.manager.OptionsManager
import com.atlassian.jira.issue.customfields.option.Option
import com.atlassian.jira.issue.fields.CustomField
import com.atlassian.jira.issue.fields.config.manager.FieldConfigManager

if(issue.issueTypeObject.name != "ABC")
    return;

CustomFieldManager customFieldManager = ComponentAccessor.getCustomFieldManager();
CustomField customerPriority = issue.getCustomFieldValue(customFieldManager.getCustomFieldObject("customfield_12345"));

OptionsManager optionsManager = ComponentAccessor.getOptionsManager();
FieldConfigManager fieldConfigManager = ComponentAccessor.getComponent(FieldConfigManager.class)
for(Option option: optionsManager.getOptions(fieldConfigManager.getFieldConfig(issue.getId()))){
    if(option.getValue().equals("XYZ")) {
        issue.setCustomFieldValue(customerPriority, option)
        break;
    }
}
Rupa Jain December 22, 2016

There seems to be an issue in this part of the above code:

for(Option option: optionsManager.getOptions(fieldConfigManager.getFieldConfig(myIssue.getId()))){

if(option.getValue().equals("Project")) {

issue.setCustomFieldValue(customerPriority, option)
break;
}
}

Vasiliy Zverev
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.
December 22, 2016

Does this code work?

Do you get any errors?

Rupa Jain December 22, 2016

I get an error for this line:

for(Option option: optionsManager.getOptions(fieldConfigManager.getFieldConfig(myIssue.getId()))){


Error message:

java.lang.NullPointerException at com.atlassian.jira.issue.fields.config.persistence.FieldConfigPersisterImpl.getFieldConfig(FieldConfigPersisterImpl.java:193) at com.atlassian.jira.issue.fields.config.manager.FieldConfigManagerImpl.getFieldConfig(FieldConfigManagerImpl.java:33) at com.atlassian.jira.issue.fields.config.manager.FieldConfigManager$getFieldConfig.call(Unknown Source) at Script85.run(Script85.groovy:27) 

Rupa Jain December 22, 2016

I tried the following code, there is no error, but it is not updating the Custom Field.
What am I missing: 

import com.atlassian.jira.component.ComponentAccessor;
import com.atlassian.jira.issue.CustomFieldManager;
 
import com.atlassian.jira.issue.customfields.manager.OptionsManager
import com.atlassian.jira.issue.customfields.option.Option
import com.atlassian.jira.issue.fields.CustomField
import com.atlassian.jira.issue.fields.config.manager.FieldConfigManager
 
if(issue.issueTypeObject.name != "ABC")
	return;
 
CustomFieldManager customFieldManager = ComponentAccessor.getCustomFieldManager();
def customerPriority = ComponentAccessor.customFieldManager.getCustomFieldObjectByName("Priority");
 
def cfConfig = customerPriority.getRelevantConfig(issue);
def value = ComponentAccessor.optionsManager.getOptions(cfConfig)?.find {
    it.toString() == 'XYZ'
}

issue.setCustomFieldValue(customerPriority,value);

issue.store();
Vasiliy Zverev
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.
December 24, 2016

Do not use issue update in code. It is bad practice. Make sure that you have "Store issue into database" build-in postfunction after your script postfunction.

 

Rupa Jain December 25, 2016

Tried it, but does not work.

Also I tried to run the following code in 'Script Console' of script-runner, but does not update the value of the Custom Field:

import com.atlassian.jira.component.ComponentAccessor;
import com.atlassian.jira.issue.CustomFieldManager;
import com.atlassian.jira.issue.Issue;
import com.atlassian.jira.issue.MutableIssue;
import com.atlassian.jira.issue.IssueManager;
import com.atlassian.jira.ComponentManager;
import com.atlassian.jira.issue.resolution.Resolution;
 
import com.atlassian.jira.issue.customfields.manager.OptionsManager;
import com.atlassian.jira.issue.customfields.option.Option;
import com.atlassian.jira.issue.fields.CustomField;
import com.atlassian.jira.issue.fields.config.manager.FieldConfigManager;
IssueManager issueManager = ComponentManager.getInstance().getIssueManager();
MutableIssue myIssue = issueManager.getIssueObject("JJJ-98765")
if(myIssue.issueTypeObject.name == "ABC")
{
 
CustomFieldManager customFieldManager = ComponentAccessor.getCustomFieldManager();
def customerPriority = customFieldManager.getCustomFieldObjectByName("customfield_12345")
def cfConfig = customerPriority.getRelevantConfig(myIssue);

def value = ComponentAccessor.optionsManager.getOptions(cfConfig)?.find {
    it.toString() == 'XYZ'
}
myIssue.setCustomFieldValue(customerPriority,value);
myIssue.store();
}

Can you provide a piece of code that works well in your script-console?

Vasiliy Zverev
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.
December 25, 2016

You use myIssue variable instead issue. Also you get issue with specified issue key. Issue.store() is depricated. Do not use it. Never.

See updated code (I refactored it a litle)

import com.atlassian.jira.component.ComponentAccessor;
import com.atlassian.jira.issue.CustomFieldManager;
import com.atlassian.jira.issue.MutableIssue;
import com.atlassian.jira.issue.IssueManager;
import com.atlassian.jira.ComponentManager
import com.atlassian.jira.issue.fields.CustomField;

IssueManager issueManager = ComponentManager.getInstance().getIssueManager();

//Is it requared here?
MutableIssue issue = issueManager.getIssueObject("JJJ-98765")
if(issue.issueTypeObject.name != "ABC")
    return;

CustomFieldManager customFieldManager = ComponentAccessor.getCustomFieldManager();
CustomField customerPriority = customFieldManager.getCustomFieldObjectByName("customfield_12345")
def cfConfig = customerPriority.getRelevantConfig(issue);

def value = ComponentAccessor.optionsManager.getOptions(cfConfig)?.find {
    it.toString() == 'XYZ'
}     
issue.setCustomFieldValue(customerPriority,value);
Rupa Jain December 25, 2016

Used 'myIssue' only when running it in 'Script Console' on a particular issue.

Rupa Jain December 25, 2016

Tried the above code, but does not update the value of the Custom Field for 'JJJ-98765'.

There are no errors, the 'value' is also taking the correct option, it is jut not setting the Custom Field.

Rupa Jain January 5, 2017

Any update on this?

JamieA
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.
January 5, 2017

can you post the actual script you are using

JamieA
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.
January 5, 2017

for a post-function that's first in the list, you just need:

issue.setCustFieldValue...

Don't redefine issue, or get it from the db, or call .store.

Rupa Jain January 8, 2017

Jamie,

 

This is my actual script:

import com.atlassian.jira.component.ComponentAccessor;
import com.atlassian.jira.issue.CustomFieldManager;
  
import com.atlassian.jira.issue.customfields.manager.OptionsManager
import com.atlassian.jira.issue.customfields.option.Option
import com.atlassian.jira.issue.fields.CustomField
import com.atlassian.jira.issue.fields.config.manager.FieldConfigManager
  
if(issue.issueTypeObject.name != "Bug")
    return;
  
CustomFieldManager customFieldManager = ComponentAccessor.getCustomFieldManager();
def customerPriority = ComponentAccessor.customFieldManager.getCustomFieldObjectByName("Priority");
  
def cfConfig = customerPriority.getRelevantConfig(issue);
def value = ComponentAccessor.optionsManager.getOptions(cfConfig)?.find {
    it.toString() == 'Project'
}
 
issue.setCustomFieldValue(customerPriority,value);
log.warn(customerPriority)
log.warn(value)

 

And I get the following values in my log file:

'log.warn(customerPriority)'= Priority
'log.warn(value)'= Project

Its just not updating this value on the JIRA ticket when the ticket is created.

I am using the following versions:
JIRA - 6.4.6
Scriptrunner - 3.1.4

 

The above post-function is being used in the 'Create Transition' of the workflow and placed after 'Creates issue originally'

Purpose of the script:
When a ticket is being created, if the issue type is 'Bug', the 'Priority' custom field, which is a single value select list should take the value 'Project'.
In short for issue type Bug, the 'Priority' Custom Field should automatically have the value 'Project' when the ticket is created.

Thanks,

Rupa

Vasiliy Zverev
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.
January 9, 2017

There is a bug for create transition. Postfunction to store changes do not work correct. So it is better to add manually store changes, like this:

import com.atlassian.jira.component.ComponentAccessor
import com.atlassian.jira.event.type.EventDispatchOption;
import com.atlassian.jira.issue.CustomFieldManager
import com.atlassian.jira.issue.UpdateIssueRequest
import com.atlassian.jira.issue.fields.CustomField;

if(issue.issueTypeObject.name != "Bug")
    return;

CustomField customerPriority = ComponentAccessor.customFieldManager.getCustomFieldObjectByName("Priority");

def cfConfig = customerPriority.getRelevantConfig(issue);
def value = ComponentAccessor.optionsManager.getOptions(cfConfig)?.find {
    it.toString() == 'Project'
}

issue.setCustomFieldValue(customerPriority, value);
log.warn(customerPriority)
log.warn(value)

ComponentAccessor.getIssueManager().updateIssue(
        ComponentAccessor.getJiraAuthenticationContext().getUser()
        , issue
        , UpdateIssueRequest.builder().eventDispatchOption(EventDispatchOption.ISSUE_UPDATED).sendMail(false).build()
)
0 votes
Bhupesh Nagda August 22, 2018

hi all

hi  @Rupa Jain

Did you find a solution for this?

I am facing similar issue on updating s select list on create transition.

I have observed one strange behavior:

If i put the custom script transition at first position in post functions then log.warn(issue) gives value of summary of ticket in logs and does not update the select list value.

However when i make it second then it prints the relevant issue key but still does not update the select list value.

I want to set a select list value (Portfolio)based on value of second select list(Business Area) and then assign the ticket based on value of second select list.

Please bear with me on rookie way of coding!

JIRA 6.4.13

Script Runner: 4.1.3.29

import com.atlassian.jira.issue.Issue
import com.atlassian.jira.bc.issue.IssueService
import com.atlassian.jira.issue.IssueInputParameters
import com.atlassian.jira.component.ComponentAccessor
import com.atlassian.jira.issue.fields.CustomField
import com.atlassian.jira.issue.CustomFieldManager
import com.atlassian.jira.ComponentManager
import com.atlassian.jira.issue.MutableIssue
import com.atlassian.crowd.embedded.api.User
import com.atlassian.jira.issue.ModifiedValue
import com.atlassian.jira.issue.util.DefaultIssueChangeHolder
import com.atlassian.jira.user.ApplicationUser
import com.atlassian.crowd.embedded.api.User
import com.atlassian.jira.issue.customfields.manager.OptionsManager
import com.atlassian.jira.issue.customfields.option.Options
import com.atlassian.jira.event.type.EventDispatchOption
import com.atlassian.jira.issue.UpdateIssueRequest

 

def customFieldManager = ComponentAccessor.getCustomFieldManager()
def userManager = ComponentAccessor.getUserManager()

String myUserName
User usr

def issueManager = ComponentAccessor.getIssueManager();
User currentUser = ComponentAccessor.getJiraAuthenticationContext().getLoggedInUser();

//Set Issue Type to SR_Service Request
def newIssueType = ComponentAccessor.issueTypeSchemeManager.getIssueTypesForProject(issue.projectObject).find{it.name=="SR_Service Request"}
if (newIssueType) issue.setIssueTypeObject(newIssueType)


def BusinessAreaCf = customFieldManager.getCustomFieldObjectByName("Business Area")
def BusinessArea = issue.getCustomFieldValue(BusinessAreaCf)
log.warn("Busines Area value is : "+BusinessArea)
log.warn("issue object is :"+issue)
def reqPortfolioCf = customFieldManager.getCustomFieldObjectByName("Portfolio")
def fieldConfig = reqPortfolioCf.getRelevantConfig(issue)
def reqPortfolio

if(BusinessArea != null)
{
if(BusinessArea.toString() == "Enterprise")
{
reqPortfolio = ComponentAccessor.optionsManager.getOptions(fieldConfig)?.find {
it.toString() == 'EBU'
}
println("portfolio is "+reqPortfolio)
issue.setCustomFieldValue(reqPortfolioCf, reqPortfolio)
log.warn(reqPortfolio)
log.warn(reqPortfolioCf)
ComponentAccessor.getIssueManager().updateIssue(
ComponentAccessor.getJiraAuthenticationContext().getUser()
, issue
, UpdateIssueRequest.builder().eventDispatchOption(EventDispatchOption.ISSUE_UPDATED).build()
)
}
else if(BusinessArea.toString() == "Finance")
{
reqPortfolio = ComponentAccessor.optionsManager.getOptions(fieldConfig)?.find {
it.toString() == 'FIN'
}
println("portfolio is "+reqPortfolio)
issue.setCustomFieldValue(reqPortfolioCf, reqPortfolio)
log.warn(reqPortfolio)
log.warn(reqPortfolioCf)
ComponentAccessor.getIssueManager().updateIssue(
ComponentAccessor.getJiraAuthenticationContext().getUser()
, issue
, UpdateIssueRequest.builder().eventDispatchOption(EventDispatchOption.ISSUE_UPDATED).build()
)
}
else if(BusinessArea.toString() == "Customer")
{
reqPortfolio = ComponentAccessor.optionsManager.getOptions(fieldConfig)?.find {
it.toString() == 'CBU'
}
println("portfolio is "+reqPortfolio)
issue.setCustomFieldValue(reqPortfolioCf, reqPortfolio)
log.warn(reqPortfolio)
log.warn(reqPortfolioCf)
ComponentAccessor.getIssueManager().updateIssue(
ComponentAccessor.getJiraAuthenticationContext().getUser()
, issue
, UpdateIssueRequest.builder().eventDispatchOption(EventDispatchOption.ISSUE_UPDATED).build()
)
}

}
//" Based on Portfolio field update Assignee field
//" We just need three cases for Portfolio: 'Cable Reporting', 'NGC', 'Enterprise, Finance, Consumer Mobile'


if (reqPortfolio) {
if (reqPortfolio.toString() == "CBU") {
if(issue.components*.name.contains('TSSC-DataProv'))
{
myUserName = "BICC.TSSC-DataProv"
println("Username is : "+myUserName)
}
else
myUserName = "BICC.CBU-Reporting" // BICC.CBU-Reporting@vodafone.com
}

else if (reqPortfolio.toString() == "FIN") {
myUserName = "BICC.Finance-Reporti" // BICC.Finance-Reporting@Vodafone.com
println("Username is : "+myUserName)
}

else if (reqPortfolio.toString() == "EBU") {
myUserName = "BICC.EBU-Reporting" // BICC.EBU-Reporting@vodafone.com
println("Username is : "+myUserName)
}
else if (reqPortfolio.toString() == "CBU-fixed")
{
if(issue.components*.name.contains('TSSC-DataProv'))
{
myUserName = "BICC.TSSC-DataProv"
}
}

// set aggignee
usr = userManager.getUserObject(myUserName)
issue.setAssignee(usr)

}

 

Output==>

2018-08-22 17:50:50,383 http-bio-8050-exec-56 WARN admin 1070x49299x1 dgqcse 10.74.207.7,139.7.95.77 /secure/QuickCreateIssue.jspa [scriptrunner.jira.workflow.ScriptWorkflowFunction] Busines Area value is : [Finance]
2018-08-22 17:50:50,384 http-bio-8050-exec-56 WARN admin 1070x49299x1 dgqcse 10.74.207.7,139.7.95.77 /secure/QuickCreateIssue.jspa [scriptrunner.jira.workflow.ScriptWorkflowFunction] issue object is :SR-1579

Rupa Jain August 23, 2018

Hi Bhupesh,

 

The following script worked for me (placed it before 'Creates Issue' post function):

import com.atlassian.jira.component.ComponentAccessor;
import com.atlassian.jira.issue.CustomFieldManager;

import com.atlassian.jira.issue.customfields.manager.OptionsManager
import com.atlassian.jira.issue.customfields.option.Option
import com.atlassian.jira.issue.fields.CustomField
import com.atlassian.jira.issue.fields.config.manager.FieldConfigManager

if(issue.issueTypeObject.name != "ABC")
return;

CustomFieldManager customFieldManager = ComponentAccessor.getCustomFieldManager();
def SomeCustomField = ComponentAccessor.customFieldManager.getCustomFieldObjectByName("XYZ");

def cfConfig = SomeCustomField.getRelevantConfig(issue);
def value = ComponentAccessor.optionsManager.getOptions(cfConfig)?.find {
it.toString() == 'SomeValue'
}

issue.setCustomFieldValue(SomeCustomField,value);

 

Thanks,

Rupa

Suggest an answer

Log in or Sign up to answer