Name

global.CIUtils

Description

Utility class for working with configuration items

Script

var CIUtils = Class.create();

CIUtils.prototype = {

  initialize: function() {
      this.maxDepth = gs.getProperty('glide.relationship.max_depth', 10); // how deep to look
      this.currentDepth = 0;

      this.mepAll = new Object(); // list of manual endpoints
      this.services = new Object(); // list of affected services
      this.parents = new Object(); // already checked parents
      this.maxSize = gs.getProperty('glide.relationship.threshold', 1000); // how many records to return
      this.added = 0; // track how many added, since can't get size() for an Object
  },

  /**
   * Determine which business services are affected by a specific CI
   * 
   * Inputs:
   *    id is the sys_id of a configuration item (cmdb_ci)
   *    customValues is an object allowing for maxDepth 
   *        and maxSize to be set individually per function call
   *        Members must be named "maxDepth" and "maxSize"
   *
   * Returns:
   *    an array of sys_id values for cmdb_ci_server records downstream of
   *    (or affected by) the input item
   */

  servicesAffectedByCI: function(id, customValues) {
      var ci = new GlideRecord("cmdb_ci");
      if (ci.get(id)) {
  		
          if (customValues) {
              this.services = SNC.CMDBUtil.getRelatedServices(id, 
  															customValues.maxDepth ? customValues.maxDepth : this.maxDepth,
  														    customValues.maxSize ? customValues.maxSize : this.maxSize);
          } else {
              this.services = SNC.CMDBUtil.getRelatedServices(id, this.maxDepth, this.maxSize);
          }
      } else {
  		return [];
  	}

      // Add services associated by service mapping
      this.addServicesAssociatedByServiceMapping(id);
  	// convert Java set to javascript array of affected services
      return j2js(this.services);
  },

  /**
   * Add business services associated to the CI by service mapping. Service mapping
   *  maintains service models using the CMDB service model API
   *  Input: 
   *      id - the CI sys_id 
   *  Output:
   *      svcarr - list of associated services 
   */
  addServicesAssociatedByServiceMapping: function(id) {
      if (!GlidePluginManager.isActive('com.snc.service-mapping'))
          return;

      // Add service associations created by service mapping
      var bsm = new SNC.BusinessServiceManager();
      var svcList = bsm.getServicesAssociatedWithCi(id, true);
      for (var iterator = svcList.iterator(); iterator.hasNext();) {
          var svc = iterator.next();
          this._addService(svc, this.services);
      }
  },
  /**
   * Determine which business services are affected by a task
   * 
   * Inputs:
   *    task is a task GlideRecord (e.g., incident, change_request, problem)
   *
   * Returns:
   *    an array of sys_id values for cmdb_ci_server records downstream of
   *    (or affected by) the configuration item referenced by the task's cmdb_ci field
   */

  servicesAffectedByTask: function(task) {
      var id = task.cmdb_ci.toString();
      return this.servicesAffectedByCI(id);
  },

  _addParentServices: function(value, services, currentDepth, customValues) {
      // PRB1452345
      if (value === undefined || value === 'undefined') {
          gs.error("Expected sys_id to be defined, instead found undefined");
          return;
      }
      if (this.parents[value]) // already checked?
          return;
      else this.parents[value] = true;

      //use custom values if provided
      var maxDepth = 0;
      var maxSize = 0;
      if (customValues && customValues.maxDepth && !isNaN(customValues.maxDepth)) {
          maxDepth = customValues.maxDepth;
      } else {
          maxDepth = this.maxDepth;
      }
      if (customValues && customValues.maxSize && !isNaN(customValues.maxSize)) {
          maxSize = customValues.maxSize;
      } else {
          maxSize = this.maxSize;
      }

      if (this.added >= maxSize)
          return;
      else {
          currentDepth++;
          var al = SNC.CMDBUtil.getRelatedRecords(value, "", "cmdb_ci", "cmdb_ci", "child"); // returns ArrayList
          if (al.size() > 0) {
              //collect manual end points
              var mep = new GlideRecord('cmdb_ci_endpoint');
              mep.addQuery('sys_id', al);
              mep.query();
              while (mep.next()) {
                  this.mepAll[mep.sys_id] = true;
              }
              // first add the unique services
              var kids = new GlideRecord('cmdb_ci_service');
              kids.addQuery('sys_id', al);
              kids.query();
  			while (kids.next()) {
  				var str = kids.sys_id;
  				if (!services[str]) {
  					this._addService(str, services);
  				}
  				if (this.added >= maxSize)
  					return;
  				if (currentDepth < maxDepth)
  					this._addParentServices(str, services, currentDepth);
  			}

              // now check parents of non-services
              for (var i = 0; i < al.size(); i++) {
                  var parent = al.get(i);
                  if (parent) {
                      var str = parent + "";
                      if (!services[str]) // if already in "services", we already checked its parents
                          if (this.mepAll[str] && currentDepth - 1 < maxDepth)
                              this._addParentServices(str, services, currentDepth - 1);
                          else if (currentDepth < maxDepth)
                              this._addParentServices(str, services, currentDepth);
                  }
              }
          }
      }
  },

  _addService: function(id, services) {
      if (services.get(id))
  	   return;
      services.add(id);
      this.added++;
  },

  /**
   * Returns an array of IP addresses belonging to the given CI (including 127.0.0.1).
   */
  getIPs: function(ci_sys_id) {
      var ipgr = new GlideRecord('cmdb_ci_ip_address');
      ipgr.addQuery('nic.cmdb_ci', ci_sys_id);
      ipgr.addQuery('ip_version', '4');
      ipgr.addQuery('install_status', '<>', 100);
      ipgr.addQuery('nic.install_status', '<>', 100);
      ipgr.query();
      var result = [];
      while (ipgr.next())
          result.push(ipgr.getValue('ip_address'));
      result.push('127.0.0.1');
      return result;
  },

  canShowRefreshServicesUIAction: function(tableClassName) {
      var ciTable = gs.getProperty('com.snc.task.refresh_impacted_services');
      if (ciTable) {
          var tableList = ciTable.split(',');
          for (var i = 0; i < tableList.length; ++i) {
              var table = tableList[i];
              table = table.trim();
              if (tableClassName + "" === table)
                  return true;
          }
      } else
          return false;
  },

  refreshImpactedServices: function(current) {
      this.removeImpactedServices(current.sys_id);
      if (!current.cmdb_ci.nil())
          this.addImpactedServices(current.sys_id, this.servicesAffectedByCI(current.cmdb_ci));
  },

  removeImpactedServices: function(taskSysId) {
      var m2m = new GlideRecord('task_cmdb_ci_service');
      m2m.addQuery('task', taskSysId);
      m2m.addQuery('manually_added', false);
      m2m.deleteMultiple();
  },

  addImpactedServices: function(taskSysId, services) {
      //Remove any manually added services from services array so we do not get unique key violation
      var manualServices = this.getManuallyAddedServices(taskSysId);
      if (manualServices.length > 0) {
          services = services.filter(function(el) {
              return manualServices.indexOf(el) === -1;
          });
      }

      var m2m = new GlideRecord('task_cmdb_ci_service');
      for (var i = 0; i < services.length; i++) {
          m2m.initialize();
          m2m.task = taskSysId;
          m2m.cmdb_ci_service = services[i];
          m2m.manually_added = false;
          m2m.insert();
      }
  },

  getManuallyAddedServices: function(taskSysId) {
      var manualServices = [];

      if (!taskSysId)
          return manualServices;

      var manualServicesGr = new GlideRecord('task_cmdb_ci_service');
      manualServicesGr.addQuery('task', taskSysId);
      manualServicesGr.addQuery('manually_added', true);
      manualServicesGr.query();

      while (manualServicesGr.next())
          manualServices.push(manualServicesGr.cmdb_ci_service + "");

      return manualServices;
  },

  refreshImpactedServicesFromAffectedCIs: function(current) {
      if (!current || !current.isValidRecord()) {
          gs.error("[CIUtils.refreshImpactedServicesFromAffectedCIs] : Invalid parameter");
          return;
      }

      var services = this._getImpactedServicesFromAffectedCIs(current.sys_id + '');
      this.removeImpactedServices(current.sys_id + '');
      if (services) {
          this.addImpactedServices(current.sys_id + '', services);
      }
  },

  _getImpactedServicesFromAffectedCIs: function(taskId) {
      var impactedServices = {};
      //fetching records from the svc_ci_assoc table
      //this table has entries when Service Mapping is being used
      //it has all CIs associated with a particular application service
      var serviceConfigItemAssocGr = new GlideAggregate("svc_ci_assoc");
      serviceConfigItemAssocGr.addQuery("JOINsvc_ci_assoc.ci_id=task_ci.ci_item!task=" + taskId);
      serviceConfigItemAssocGr.groupBy("service_id");
      serviceConfigItemAssocGr.query();

      while (serviceConfigItemAssocGr.next())
          impactedServices[serviceConfigItemAssocGr.service_id + ""] = null;

      return Object.keys(impactedServices);
  },

  type: 'CIUtils'

};

Sys ID

c93a87d20a0a0b1d0196af61b0ca8db5

Offical Documentation

Official Docs: