Scriptrunner listener to update custom date/time field For Cloud JIRA

Hi All,

I need a listener that will add current timestamp (date or datetime) to a custom date/time fields when another field (Story Points) is updated, for JIRA Cloud.

For example, if custom checkbox "Story Points" is edited, the listener detects this change and will timestamp the custom date/time field "StoryPointsLastChangeDate".

And, should the StoryPointsLastChangeDate a 'date' field or a 'datetime' custom field?

Thanks to @Conor McCooey @Thanos Batagiannis [Adaptavist] .

I fond your post at : https://community.atlassian.com/t5/Jira-questions/Scriptrunner-listener-to-update-custom-date-time-field/qaq-p/387444

 

But for JIRA Cloud, it does not work.

my script listner:

import com.atlassian.jira.component.ComponentAccessor
import com.atlassian.jira.issue.Issue
import com.atlassian.jira.issue.ModifiedValue
import com.atlassian.jira.issue.util.DefaultIssueChangeHolder

import java.sql.Timestamp

Issue issue = issue
def change = event?.getChangeLog()?.getRelated("ChildChangeItem").find {it.field == "Story Points"}
if (change) {
def cf = ComponentAccessor.getCustomFieldManager().getCustomFieldObjectByName("StoryPointsLastChangeDate")
def changeHolder = new DefaultIssueChangeHolder()
def now = new Timestamp(new Date().getTime())
cf.updateValue(null, issue, new ModifiedValue(issue.getCustomFieldValue(cf), now),changeHolder)
}

 

The errors:

2017-11-02 03:20:45.232 ERROR - startup failed:
Script1.groovy: 3: unable to resolve class com.atlassian.jira.issue.ModifiedValue
@ line 3, column 1.
import com.atlassian.jira.issue.ModifiedValue
^

Script1.groovy: 2: unable to resolve class com.atlassian.jira.issue.Issue
@ line 2, column 1.
import com.atlassian.jira.issue.Issue
^

Script1.groovy: 1: unable to resolve class com.atlassian.jira.component.ComponentAccessor
@ line 1, column 1.
import com.atlassian.jira.component.ComponentAccessor
^

Script1.groovy: 4: unable to resolve class com.atlassian.jira.issue.util.DefaultIssueChangeHolder
@ line 4, column 1.
import com.atlassian.jira.issue.util.DefaultIssueChangeHolder
^

4 errors

2017-11-02 03:20:45.653 ERROR - Class: com.adaptavist.sr.cloud.events.ScriptExecution, Config: null

 

Any help is much appreciated.

 

Regards,

Darren

3 answers

1 accepted

I have created an example code for you. Please have a look at the below code.

import java.time.ZonedDateTime
import java.time.ZoneId
import java.time.format.DateTimeFormatter

def storyPointsCheckboxFieldId = "customfield_10718"
def storyPointsLastChangeDateFieldId = "customfield_10719"

def customFieldChange = changelog.items.find { item -> item.fieldId == storyPointsCheckboxFieldId }
if (customFieldChange) {
logger.info("Custom field has been updated from value: {} to value: {}", customFieldChange.fromString, customFieldChange.toString)
def currentDateTime = ZonedDateTime.now().format(DateTimeFormatter.ISO_LOCAL_DATE_TIME)
logger.info("Making a request to update custom field id: {} with value: {}", storyPointsLastChangeDateFieldId, currentDateTime)

def result = put('/rest/api/2/issue/ADSD-2')
.header('Content-Type', 'application/json')
.body([
fields:[
(storyPointsLastChangeDateFieldId): currentDateTime
]
])
.asString()
if (result.status == 204) {
logger.info("Successfully updated field {} with value {}", storyPointsLastChangeDateFieldId, currentDateTime)
} else {
logger.error("Failed update field: {}. Jira responded {}: {}", storyPointsLastChangeDateFieldId, result.status, result.body)
}

}

You only need to replace ids of custom fields, i.e. storyPointsCheckBoxFieldId and storyPointsLastChangeDateFieldId.

In my example field storyPointsLastChangeDateFieldId is a 'Date Time Picker' custom field, but storyPointsCheckboxFieldId has a type 'Checkboxes'.

Thank you @Andrzej for you quick help. This example is really great help.

 

I have several questions:

1. Seems the currentDateTime could be sent to both the date and date time custom fields. No need to get a currentDate, right?

2. how to update both the date custom field and date time custom field? Is it possible to put in one put REST call?

now I could do it via two put REST call.....

// def resultDate = put('/rest/api/2/issue/${issue.key}')
def resultDate = put('/rest/api/2/issue/ACM-713')
.header('Content-Type', 'application/json')
.body([
fields:[
(StoryPointsLastChangeDateID): currentDateTime
]
])
.asString()
if (resultDate.status == 204) {
logger.info("Successfully updated field Story Points Last Change Date with value {} for issue {}", currentDateTime, issue.id)
logger.info(" ")
} else {
logger.error("Failed update field Story Points Last Change Date. Jira responded {}: {}", resultDate.status, resultDate.body)
logger.info(" ")
}

logger.info("Making a request to update custom field Story Points Last Change Date Time with value: {}", currentDateTime)
logger.info(" ")
// def resultDateTime = put('/rest/api/2/issue/${issue.key}')
def resultDateTime = put('/rest/api/2/issue/ACM-713')
.header('Content-Type', 'application/json')
.body([
fields:[
(StoryPointsLastChangeDateTimeID): currentDateTime
]
])
.asString()
if (resultDateTime.status == 204) {
logger.info("Successfully updated field Story Points Last Change Date Time with value {} for issue {}", currentDateTime, issue.id)
logger.info(" ")

it throw errors if I put two fields in one put call like:

 def resultDate = put('/rest/api/2/issue/ACM-713')
.header('Content-Type', 'application/json')
.body([
fields:[
(StoryPointsLastChangeDateID): currentDateTime
(StoryPointsLastChangeDateTimeID): currentDateTime
]
])
.asString()

 

3.

def result2 = put('/rest/api/2/issue/${issue.id}')
put('/rest/api/2/issue/${issue.id}')
and 
put('/rest/api/2/issue/${issue.key}')

return error:

2017-11-03 06:25:49.291 WARN - PUT request to /rest/api/2/issue/${issue.id} returned an error code: status: 404 - Not Found
body: {"errorMessages":["Issue does not exist or you do not have permission to see it."],"errors":{}}

 

but hard code works:

def result2 = put('/rest/api/2/issue/ACM-713')

returns:

2017-11-03 06:28:42.134 INFO - PUT /rest/api/2/issue/ACM-713 asString Request Duration: 1443ms

 

 

So how to make it work while not hard code?

 

4. Is it possible that, how to make the related date and date time custom field only editable by the Script Runner or maybe as well as some admin users/groups?

1) I'm not sure, you need to test it whether date time fits in date field or not.

2) What type of error did you get when you put two fields in one call?

3) There is a bug in the code. 

Please replace:

 put('/rest/api/2/issue/${issue.id}')

with: 

 put("/rest/api/2/issue/${issue.id}")

Otherwise code ${issue.id} won't be evaluated.

Awesome! it works now! Really appreciate your help on this!

 

BTW, any idea about this?

4. Is it possible that, make the related date and date time custom field only editable by the Script Runner or maybe as well as some admin users/groups?

@Andrzej Wieczorek

Hi

I tried the 

import java.time.ZonedDateTime
import java.time.ZoneId
import java.time.format.DateTimeFormatter

def storyPointsCheckboxFieldId = "customfield_10718"
def storyPointsLastChangeDateFieldId = "customfield_10719"

def customFieldChange = changelog.items.find { item -> item.fieldId == storyPointsCheckboxFieldId }
if (customFieldChange) {
logger.info("Custom field has been updated from value: {} to value: {}", customFieldChange.fromString, customFieldChange.toString)
def currentDateTime = ZonedDateTime.now().format(DateTimeFormatter.ISO_LOCAL_DATE_TIME)
logger.info("Making a request to update custom field id: {} with value: {}", storyPointsLastChangeDateFieldId, currentDateTime)

def result = put('/rest/api/2/issue/ADSD-2')
.header('Content-Type', 'application/json')
.body([
fields:[
(storyPointsLastChangeDateFieldId): currentDateTime
]
])
.asString()
if (result.status == 204) {
logger.info("Successfully updated field {} with value {}", storyPointsLastChangeDateFieldId, currentDateTime)
} else {
logger.error("Failed update field: {}. Jira responded {}: {}", storyPointsLastChangeDateFieldId, result.status, result.body)
}

}

Got a few error right from the start

result:

groovy.lang.MissingPropertyException: No such property: changelog for class: Script1
at Script1.run(Script1.groovy:8)
at Script1$run.call(Unknown Source)
at Script1$run.call(Unknown Source)
at com.adaptavist.sr.cloud.workflow.AbstractScript.evaluate(AbstractScript.groovy:30)
at com.adaptavist.sr.cloud.workflow.AbstractScript$evaluate$0.callCurrent(Unknown Source)
at com.adaptavist.sr.cloud.events.ScriptExecution.run(ScriptExecution.groovy:27)
at ConsoleScriptExecution2_groovyProxy.run(Unknown Source)

Logs:

No such property: changelog for class: Script1 on line 8
Class: com.adaptavist.sr.cloud.events.ConsoleScriptExecution, Config: [:]

 

Could you help me with this? 

Hi,

'changelog' binding is only available for Issue Updated event. Could you please tell me for which event type the script was executed?

Right so I found out that this error is only in the Script Console and in the script listener everything is fine.

Now it just wont update the right fields:

2018-04-25 13:55:52.335 INFO - Custom field has been updated from value: null to value: fyjdgtjrt
2018-04-25 13:55:52.336 INFO - Making a request to update custom field id: customfield_10210 with value: 2018-04-25T13:55:52.335
2018-04-25 13:55:52.603 WARN - PUT request to /rest/api/2/issue/ADSD-2 returned an error code: status: 404 - Not Found
body: {"errorMessages":["Issue does not exist or you do not have permission to see it."],"errors":{}}
2018-04-25 13:55:52.604 INFO - PUT /rest/api/2/issue/ADSD-2 asString Request Duration: 266ms
2018-04-25 13:55:52.605 ERROR - Failed update field: customfield_10210. Jira responded 404: {"errorMessages":["Issue does not exist or you do not have permission to see it."],"errors":{}}

 Manual editing works fine

@Andrzej Wieczorek

Could you direct me to some direction why this sort of error message is appearing? As I mentioned manually every user can edit issues, but for some reason scriptrunner has problems with it.

Could you please try to use 'Permission helper' in order to check if 'ScriptRunner for Cloud' user can edit the issue?

Screen Shot 2018-04-26 at 10.57.48.png

Make sure that you are using ScriptRunner user for that operation, if you are using Current User, please make sure that given user has a permission to edit the issue.

I tried running it as both current user and scriptrunner user. Same issues for both. Permission helper also confirmed that both of them have the right amount of access.

Suggest an answer

Log in or Sign up to answer
How to earn badges on the Atlassian Community

How to earn badges on the Atlassian Community

Badges are a great way to show off community activity, whether you’re a newbie or a Champion.

Learn more
Community showcase
Published yesterday in Jira

Mission-critical battery manufacturer fulfills FAA software requirements with Commit Policy Plugin

EaglePicher Technologies is a leading manufacturer of battery systems for diverse industries like defense, aviation, space or medical. As they operate in highly regulated industries, keeping a clear ...

118 views 0 2
Read article

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