Create
cancel
Showing results for 
Search instead for 
Did you mean: 
Sign up Log in

DIY REST API to update Customer Request Type for issue

Requirements

This article is for JSM Data Center with ScriptRunner. You will need scripting experience.

Background

When I first tried to update the Customer Request Type (CRT) field with a script, it was a challenge, to say the least. There's a kind of key value that it stores for the CRT field for an issue, not an ID, not the name. It looks something like this:

lowercaseprojectkey/33e5ca1a-54e2-4aq4-8351-1c82c52erf98

It is not a string, though.

I saw on the Community that people would like to have a REST API for updating the CRT.

Use cases / Audience

Granted, this REST API article does require that you have ScriptRunner. Those of you who need the REST API because you don't have something like ScriptRunner, won't find this of use.

Those of you who do have ScriptRunner and want to make the ability to update CRTs in bulk with, for example, a csv file (in another script) from your own machine (not the server), or want to make that ability available to users, this is for you.

Create

You'll need to create (at least) three pieces for this to work.

  • Resource to the local database
  • Script
    • Can be inline
    • I prefer to keep all my scripts in the Script Editor. If you do use this method, you'll need to put the script at the root level in Script Editor, not under a folder.
  • REST Endpoint

Resource

Create a Resource in ScriptRunner to the Local database and call the Pool name local. No need for any additional script (unless you want).

resource.png

Script

Caveat: I have a separate script to do a SQL query, but I did my best to embed that code in this script so that it's all in one for you. I haven't tested it like this, though.

Changes you'll need to make:

  • Customer Request Type field ID
    • You'll need to put the ID for your instance's field
    • Trust me; it's much easier to code with the ID than the name
    • To find the ID with the UI
      • navigate to the Admin console (Issues)
      • then Custom Fields
      • search for Customer Request Type
      • hover over one of the links for the field
      • look at the end of the URL that pops up in your browser (usually bottom left)
  • SQL statement
    • Will vary with database type
    • My example is Oracle PLSQL
  • Optional - output
    • You can change the output if you like
    • I have it simply outputting true/false for if it errors or not

Advanced apologies for  lack of indentation since Atlassian's code block format doesn't handle them when pasting in code.

import com.onresolve.scriptrunner.runner.rest.common.CustomEndpointDelegate
import groovy.json.JsonBuilder
import groovy.transform.BaseScript

import javax.servlet.http.HttpServletRequest
import javax.ws.rs.core.MultivaluedMap
import javax.ws.rs.core.Response

import java.net.URLDecoder
import org.apache.commons.lang3.StringUtils

import com.atlassian.jira.component.ComponentAccessor
import com.atlassian.jira.issue.CustomFieldManager
import com.atlassian.jira.issue.fields.CustomField
import com.atlassian.jira.issue.Issue
import com.atlassian.jira.issue.IssueManager
import com.atlassian.jira.issue.ModifiedValue
import com.atlassian.jira.issue.util.DefaultIssueChangeHolder

import com.onresolve.scriptrunner.db.DatabaseUtil
import groovy.sql.Sql

@BaseScript CustomEndpointDelegate delegate

updateIssueRequestType(
httpMethod: "PUT", groups: ["jira-administrators"]
) { MultivaluedMap queryParams, String body, HttpServletRequest request ->
// validate there are parameters
def param = getAdditionalPath(request)
assert param =~ "^/[a-zA-Z0-9_]+"

// split the URI into parts to get the parameters at the end
String[] arr = param.split("/")
String issuekey = arr[-2] //next to last parameter
String requestTypeName = URLDecoder.decode(arr.last()) //last parameter

// get Customer Request Type (CRT) field object
CustomFieldManager customFieldManager = ComponentAccessor.getCustomFieldManager()
//************************************************************************************
// Change value to your customfield's ID
CustomField customField = customFieldManager.getCustomFieldObject("customfield_12345")
//************************************************************************************

// get issue object based on provided issue key
IssueManager issueManager = ComponentAccessor.getIssueManager()
Issue issue = issueManager.getIssueByCurrentKey(issuekey)

// get Customer Request Type (CRT) key based on name and project key
String[] arrIssueKey = param.split("-")
String projectKey = arrIssueKey[0].toLowerCase()
// remove leading forward slash
projectKey = StringUtils.removeStart(projectKey, "/")

//-----------------------------------------------------------------------------
// Here's my embedded SQL script. No guarantees this part works as expected.

// Get the request type key from a SQL query
// backslash \ at the end of the line makes the line continuous
// This is PLSQL for Oracle. It will vary from MySQL or other dbs
String sql = "SELECT (vp.KEY || '/' || vpf.KEY) AS requestTypeKey\
FROM AO_54307E_VIEWPORT vp\
INNER JOIN AO_54307E_VIEWPORTFORM vpf ON vp.ID=vpf.VIEWPORT_ID\
WHERE ROWNUM <= 1 AND vp.KEY = '${projectKey}' AND vpf.NAME = '${requestTypeName}'"

def rows = DatabaseUtil.withSql('local') { sql ->
sql.rows(strSQL)
}

if (!rows.size()) {
log.debug "No results returned"
return
}

def requestTypeKey
rows.collect{ row ->
requestTypeKey = row.getAt(0)
}
//-----------------------------------------------------------------------------

// get the request type object from the key
def requestType = customField.getCustomFieldType().getSingularObjectFromString(requestTypeKey)

Boolean blnResult = false

try {
// update CRT value in issue
customField.updateValue(null, issue, new ModifiedValue(issue.getCustomFieldValue(customField), requestType), new DefaultIssueChangeHolder())
blnResult = true
} catch (Exception e) {
blnResult = false
}
// return result of true/false if field was updated for issue
return Response.ok(new JsonBuilder([result: blnResult]).toString()).build()
}

 

REST Endpoint

Create your custom REST endpoint with the above script either inline or saved in the Script Editor.

endpoint.png

Run

To access the REST endpoint, you'll use a variation of this URI:

<jira_base_url>/rest/scriptrunner/latest/custom/updateIssueRequestType/<issuekey>/<requestTypeName>
For example:

Conclusion

Your script may take some tweaking and testing, but hopefully some of you will find this useful. If you do, please Like this article.

0 comments

Comment

Log in or Sign up to comment
TAGS
AUG Leaders

Atlassian Community Events