How to make attachments mandatory based on user inputs on a service catalog request form before submission in platform or native or portal UI when requesting separately or in order guide?
Note: The functionality explained below uses DOM to achieve desired outcome. From the portal perspective, the approach will only work if the OOB widgets or widgets copied from OOB code are not modified drastically, especially the bits of code which deals with how the attachments added are displayed on browser must not be modified.
STEP1: Create a UI Script which exposes a global function to retrieve count of attachments on platform UI Form
API Name : PlatformUIFormAttachmentUtil
Description : UI Script which exposes a global function to retrieve count of attachments on platform UI Form
function getPlatformUIFormAttachmentsCount() {
try {
/* Counts the number of attachments added to the form using DOM. Control may not go to catch block even if DOM changes on platform UI */
return document.querySelectorAll("ul#header_attachment_list li.attachment_list_items>span").length;
} catch (e) {
return -1;
}
}
STEP2: Create a UI script which provides utility function to validate the count of attachment(s) on a catalog item request form as well as in order guide (if catalog item is requested through it) in the Service Portal
API Name : SPSCItemAttachmentUtil
UI Type : Mobile / Service Portal
Description : This UI script provides utility function to validate the count of attachment(s) on a catalog item request form as well as in order guide (if catalog item is requested through it) in the Service Portal
function SPSCItemAttachmentUtil() {
return {
getSPSCItemAttachmentCount: function (isOrderGuide, g_form) {
/**
If the catalog item is used in an order guide pass the sys_id of the catalog item from the sc_cat_item table.
Returns -1 if the DOM elements or HTML template of portal widgets change in future
Returns 0 if no attachments found in the item.
Returns > 0 or count of attachments, if attachments are found
*/
var length, id;
if(isOrderGuide == true) {
id = g_form.getUniqueValue();
}
try {
if (id == undefined) {
try {
length = angular.element("#sc_cat_item").scope().attachments.length;
} catch (e) {
length = 0; // Scope is undefined if there are no attachments, catch block should set length as 0
}
} else {
if (angular.element("#" + id).length != 0)
length = angular.element("#" + id + " .file-list-wrap ul>li").length;
else
return -1; // DOM element not found
}
} catch (err) {
return -1; // DOM element not found (or) Found elements property invalid
}
return length;
}
};
}
STEP3: Create an onLoad client script which loads the attachment validation utility function on portal widgets
Name : Load AttachValUIScript
Applies to : A Catalog item
UI Type : Mobile / Service Portal
Catalog Item : <> Applies on a Catalog Item view : true function onLoad() { if ((typeof g_service_catalog) != 'undefined') { // Makes sure to execute only on Portal if (g_service_catalog.u_my_sc_attachmentUtils == undefined) { g_ui_scripts.getUIScript('SPSCItemAttachmentUtil').then(function (script) { g_service_catalog.u_my_sc_attachmentUtils = script(); }); } } } STEP4: Create an onSubmit client script which performs mandatory attachment validations on desired catalog item in portal and platform UI when requested individually or in order guide Name : Force Attachment AllUIs Applies to : A Catalog item Catalog Item : <>
Applies on a Catalog Item view : true
Description: Works on Portal and Platform UI. Single script for both UIs. If you want to throw custom error messge in portal to end user, do not check mandatory attachment checkbox in Catalog item in portal settings tab
Script : As shown below. Please read the comments in the below code to know how to modify it as per your requirement
function onSubmit() {
var madatoryAttachmentCondition = true;
// Pass true if you need atleast one attachment irrespective of varaiable fields filled by user.
// Otherwise provide a condition instead of true value : Example -
// (g_form.getValue('Variable1Name') == "Variable1Value" && g_form.getValue('Variable2Name') == "Variable2Value");
var desiredAttachmentCount = 1;
// Must be greater than or equal to 1 to work properly.
// Provide how many minimum number of attachments required from user's end to submit the given catalog item.
var attach_validation_fail_msg = "'<<ItemName>>' request attachment validation failure: <<Custom Error Message Goes Here>>!";
// Replace or pass an error message text as relevant to your business case
if (madatoryAttachmentCondition) {
var attachmentCount;
if ((typeof g_service_catalog) == 'undefined') { // Block executes for Platform View (For both OrderGuide and Direct Request Submission)
attachmentCount = getPlatformUIFormAttachmentsCount();
if (attachmentCount == -1) {
alert("Attachment validation issue! Please contact System Admin!");
return false;
}
if (attachmentCount < desiredAttachmentCount) {
alert(attach_validation_fail_msg);
return false;
} else {
return true;
}
} else { // This block executes in ServicePortal (For both OrderGuide and Direct Request Submission)
var isOrderGuide = g_service_catalog.isOrderGuide();
attachmentCount = g_service_catalog.u_my_sc_attachmentUtils.getSPSCItemAttachmentCount(isOrderGuide, ((isOrderGuide == true)?g_form:""));
if (attachmentCount >= desiredAttachmentCount) {
return true;
} else {
if (attachmentCount == -1)
alert("Attachment validation issue! Please contact System Admin!"); //Review SPSCItemAttachmentUtil UI Script function and check to see if there are any DOM changes after upgrade and update script accordingly to solve the issue;
else
alert(attach_validation_fail_msg);
return false;
}
}
}
}
Once all these changes are done, do remember to check if system is performing mandatory attachment validations as mentioned here:i) During submission of catalog item request in platform UIii) During submission of catalog item request in service portal.iii) Platform UI: Choose the catalog item in an order guide and test during check out or switching to next tab
iv) Portal UI: Choose the catalog item in an order guide and test during submission
After implementing all the 4 scripts, if you need to use this for more catalog items duplicate STEP3 and STEP4 scripts with desired modifications and choose the catalog item on which you need to perform mandatory attachment validations
Final Notes:
Few part(s) of the code references mentioned above were already mentioned in individual articles in the past. But was unable to find the code which works in all scenarios and UIs uniformly.
Reasons why I chose the approach mentioned in the above steps:
- Limited DOM traversal only 2 UI scripts, to make it easier to maintain code. Even if there are changes to UI in future, we may just need to update these two UI scripts in future.
- Both onLoad and onSubmit scripts are required to make it work. Reason for doing this way is:
- * To make sure that UI script loads only when it is required.
- Desktop UI attachment validation script in STEP1 is kept as global as the dynamic loading did not work during on load in service catalog forms.
https://www.servicenow.com/community/developer-articles/how-to-make-attachments-mandatory-based-on-user-inputs-on-a/ta-p/2304663
