Query CMDB_CI & child tables to populate fields on a form

litchick10
Tera Guru

I am trying to create an on change client script so that when the user selects a CI from the cmdb_ci reference field related CI information populates the fields

Here is my code so far:

 function onChange(control, oldValue, newValue, isLoading, isTemplate) {
  if (isLoading || newValue === '') {
      return;
  }

var ci = new GlideRecord('cmdb_ci');
ci.addQuery('sys_id', newValue);
ci.query(function(ci) { // this callback query is used to comply with Central Station (Service Portal)

if(ci.next()) {

// If it's found, fill in the fields with its data

g_form.setValue('u_ciname', ci.name);
g_form.setValue('u_ciitowner', ci.cmdb_ci_business_app.it_application_owner.name);
g_form.setValue('u_civendor', ci.vendor.name);
g_form.setValue('u_ciowner', ci.cmdb_ci_business_app.business_owner.name);
g_form.setValue('u_civersion', ci.cmdb_ci_business_app.version);
g_form.setValue('u_cidescription', ci.cmdb_ci_business_app.u_description);

}

});

}

The ci.name populates but none of the info from the table cmdb_ci_business_app (extends cmdb_ci) populates

 

find_real_file.png

I am just not sure how to query the tables that extend the cmdb_ci

1 ACCEPTED SOLUTION

litchick10
Tera Guru

Solved by Creating a Script Include that calls data from cmdb_ci_Business_application and then called the script from my client script.

Script Includes

var userUtils = Class.create();
userUtils.prototype = Object.extendsObject(global.AbstractAjaxProcessor, {

	userAjaxHandler: function() {
		/*extract parameters from client script call */
		var userSysId = this.getParameter("sysparm_usersysid");
			
		/*call helper function to return the user details based on the required fields*/
		var answer = this.userGroupMembership(userSysId);
		return answer;
	},

	cmdb_ci_business_app_data: function() {
		var cmdbCi = this.getParameter('sysparm_my_cmdb_ci');
		var busApp = new GlideRecord("cmdb_ci_business_app"); //query sys_user table
		busApp.addQuery('sys_id', cmdbCi);
		busApp.query();
		
		if(busApp.next()) {
			var json = new JSON();
			var object = {
				'it_application_owner' : busApp.it_application_owner.name.toString(),
				'bus_owner' : busApp.u_ub_business_owner.name.toString(),
				'vendor' : busApp.vendor.name.toString(),
				'version' : busApp.getValue("u_version"),
				'description' : busApp.getValue("u_description")
			};

			var data = json.encode(object);
			return data;
		}

	},
	
	type: 'userUtils'
});

Client Script

 function onChange(control, oldValue, newValue, isLoading, isTemplate) {
  if (isLoading || newValue === '') {
	//clear out form if value is blank or new form
	g_form.clearValue('u_ciname');
	g_form.clearValue('u_ciitowner');
	g_form.clearValue('u_civendor');
	g_form.clearValue('u_ciowner');
	g_form.clearValue('u_civersion');
	g_form.clearValue('u_cidescription');
      return;
  }
	//clear out existing values when changed to a new value
	//Need to do this here or when changing from an Business App to any other class or only CI name updates
	g_form.clearValue('u_ciitowner');
	g_form.clearValue('u_civendor');
	g_form.clearValue('u_ciowner');
	g_form.clearValue('u_civersion');
	g_form.clearValue('u_cidescription');
 
	//Populates CIs in both Business Application class and all other classes. 
	var ci  = new GlideRecord('cmdb_ci');
	ci.addQuery('sys_id', newValue);
	ci.query(function(ci) { 
	if(ci.next()){
		g_form.setValue('u_ciname', ci.name);
	}});

	//Call to Script Include to get cmdb values
	var ga = new GlideAjax('userUtils'); //Script include name
	ga.addParam('sysparm_name', 'cmdb_ci_business_app_data');//sysparm_name is the name of the function in the script include to call
	ga.addParam('sysparm_my_cmdb_ci', newValue);
	ga.getXML(mycallbackFunction);
	
 }
	function mycallbackFunction(response){
		var answer = response.responseXML.documentElement.getAttribute('answer');
		var returneddata = JSON.parse(answer);
		//Sets the field values for applications that are business applications. NOTE: Non Business Applications do not have fields with these data points
        g_form.setValue('u_ciitowner', returneddata.it_application_owner);
        g_form.setValue('u_civendor', returneddata.vendor);   
        g_form.setValue('u_ciowner', returneddata.bus_owner); 
        g_form.setValue('u_civersion', returneddata.version); 
        g_form.setValue('u_cidescription', returneddata.description);
}

 

View solution in original post

4 REPLIES 4

Ankur Bawiskar
Tera Patron
Tera Patron

Hi,

you can only dot walk 1 level in client script.

Why not bring the fields of cmdb_ci on the form using dot walk and make those readonly? no need to populate and those would change automatically when ci is changed

Mark Correct if this solves your issue and also mark 👍 Helpful if you find my response worthy based on the impact.
Thanks
Ankur

Regards,
Ankur
Certified Technical Architect  ||  9x ServiceNow MVP  ||  ServiceNow Community Leader

I'm not sure I understand what you mean by bring it onto the form via dot walk.  I did create a business rule that populates these on save but I'd really like the info to populate on change. 

I am fairly new at SNOW dev so I may just not be understanding what you are suggesting.

 

litchick10
Tera Guru

Solved by Creating a Script Include that calls data from cmdb_ci_Business_application and then called the script from my client script.

Script Includes

var userUtils = Class.create();
userUtils.prototype = Object.extendsObject(global.AbstractAjaxProcessor, {

	userAjaxHandler: function() {
		/*extract parameters from client script call */
		var userSysId = this.getParameter("sysparm_usersysid");
			
		/*call helper function to return the user details based on the required fields*/
		var answer = this.userGroupMembership(userSysId);
		return answer;
	},

	cmdb_ci_business_app_data: function() {
		var cmdbCi = this.getParameter('sysparm_my_cmdb_ci');
		var busApp = new GlideRecord("cmdb_ci_business_app"); //query sys_user table
		busApp.addQuery('sys_id', cmdbCi);
		busApp.query();
		
		if(busApp.next()) {
			var json = new JSON();
			var object = {
				'it_application_owner' : busApp.it_application_owner.name.toString(),
				'bus_owner' : busApp.u_ub_business_owner.name.toString(),
				'vendor' : busApp.vendor.name.toString(),
				'version' : busApp.getValue("u_version"),
				'description' : busApp.getValue("u_description")
			};

			var data = json.encode(object);
			return data;
		}

	},
	
	type: 'userUtils'
});

Client Script

 function onChange(control, oldValue, newValue, isLoading, isTemplate) {
  if (isLoading || newValue === '') {
	//clear out form if value is blank or new form
	g_form.clearValue('u_ciname');
	g_form.clearValue('u_ciitowner');
	g_form.clearValue('u_civendor');
	g_form.clearValue('u_ciowner');
	g_form.clearValue('u_civersion');
	g_form.clearValue('u_cidescription');
      return;
  }
	//clear out existing values when changed to a new value
	//Need to do this here or when changing from an Business App to any other class or only CI name updates
	g_form.clearValue('u_ciitowner');
	g_form.clearValue('u_civendor');
	g_form.clearValue('u_ciowner');
	g_form.clearValue('u_civersion');
	g_form.clearValue('u_cidescription');
 
	//Populates CIs in both Business Application class and all other classes. 
	var ci  = new GlideRecord('cmdb_ci');
	ci.addQuery('sys_id', newValue);
	ci.query(function(ci) { 
	if(ci.next()){
		g_form.setValue('u_ciname', ci.name);
	}});

	//Call to Script Include to get cmdb values
	var ga = new GlideAjax('userUtils'); //Script include name
	ga.addParam('sysparm_name', 'cmdb_ci_business_app_data');//sysparm_name is the name of the function in the script include to call
	ga.addParam('sysparm_my_cmdb_ci', newValue);
	ga.getXML(mycallbackFunction);
	
 }
	function mycallbackFunction(response){
		var answer = response.responseXML.documentElement.getAttribute('answer');
		var returneddata = JSON.parse(answer);
		//Sets the field values for applications that are business applications. NOTE: Non Business Applications do not have fields with these data points
        g_form.setValue('u_ciitowner', returneddata.it_application_owner);
        g_form.setValue('u_civendor', returneddata.vendor);   
        g_form.setValue('u_ciowner', returneddata.bus_owner); 
        g_form.setValue('u_civersion', returneddata.version); 
        g_form.setValue('u_cidescription', returneddata.description);
}

 

Glad that it worked.

So what I was referring is you can configure the form layout and bring the relevant fields such as Owner, Vendor, Description by dot walking the CI field

In this manner whenever the CI is changed it would automatically show the values for those fields for that CI; also when you change it would work

Mark Correct if this solves your issue and also mark 👍 Helpful if you find my response worthy based on the impact.
Thanks
Ankur

Regards,
Ankur
Certified Technical Architect  ||  9x ServiceNow MVP  ||  ServiceNow Community Leader