One very common service request or change request approval requirement is to ask for a percentage or majority-based approval. This is something that ServiceNow workflow can do, but it requires a bit of scripting. In the following article, I’ll show you how you can set up some simple scripts in your graphical workflow ‘Approval’ activities to handle these scenarios for any percentage you choose.
The following example scripts are designed to be placed directly in the ‘Approval Script’ field on a workflow ‘Approval’ activity as shown in the screenshot above. The ‘Approval Script’ field is only visible if you select ‘Condition based on script’ from the ‘Wait for’ field. Once you paste the script in, just adjust the ‘approvePercent’ variable for the specific approval percentage needed.
Percentage-based approval with an ‘Approval – User’ activity
This first example assumes you’ve got a group of users grouped into a single workflow activity. These users could all be members of a single group. In fact, this is how I typically do majority approvals for the Change Advisory Board. Regardless of whether the users come from a group or are added individually, they are all combined together when evaluating counts in an ‘Approval – User’ activity.
var approvePercent = 50;
if((counts.approved/counts.total)*100 >= approvePercent){
answer = 'approved';
}
if((counts.rejected/counts.total)*100 > (100 - approvePercent)){
answer = 'rejected';
}
Percentage-based approval with an ‘Approval – Group’ activity
It is also possible (albeit a bit more complex) to do percentage-based approvals with an ‘Approval – Group’ activity. The primary difference here is that you can require a certain percentage from multiple groups. In the example given, each individual group must meet the 50% approval threshold before the activity will return ‘Approved’ and tell the workflow to advance. Any single group not meeting the 50% mark will force a rejection for the entire activity. This took me way more time than it should have to figure out :). Hopefully it saves you a bit of time.
var approvePercent = 50;
var approveCount = 0;
for(var id in groups){
var group = groups[id];
if((group.approved/group.total)*100 >= approvePercent){
//Mark the group approval record 'Approved'
var groupApproval = new GlideRecord('sysapproval_group');
groupApproval.get(id);
groupApproval.approval = 'approved';
groupApproval.update();
approveCount++;
}
if((group.rejected/group.total)*100 > (100 - approvePercent)){
answer = 'rejected';
break;
}
}
//Ensure all groups have approved
if(approveCount == counts.total){
answer = 'approved';
}
I have a question about this, We use an additional approves script for approval, so for instance we have set up in change module that it could be one of three groups doing the approvals, not all at the same time, each group has a different number of people associated with it, Everything works great right now but it set to 1 Person approves the rest aren’t needed, we want to set this style up for a percentage of 60% approved sets Status to approved or 60% rejected sets the status to Closed, will this work for that type of approval?
These scripts do pretty much what you’re describing with one difference. The percentage indicated is for approval, not rejection. If you do what you’re describing you would end up with cases where the percentage wasn’t met either way so the workflow wouldn’t go anywhere.
OK tried this script but it errors out saying Group ID not defined, any thoughts?
I’m not sure what would cause that, but it sounds like you’ve probably got something else in our environment that is interfering. The scripts here don’t even reference anything named ‘Group ID’. You could identify if it was something in your config or something in ServiceNow by setting the same thing up in a ServiceNow demo instance to test.
Thanks Mark, got it worked out, I was using the group script but should have been using the user one, Even though we are using groups, not all the groups approve or reject. Thanks for your wisdom and thanks for all the posts you do, People like me really appreciate you.
Thanks! I’m glad you got it working.
Hello – how can I setup if my ECAB Approval-User has 4 Members (Lets say A, B, C, D)
If A approves then B, C, D go to No Longer Required
else if
B, C, D approve then A should go to No Longer Required
Any help on how to get started here?
Hi Mark
I need something very similar to Waqas i think.
My scenario is that I have approvals set at a value. So approval for <25K could come from one of two groups. Group one is level 2 users and group two are level 1 users (more important. So;
for the 1st group to grant approval 2 users must have approved
OR
for the 2nd group to have approved at least on members of the group must approve.
Can this be done? I'm sure it can with complex javascript, which is why i'm here.
Dave
I want to do similar kind of thing, I want ‘CAB’ approval of user A mandatory if he approves other approvals no longer required or approval should continues until user A approves.
(user A is also a part of ‘Change manager’ group).
Can you please help
thanks in advance
Check out the ‘Making a specific person the key approver’ section in this Guru post…
https://servicenowguru.wpengine.com/scripting/change-management-workflow-approval-scripts-servicenowcom/
What if any rejects? Can I get the additional script? I am using “Percentage-based approval with an ‘Approval – User’ activity”. If ANY one rejects the whole request is rejected.
That use case is also easily accomplished. You just have to change the ‘counts.rejected’ piece to look like this…
answer = 'rejected';
}