← Script library

Business Rules

Display Business Rule - Calculate Values

Calculate and display values on forms without modifying the database, useful for showing metrics, totals, or derived information.

JavaScript
(function executeRule(current, previous /*null when async*/) {

  // Display Business Rules run when records are fetched for display
  // Values set here are NOT saved to database
  // Use for calculated fields, metrics, and display-only information

  try {
    // Example 1: Calculate time since incident opened
    if (current.opened_at) {
      var openedAt = new GlideDateTime(current.opened_at);
      var now = new GlideDateTime();
      var duration = GlideDateTime.subtract(openedAt, now);

      // Convert to days
      var durationMs = duration.getNumericValue();
      var durationDays = Math.abs(durationMs / (1000 * 60 * 60 * 24));

      // Set display field (create a read-only field for this)
      current.u_days_open = durationDays.toFixed(1);
    }

    // Example 2: Calculate SLA breach risk
    if (current.sla_due) {
      var slaDue = new GlideDateTime(current.sla_due);
      var now = new GlideDateTime();
      var timeUntilDue = GlideDateTime.subtract(now, slaDue);
      var hoursUntilDue = timeUntilDue.getNumericValue() / (1000 * 60 * 60);

      if (hoursUntilDue < 0) {
        current.u_sla_status = 'Breached';
      } else if (hoursUntilDue < 2) {
        current.u_sla_status = 'Critical - ' + hoursUntilDue.toFixed(1) + 'h remaining';
      } else if (hoursUntilDue < 4) {
        current.u_sla_status = 'Warning - ' + hoursUntilDue.toFixed(1) + 'h remaining';
      } else {
        current.u_sla_status = 'On Track - ' + hoursUntilDue.toFixed(1) + 'h remaining';
      }
    }

    // Example 3: Count related records
    var relatedTaskCount = new GlideAggregate('incident_task');
    relatedTaskCount.addQuery('incident', current.sys_id);
    relatedTaskCount.addQuery('active', 'true');
    relatedTaskCount.addAggregate('COUNT');
    relatedTaskCount.query();

    if (relatedTaskCount.next()) {
      current.u_active_tasks_count = relatedTaskCount.getAggregate('COUNT');
    } else {
      current.u_active_tasks_count = '0';
    }

    // Example 4: Calculate priority score (weighted calculation)
    var urgency = parseInt(current.urgency) || 3;
    var impact = parseInt(current.impact) || 3;
    var priorityScore = (urgency * 0.6) + (impact * 0.4);
    current.u_priority_score = priorityScore.toFixed(2);

    // Example 5: Show caller's total incident count
    if (current.caller_id) {
      var callerIncidentCount = new GlideAggregate('incident');
      callerIncidentCount.addQuery('caller_id', current.caller_id);
      callerIncidentCount.addAggregate('COUNT');
      callerIncidentCount.query();

      if (callerIncidentCount.next()) {
        current.u_caller_incident_count = callerIncidentCount.getAggregate('COUNT');
      }
    }

    // Example 6: Calculate estimated resolution time based on category
    var categoryResolutionTimes = {
      'hardware': 4,
      'software': 2,
      'network': 1,
      'database': 6,
      'inquiry': 0.5
    };

    var category = current.category.toString();
    if (categoryResolutionTimes[category]) {
      var estimatedHours = categoryResolutionTimes[category];
      current.u_estimated_resolution_hours = estimatedHours.toString();

      // Calculate estimated completion time
      if (current.opened_at) {
        var opened = new GlideDateTime(current.opened_at);
        opened.addHours(estimatedHours);
        current.u_estimated_completion = opened.getValue();
      }
    }

    // Example 7: Show assignment group workload
    if (current.assignment_group) {
      var groupWorkload = new GlideAggregate('incident');
      groupWorkload.addQuery('assignment_group', current.assignment_group);
      groupWorkload.addQuery('active', 'true');
      groupWorkload.addQuery('state', 'NOT IN', '6,7,8');  // Not resolved/closed/cancelled
      groupWorkload.addAggregate('COUNT');
      groupWorkload.query();

      if (groupWorkload.next()) {
        var workloadCount = groupWorkload.getAggregate('COUNT');
        current.u_group_workload = workloadCount + ' active incidents';

        // Set workload indicator
        if (workloadCount > 50) {
          current.u_group_capacity = 'Over Capacity';
        } else if (workloadCount > 30) {
          current.u_group_capacity = 'High Load';
        } else if (workloadCount > 15) {
          current.u_group_capacity = 'Normal';
        } else {
          current.u_group_capacity = 'Low Load';
        }
      }
    }

    // Example 8: Calculate business hours remaining
    if (current.sla_due) {
      var schedule = new GlideSchedule();
      schedule.load('8-5 weekdays excluding holidays');  // Use your schedule

      var now = new GlideDateTime();
      var slaDue = new GlideDateTime(current.sla_due);

      var businessHoursRemaining = schedule.duration(now, slaDue);
      var businessHours = businessHoursRemaining.getByFormat('HH:mm');

      current.u_business_hours_remaining = businessHours;
    }

  } catch (e) {
    gs.error('Display BR error for incident ' + current.number + ': ' + e.message);
  }

})(current, previous);

How to use it

1. Create a new Business Rule on your table 2. Set When: "display" 3. Leave Insert, Update, Delete, Query unchecked 4. Create display-only fields (read-only) for calculated values 5. Add your calculation logic 6. Test by viewing records - values should appear but not save 7. Consider performance impact - runs on every record view 8. Use GlideAggregate carefully to avoid slow queries

Adapt the table names, fields, and conditions to your instance. Test the behavior in a development environment before using it in production.