Checking Catalog Item Availability from another Catalog Item

LilithP
Tera Contributor

Hello, 

At a high level I want to accomplish the following:

  1. User opens Catalog Item "A"
  2. User answers a precursor question with "No"
    1. Client script checks if "Requested For" user can access Catalog Item "B" using the "Available For" criteria
    2. If yes, redirect to Catalog Item "B"
    3. If not, return none.

So far I have worked out how to follow the table breadcrumbs to the individual user criteria records for Catalog Item "B".
Is there a quick and easy way to check a user against those records to see if they fit conditions, or do I need to pull in all the user data and check each criteria individually (e.g. role, groups, company, etc)?

1 ACCEPTED SOLUTION

Hi @LilithP ,

 

1. create a client callable script include

name: userCriteriaCheckAjax

ChaitanyaILCR_0-1753164366191.png

 

script 

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

    checkUserWithUC: function() {
        var userID = this.getParameter('sysparm_userid') ? this.getParameter('sysparm_userid') : gs.getUserID();
        var userCriteria = [];
        var catm2mgr = new GlideRecord('sc_cat_item_user_criteria_mtom');
        catm2mgr.addEncodedQuery('sc_cat_item=' + this.getParameter('sysparm_catid'));
        catm2mgr.query();
        while (catm2mgr.next()) {
            userCriteria.push(catm2mgr.getValue('user_criteria'));
        }
        return sn_uc.UserCriteriaLoader.userMatches(userID, userCriteria);

    },

    type: 'userCriteriaCheckAjax'
});

 

adjust you client script like this

 

 

adjust 10th line by adding your catalog item sysid (the one which your want to check the user criteria against)

 

I have added an alert for quick chek if this work you can redirect the user to desired catalog item location

 

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

    var requestedForId = g_form.getValue('requested_for');
    var ga = new GlideAjax('global.userCriteriaCheckAjax');
    ga.addParam('sysparm_name', 'checkUserWithUC');
    ga.addParam('sysparm_userid', requestedForId);
    ga.addParam('sysparm_catid', 'put your catalog item sysid here'); // replace with your target catalog item which you wanted to route to

    ga.getXMLAnswer(function(answer) {
        var isEligible = (answer === 'true');
        alert('User eligibility:', isEligible);
		//add your routing logic here
		//g_navigation.open('com.glideapp.servicecatalog_cat_item_view.do?v=1&sysparm_id=01243276837e2210a2dfb5b6feaad333','blank'); you can use this kin of line for redirection of user by replacing the sysid in the url
    });

}

 

Please mark my answer as helpful/correct if it resolves your query.

Regards,
Chaitanya

 

 

 

View solution in original post

5 REPLIES 5

Chaitanya ILCR
Mega Patron

Hi @LilithP ,

 

you can use below line of code in the client callable script include and use glide ajax to get the value (stringified Boolean) 

where 1st parameter being sysid of the user and second is an array of user criteria sysids

 

sn_uc.UserCriteriaLoader.userMatches(<user_sysid>, <[arrya of user criteria sysids]>);

 

hope this make sense and you can take this forward 

 

https://www.servicenow.com/community/servicenow-ai-platform-blog/a-deep-dive-to-user-criteria/ba-p/2...

 

you can refer my response for the similar ask in this below thread

https://www.servicenow.com/community/developer-forum/user-criteria-not-working-for-standard-change-t...

if not share whatever you have completed will help you out

 

 

Please mark my answer as helpful/correct if it resolves your query.

Regards,
Chaitanya

LilithP
Tera Contributor

Thank you for that bit of code, that's what I was looking for.
However, I am getting the following error: ReferenceError: sn_uc is not defined

LilithP
Tera Contributor

Here is what I currently have:

function ucMotmResults(results) {
	var ucSysIds = [];
	while(results.next()) {
		ucSysIds.push(results.getValue('user_criteria'));
	}
	requestedForId = g_form.getValue('requested_for');
	var isEligible = sn_uc.UserCriteriaLoader.userMatches(requestedForId, ucSysIds)
	console.log(isEligible);

}


function onChange(control, oldValue, newValue, isLoading) {
    if (isLoading || newValue == '' || newValue == 'yes') {
        return;
    } else {
		var ucMotm = new GlideRecord('sc_cat_item_user_criteria_mtom');
		ucMotm.addQuery('sc_cat_item.name', 'LIKE', 'Grant Local Admin');
		ucMotm.query(ucMotmResults);
	}
}

I asked ChatGPT about what might be the issue, and it mentioned that sn_uc is a server-side script include. It recommended I redo the code using GlideAjax and gave me this following code (that I get different errors on)

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

  // 1) Gather the user criteria sys_ids
  var ucSysIds = [];
  var ucMotm = new GlideRecord('sc_cat_item_user_criteria_mtom');
  ucMotm.addQuery('sc_cat_item.name', 'LIKE', 'Grant Local Admin');
  ucMotm.query(function(results) {
    while (results.next()) {
      ucSysIds.push(results.getValue('user_criteria'));
    }

    // 2) Now call our server script include
    var requestedForId = g_form.getValue('requested_for');
    var ga = new GlideAjax('UserCriteriaAjax');
    ga.addParam('sysparm_name',           'isUserEligible');
    ga.addParam('sysparm_user_id',        requestedForId);
    ga.addParam('sysparm_criteria_ids',   JSON.stringify(ucSysIds));

    // 3) Process the response
    ga.getXMLAnswer(function(answer) {
      var isEligible = (answer === 'true');
      console.log('User eligibility:', isEligible);
    });
  });
}

Error: LogRocket.min.js:2 Unhandled exception in GlideAjax. <?xml version="1.0" encoding="UTF-8"?><xml error="HTTP Processor class not found: com.glide.processors.xmlhttp.UserCriteriaAjax"/>

 

Hi @LilithP ,

 

1. create a client callable script include

name: userCriteriaCheckAjax

ChaitanyaILCR_0-1753164366191.png

 

script 

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

    checkUserWithUC: function() {
        var userID = this.getParameter('sysparm_userid') ? this.getParameter('sysparm_userid') : gs.getUserID();
        var userCriteria = [];
        var catm2mgr = new GlideRecord('sc_cat_item_user_criteria_mtom');
        catm2mgr.addEncodedQuery('sc_cat_item=' + this.getParameter('sysparm_catid'));
        catm2mgr.query();
        while (catm2mgr.next()) {
            userCriteria.push(catm2mgr.getValue('user_criteria'));
        }
        return sn_uc.UserCriteriaLoader.userMatches(userID, userCriteria);

    },

    type: 'userCriteriaCheckAjax'
});

 

adjust you client script like this

 

 

adjust 10th line by adding your catalog item sysid (the one which your want to check the user criteria against)

 

I have added an alert for quick chek if this work you can redirect the user to desired catalog item location

 

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

    var requestedForId = g_form.getValue('requested_for');
    var ga = new GlideAjax('global.userCriteriaCheckAjax');
    ga.addParam('sysparm_name', 'checkUserWithUC');
    ga.addParam('sysparm_userid', requestedForId);
    ga.addParam('sysparm_catid', 'put your catalog item sysid here'); // replace with your target catalog item which you wanted to route to

    ga.getXMLAnswer(function(answer) {
        var isEligible = (answer === 'true');
        alert('User eligibility:', isEligible);
		//add your routing logic here
		//g_navigation.open('com.glideapp.servicecatalog_cat_item_view.do?v=1&sysparm_id=01243276837e2210a2dfb5b6feaad333','blank'); you can use this kin of line for redirection of user by replacing the sysid in the url
    });

}

 

Please mark my answer as helpful/correct if it resolves your query.

Regards,
Chaitanya