Relative duration and pause condition

Sebastiaan de V
Kilo Guru

The wiki (Defining Relative Durations - ServiceNow Wiki) clearly states: "Pause conditions are not compatible with Relative Durations" I want to understand why as this is the most clear and straight forward way to implement the customer requirements on SLA. As far as I know, the relative duration is calculated only once to fill in the planned end time. When I update the TaskSLAController script (on a developer instance off course) to not consider the relative duration:

if (/*taskSLAgr.sla.duration_type != '' ||*/ !taskSLAgr.sla.pause_condition)

                // relative duration SLAs, and those without pause conditions, cannot pause

                return;

and

// a "relative-duration" SLA cannot pause, whatever conditions might be in the SLA Definition record

    /*   if (taskSLAgr.sla.duration_type != '')

                return; */

Pausing of the task sla seems to work fine, including the calculation of pause and elapsed times.

Can you explain me where this will/could go wrong? I am also looking for alternatives to implement relative duration SLAs with pause conditions.

15 REPLIES 15

Hi Guys,



Although I understand explanation of drbryson, this was a specific requirement to be implemented, despite functional and technical impact. I have created the following solution:



1. Add a reference field to the SLA definition, this is a reference to a relative duration. I use the field name "Calculated duration" (u_calculated_duration). This way they original functionality for a relative duration and user specified duration can still be used as before. I added and updated the UI policies for the SLA definition to show to correct fields en enable the pause condition when a Calculated duration is selected.



WM_-_Next_business_day___ServiceNow.png



2. Create a new version of the TaskSLA Script Include to recalculate the planned end time (breach time) as also mentioned here: ServiceNow KB: Calculating the Planned end time of an SLA in the 2011 SLA Engine (KB0550781)



So I in the function _recalculateEndTime I replaced this:



if (this.taskSLAgr.sla.duration_type == '') {


  // plain end-time extended by total (business) pause time


  var newDuration = this.taskSLAgr.sla.duration.dateNumericValue() + totalPauseTimeMS; // milliseconds


  dc.calcDuration(newDuration / 1000);


}



With this



/**


  * Author: sebastiaan.de.vlaam@plat4mation.com


  * Description: custom funcitonality to support pausing of relative SLAs.


  * The approach is to only use the (custom) relative duration during the initial plannend end time calcualtion


  * and treat the SLA as a "user specified" duration SLA for all other scripts.   Changes on the start script are contained


  * in START and END comment blocks


  * Requirements: a reference field on the SLA definition referencing cmn_relative_duration called "u_calculated duration"


  **/



  /* START customizations */


  if (this.taskSLAgr.sla.duration_type == '' ) {


            if (this.taskSLAgr.sla.u_calculated_duration) {


                      /* A user defined calculated duration is selected, so use that for calculated end time


                      * copies the same functionality as for a "normal" relative duration


                      */



                      // Store the current value of current


                      var ocurrent = null;


                      if (typeof current !== 'undefined') ocurrent = current;



                      // Determine whether we want to set current to the "task sla"   or the "table" record associated with the "SLA Definition"


                      if (this.taskSLAgr.sla.relative_duration_works_on == "SLA record") current = this.taskSLAgr;


                      else current = this.taskSLAgr.task.getRefRecord();



                      // Perform calculation using the revised value of current, uses the custom relative duration


                      dc.calcRelativeDuration(this.taskSLAgr.sla.u_calculated_duration);



                      / After the calculation, reset current back to its old value


                      if (ocurrent) current = ocurrent;



                      /* Pause time needs to consider the schedule so we calculate a new end time


                      * based on the end time provided by the realtive duration but considering the


                      * schedule, which is ignored by the relative duration calculation.


                      */


                      var schedule = new GlideSchedule();


                      schedule.load(this.taskSLAgr.schedule, tz, null);        


                      var totalMS = this._getDurationMS(schedule.duration(this._glideDateTime(this.taskSLAgr.start_time), dc.getEndDateTime()))


                      totalMS = totalMS + totalPauseTimeMS


                      dc.calcDuration(totalMS / 1000);


            }


            else {


                      // plain end-time extended by total (business) pause time


                      var newDuration = this.taskSLAgr.sla.duration.dateNumericValue() + totalPauseTimeMS; // milliseconds


                      dc.calcDuration(newDuration / 1000);


            }


  }


  /* END customization */



3. I added this little support function to the TaskSLA Script include:



/**


  * Author: sebastiaan.de.vlaam@plat4mation.com


  * Description: Convert duration object to milliseconds, works on GlideDurations used in scripts


  * Parameters: duration, a GlideDuration object


  * Returns: the duration in milliseconds


  **/


  _getDurationMS: function(duration) {


            var gdt = new GlideDateTime(duration.getValue());


            return gdt.getNumericValue();


  },



Solution is working for the use case it was implemented for. Please be aware this is a change in the "SLA engine", thus provides a risk on updates or upgrades. I'm curious to find out if there are any use - or test cases that are not working due to this change.



Regards,


Sebastiaan


Hi Sebastiaan,



Point 2: Create a new version of the TaskSLA Script Include to recalculate the planned end time



means we have two script include to calculate SLA? or you mean, changing existing TaskSLA script include?



Thanks


Ak


Hi Amdadul,



As a best practice to "update" an existing script include use the following procedure:


1. Disable out of the box script (active = false)


2. Insert & Stay to create a new version and keep same name


3. Update the new script



This way you have two scripts with the same name, TaskSLA in this case. One inactive (the out of the box script) and one active (the inserted script). You only update the new script and leave the out of the box (and now inactive) script. This ensures that you always get any bug fixes or updates which ServiceNow patches and upgrades.



You cannot have two active script includes with the same name.



Regards,


Sebastiaan



PS - Please mark Helpful, Like, or Correct Answer if applicable.


Hi Sebastiaan,


Thanks heaps for your reply. I have followed your instruction on Fuji Patch 3, seems like its not working. But If I follow same instruction on my dev cloud instance (Helsinki) it works fine. Could you please confirm if this solution works for Fuji Patch 3?


Thanks


Ak


Thanks for the help. It works now with Fuji patch 3.