HR Leave · Australia

Script — HRLXProLeaveUtilsV2.js

ServiceNow Australia · Custom app · Arabic + English readable · scripts copy/paste ready

App typeCustom
Scopex_786686_hr_leave
sys_idc84db0e8839f0b509f02b0d6feaad3c9
Replace{BASE} = your instance
Instance URLs Studio Business Rules Client Scripts Script Includes

Copy this script into ServiceNow under application x_786686_hr_leave (Australia). Table/API names already use the current scope.

Source: src/server/script_includes/HRLXProLeaveUtilsV2.js

/**
 * Script Include: HRLXProLeaveUtilsV2
 * Scope: x_786686_hr_leave
 * Application: Custom · Scope: x_786686_hr_leave · sys_id: c84db0e8839f0b509f02b0d6feaad3c9
 * Client callable: true  (extends AbstractAjaxProcessor)
 * Purpose: Leave calculations + helpers (business days, approver, balance, audit).
 *
 * Create in ServiceNow:
 *   Studio > Create Application File > Script Include
 *   Name: HRLXProLeaveUtilsV2
 *   Client callable: checked
 */
var HRLXProLeaveUtilsV2 = Class.create();
HRLXProLeaveUtilsV2.prototype = Object.extendsObject(global.AbstractAjaxProcessor, {

    /**
     * Count business days (Mon-Fri) inclusive between two date strings.
     * @param {string} startDate - 'yyyy-MM-dd'
     * @param {string} endDate   - 'yyyy-MM-dd'
     * @return {number}
     */
    calculateBusinessDays: function (startDate, endDate) {
        if (!startDate || !endDate) return 0;
        var start = new GlideDateTime(startDate + ' 00:00:00');
        var end = new GlideDateTime(endDate + ' 00:00:00');
        if (end.before(start)) return 0;

        var days = 0;
        var cursor = new GlideDateTime(start);
        while (!cursor.after(end)) {
            var dow = cursor.getDayOfWeekLocalTime(); // 1=Mon ... 7=Sun
            if (dow >= 1 && dow <= 5) days++;
            cursor.addDaysLocalTime(1);
        }
        return days;
    },

    /**
     * Resolve the approver (employee's manager) and set it on the record.
     * @param {GlideRecord} currentRecord - leave request record
     */
    setApproverFromEmployee: function (currentRecord) {
        var empId = currentRecord.getValue('u_employee_ref');
        if (!empId) return;
        var emp = new GlideRecord('x_786686_hr_leave_employee_v2');
        if (emp.get(empId) && emp.u_manager) {
            currentRecord.u_approver_user = emp.getValue('u_manager');
        }
    },

    /**
     * Write an audit row when the state changes.
     */
    auditStateChange: function (leaveSysId, oldState, newState, eventType) {
        var a = new GlideRecord('x_786686_hr_leave_audit_v2');
        a.initialize();
        a.u_leave_ref = leaveSysId;
        a.u_old_state = oldState || '';
        a.u_new_state = newState || '';
        a.u_event_type = eventType || 'state_change';
        a.u_actor = gs.getUserID();
        a.insert();
    },

    /**
     * Recalculate remaining balance for an employee/year.
     */
    recalculateBalance: function (employeeSysId, year) {
        var used = this._sumApprovedDays(employeeSysId, year);
        var bal = new GlideRecord('x_786686_hr_leave_bal_v2');
        bal.addQuery('u_employee_ref', employeeSysId);
        bal.addQuery('u_year', year);
        bal.query();
        if (bal.next()) {
            bal.u_used = used;
            bal.u_remaining = parseInt(bal.getValue('u_entitled') || 0, 10) - used;
            bal.update();
        }
    },

    _sumApprovedDays: function (employeeSysId, year) {
        var total = 0;
        var gr = new GlideAggregate('x_786686_hr_leave_req_v2');
        gr.addQuery('u_employee_ref', employeeSysId);
        gr.addQuery('u_state', 'approved');
        gr.addQuery('u_start_date', '>=', year + '-01-01');
        gr.addQuery('u_start_date', '<=', year + '-12-31');
        gr.addAggregate('SUM', 'u_days_count');
        gr.query();
        if (gr.next()) total = parseInt(gr.getAggregate('SUM', 'u_days_count') || 0, 10);
        return total;
    },

    /**
     * GlideAjax entry point for client-side day calculation.
     */
    ajaxGetBusinessDays: function () {
        return this.calculateBusinessDays(
            this.getParameter('sysparm_start'),
            this.getParameter('sysparm_end')
        );
    },

    type: 'HRLXProLeaveUtilsV2'
});