Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.
Info

Guide below is only applicable for Report Builder version higher than 1.3.42-AC (Cloud) and 4.11.2 (DC).

Starting from versions mentioned, Report Builder uses secure wrappers for "Window.AP" (Cloud) and "AJS" (DC) methods. Therefore, existing methods need to be updated. Additionally, some of the methods in the Scripted Reports API have become asynchronous, requiring them to be complemented with the "await" statement.

Introduction

We are excited to announce enhancements to the security of Scripted Reports. To improve security, reports now run in an isolated context (iframe) effectively disabling the allow-same-origin policy. While this significantly enhances security, it also introduces some changes to how scripts interact with the environment.

Key Changes

  • Isolated Context: Reports now operate in an isolated environment, restricting access to certain global objects and methods.

    • Cloud: Access to the global window object and window.AP methods is no longer available. For data requests, please use the methods of the window.SR object. For example, there is a set of methods available for Jira data through window.SR.jira. Detailed information about all available methods can be found at the following link.

    • DC: Access to the global window object and window.AJS methods is no longer available. For data requests, please use the methods of the window.SR object. For example, there is a set of methods available for Jira data through window.SR.jira. Detailed information about all available methods can be found at the following link.

    • Some reports that used the global Chart.js library may stop working. To fix this, add the following code at the top of the report script body (adjust the Chart.js version to one you use if needed):

      Code Block
      eval(await fetch('https://cdn.jsdelivr.net/npm/chart.js@2.9.4').then(res => res.text()));

      By the way, this technique can also be applied to other libraries on which the report functionality depends.

  • Asynchronous Methods: Several previously synchronous methods now return Promises. To retrieve the desired data, you must use the await keyword with following methods:

    • SR.convertSecondsToJiraTime

    • SR.getValue

    • SR.getFieldValueExtended

    • SR.getFieldValue

    • SR.getAllFieldsValues

    • SR.getDataByFieldName

    • SR.getValueByFieldName

    • SR.getHostBaseUrl

    • SR.jira.getHostBaseUrl

    • SR.jira.getAssigneeJQLByFieldName

    • SR.jira.getProjectJQLByFieldName

    • SR.fields.getValue

    • SR.fields.getFieldValue

    • SR.fields.getAllFieldsValues

    • SR.fields.getDataByFieldName

    • SR.fields.getValueByFieldName

    • SR.worklog.filterWorklogs

    • SR.worklog.sortWorklogs

  • Omitting await might result in receiving a Promise object instead of the data or encountering a DOMException.

Changes examples

Accessing Data via API

Data access within reports is now handled through the window.SR object. This object provides methods for retrieving various forms of data, including Jira-specific data through the window.SR.jira namespace.

Code example

Previously

Code Block
languagejs
// Fetch audit log data using window.AP object
const response = AP.request('/rest/api/3/auditing/record');

Now

Code Block
languagejs
// Fetch audit log data asynchronously using window.SR object
const response = await SR.request('/rest/api/3/auditing/record');

Please notice await added, as well as AP change to SR.

Accessing report input fields

Accessing report input fields should be asynchronous, and strictly use window.SR object.

Code example if you already use window.SR

Previously

Code Block
languagejs
const selectedIssues = SR.fields.getValueByFieldName('featuresPicker');
const foundIssues = SR.getIssuesByJQL(issue in (${selectedIssues}));

Now

Code Block
languagejs
const selectedIssues = await SR.fields.getValueByFieldName('featuresPicker');
const foundIssues = await SR.getIssuesByJQL(issue in (${selectedIssues}));

Code example if you still used to prefer window.AP

Previously

Code Block
languagejs
const selectedIssues = AP.fields.getValueByFieldName('featuresPicker');
const foundIssues = AP.getIssuesByJQL(issue in (${selectedIssues}));

Now

Code Block
languagejs
const selectedIssues = await SR.fields.getValueByFieldName('featuresPicker');
const foundIssues = await SR.getIssuesByJQL(issue in (${selectedIssues}));

Accessing charting libraries

To see examples of using common charting libraries with new Scripted Reports logic, please follow the documentation for specific libraries provided here Data Analysis and Visualization Libraries

Notes

Some types of content, such as YouTube embedded content, can not run in isolated iFrames, unfortunately. To keep reports using such content, you must disable the setting “Execute report inside secure sandbox“ in a specific report permissions settings. Please follow detailed guide on the setting implementation and disabling details Report execution environment.