- Post History
- Subscribe to RSS Feed
- Mark as New
- Mark as Read
- Bookmark
- Subscribe
- Printer Friendly Page
- Report Inappropriate Content
on 08-08-2018 11:35 AM
I wanted to put together a brief article around integrating ServiceNow with Dell's TechDirect warranty API to collect an asset's Warranty Expiration date. In this article, I will detail the Outbound REST message setup, scripting the business rules and UI action I used. This will be some basic REST work, but I thought I would share. Please feel free to comment if you see errors or improvements I can make.
Obtain your Dell API key from Dell TechDirect. Once you are approved for a key, Dell will provide the key along with some code samples (see the attached PDF). Currently I have a key only for their Warranty API.
Setting up the Outbound REST message and GET method:
- Create a new Outbound REST message with endpoint https://sandbox.api.dell.com/support/assetinfo/v4 (Dell will initially setup you up within their sandbox environment and then migrate your work to their prod endpoint)
- Add HTTP headers for Accept and Content-Type, both with a value of application/json
- Save the new record, which will create your default GET method.
- Obtaining the warranty end date requires endpoint: https://sandbox.api.dell.com/support/assetinfo/v4/getassetwarranty/{id}?apikey={apikey}
- Setup your GET method for some test runs with the following attributes:
- Endpoint: https://sandbox.api.dell.com/support/assetinfo/v4/geassetwarranty/${id}
- HTTP headers for Accept and Content-Type, both with a value of application/json
- HTTP Query Parameter for apikey where the value is your key (We'll remove this parameter later and store the key as a property).
- Variable substitutions for id with a value of a valid service tag
You want to grab the EndDate value from AssetEntitlementData[0] array.
Setting up a Business Rule to update Warranty Expiration
I decided to setup an On Before Insert and Update business rule to run when the Warranty Expiration field is empty and the Serial Number is not empty and the workstation is not a Mac.
(function executeRule(current, previous /*null when async*/) {
var st = current.serial_number;
try {
var r = new sn_ws.RESTMessageV2('DellTechDirect', 'GET');
r.setStringParameterNoEscape('id', st);
r.setQueryParameter('apikey', gs.getProperty('DellTechDirectKey'));
r.setHttpTimeout(10000);
r.setEccParameter('skip_sensor', true);
var response = r.execute();
var responseBody = response.getBody();
var httpStatus = response.getStatusCode();
gs.info("Status = " + httpStatus);
gs.info("Response Body = " + responseBody);
if (httpStatus == '200'){
var responseObj = JSON.parse(responseBody);
var edate = responseObj.AssetWarrantyResponse[0].AssetEntitlementData[0].EndDate.substring(0, 10);
current.warranty_expiration = edate;
}else{
gs.addErrorMessage('Looks like we ran into a problem. HTTP status: ' + httpStatus);
}
}
catch(ex) {
var message = ex.getMessage();
}
})(current, previous);
Setting up the UI Action to check warranty expiration:
I setup a Form Button UI action to only display if the Serial Number is not empty and the workstation is not a Mac. This gives our Service Desk a method to validate the Warranty Expiration.
var st = current.serial_number;
var curdate = current.warranty_expiration;
try {
var r = new sn_ws.RESTMessageV2('DellTechDirect', 'GET');
r.setStringParameterNoEscape('service_tag', st);
//r.setQueryParameter(gs.getProperty('DellTechDirectKey'));
r.setQueryParameter('apikey', gs.getProperty('DellTechDirectKey'));
r.setHttpTimeout(10000);
r.setEccParameter('skip_sensor', true);
var response = r.execute();
var responseBody = response.getBody();
var httpStatus = response.getStatusCode();
gs.info("Status = " + httpStatus);
gs.info("Response Body = " + responseBody);
if(httpStatus == '200'){
var responseObj = JSON.parse(responseBody);
var edate = responseObj.AssetWarrantyResponse[0].AssetEntitlementData[0].EndDate.substring(0, 10);
if(curdate == edate){
gs.addInfoMessage('The Warranty Expiration date is correct');
action.setRedirectURL(current);
current.update();
}
if(curdate != edate){
gs.addInfoMessage('The Warranty Expiration date changed from ' + curdate + ' to ' + edate);
current.warranty_expiration = edate;
action.setRedirectURL(current);
current.update();
}
}
else{
gs.addErrorMessage('Could not retrieve Warranty Expiration information: ' + httpStatus);
action.setRedirectURL(current);
current.update();
}
}
catch(ex) {
var message = ex.getMessage();
}
I hope this is helpful and please let me know if you have any feedback.
- 25,590 Views
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Can you provide the scheduled job script you are using for this process?
Mine is similar to the business rule John had above and looks similar the screenshot below. I am always curious if I could be doing something better or filtering the hardware table better so we target those Dell devices we need.
(function executeRule(current, previous /*null when async*/ ) {
// Get Computer records
var cmp = new GlideRecord('alm_hardware');
cmp.setLimit(300);
cmp.query();
while (cmp.next()) {
// Get Serial Number
var st = cmp.serial_number.toString();
try {
var r = new sn_ws.RESTMessageV2('DellTechDirect', 'GET');
r.setStringParameterNoEscape('id', st);
r.setHttpTimeout(10000);
r.setEccParameter('skip_sensor', true);
var response = r.execute();
var responseBody = response.getBody();
var httpStatus = response.getStatusCode();
gs.info("Status = " + httpStatus);
gs.info("Response Body = " + responseBody);
if (httpStatus == '200') {
var responseObj = JSON.parse(responseBody);
var arrayl = responseObj[0].entitlements.length;
gs.info(arrayl);
for (var i = 0; i < arrayl; i++) {
if (responseObj[0].entitlements[i].serviceLevelDescription.indexOf('ProSupport Plus for PCs and Tablets') > -1) {
var edate = responseObj[0].entitlements[i].endDate.substring(0, 10);
gs.info("End Date = " + edate);
cmp.warranty_expiration = edate;
cmp.update();
}
}
} else {
gs.addErrorMessage('Looks like we ran into a problem. HTTP status: ' + httpStatus);
}
} catch (ex) {
var message = ex.getMessage();
}
}
})(current, previous);
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Sure.
Just a background history first. We update the warranty information in the Workstations table (cmdb_ci_computer), because ServiceNow will replicate that information to the Asset table anyway.
Also, I had to add few checks, because as a global company, some countries have different contracts with Dell, which was causing issues when the warranty was extended or different type of service, you will notice in the script below:
(function executeRule(current, previous /*null when async*/ ) {
// Get Computer records
var cmp = new GlideRecord('cmdb_ci_computer');
cmp.addQuery('model_id.display_name', 'CONTAINS', 'Dell');
cmp.addQuery('operational_status', 1);
//cmp.addNotNullQuery('warranty_expiration');
cmp.setLimit(15000);
cmp.query();
while (cmp.next()) {
// Get Serial Number
var st = cmp.serial_number.toString();
try {
var r = new sn_ws.RESTMessageV2('DellTechDirect', 'GET');
r.setStringParameterNoEscape('id', st);
r.setHttpTimeout(10000);
r.setEccParameter('skip_sensor', true);
var response = r.execute();
var responseBody = response.getBody();
var httpStatus = response.getStatusCode();
gs.info("Status = " + httpStatus);
gs.info("Response Body = " + responseBody);
if (httpStatus == '200') {
var responseObj = JSON.parse(responseBody);
var getShipDate = responseObj[0].shipDate.toString();
var isShipDate = false;
var format = "";
if (getShipDate != "" || getShipDate != null || getShipDate != undefined) {
isShipDate = true;
format = new GlideDateTime(getShipDate).getDate();
gs.info("format " + format);
}
var arrayl = responseObj[0].entitlements.length;
gs.info(arrayl);
var warrantyExpiration = null;
for (var i = 0; i < arrayl; i++) {
var entitlement = responseObj[0].entitlements[i];
if (entitlement.serviceLevelDescription.indexOf('ProSupport with Next Business Day Service') > -1) {
if (entitlement.entitlementType.indexOf('EXTENDED') > -1) {
warrantyExpiration = entitlement.endDate.substring(0, 10);
//gs.info("Applying Next Business EXTENDED Day date for " + st + " " + warrantyExpiration);
//current.warranty_expiration = nexdate;
//current.update();
break;
} else {
warrantyExpiration = entitlement.endDate.substring(0, 10);
//gs.info("Applying Next Business Day date for " + st + " " + warrantyExpiration);
break;
}
}
if (entitlement.serviceLevelDescription.indexOf('Parts Only') > -1) {
if (entitlement.entitlementType.indexOf('EXTENDED') > -1) {
warrantyExpiration = entitlement.endDate.substring(0, 10);
//gs.info("Found Extended End Date Parts Only = " + warrantyExpiration + " " + st);
break;
//current.warranty_expiration = exdate;
//current.update();
} else {
warrantyExpiration = entitlement.endDate.substring(0, 10);
//gs.info("Found End Date Parts Only = " + warrantyExpiration + " " + st);
break;
}
}
if (entitlement.serviceLevelDescription.indexOf('ProSupport Plus') > -1) {
if (entitlement.entitlementType.indexOf('EXTENDED') > -1) {
warrantyExpiration = entitlement.endDate.substring(0, 10);
//gs.info("Found Extended End Date = " + warrantyExpiration + " " + st);
break;
//current.warranty_expiration = exdate;
//current.update();
} else if (!warrantyExpiration) {
//var edate = responseObj[0].entitlements[i].endDate.substring(0, 10);
warrantyExpiration = entitlement.endDate.substring(0, 10);
//gs.info("End Date = " + warrantyExpiration + " " + st);
//current.warranty_expiration = edate;
//current.update();
}
}
}
if (warrantyExpiration || isShipDate) {
if (warrantyExpiration) {
//gs.info("Setting the warranty_expiration to: " + warrantyExpiration + " for serial number " + st);
cmp.warranty_expiration = warrantyExpiration;
}
if (isShipDate) {
cmp.purchase_date = format;
}
cmp.update();
}
} else {
gs.addErrorMessage('Looks like we ran into a problem. HTTP status: ' + httpStatus);
}
} catch (ex) {
var message = ex.getMessage();
}
}
})(current, previous);
Hope that helps.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Luiz,
That helps..thanks!
I believe I may use the computer table too. I built the UI Action on that table as our itil users are more familiar with it versus the hardware table. I think I am going to apply the scheduled job to the computer table similar to how you did.
How often do you run this? Any issues with the 15,000 limit? Ours wouldn't be close to that large, I'm just curious.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
There is an app on ServiceNow Share:
https://developer.servicenow.com/connect.do#!/share/contents/9049921_dell_warranty_import1?v=1&t=PRO.... Atleast it can be use as a cross reference.
There is one for Lenovo as well:
https://developer.servicenow.com/connect.do#!/share/contents?page=1&keyword=warranty
Regards,
Sharad

- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
not sure if you still need this or not, but the rest message looks like this:
and the GET method looks like this
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
Hey @Steven Parker
We had the limit to 10k, when we started getting close I raised to 15k to only find out the company signed a contract with Lenovo... 😂
We had to do something similar for Lenovo, but they are more strict, have limit per hour, up to four hours, etc.
Our users prefer to use the Asset table as well.
I've set this schedule to run every Saturday.
But also created a business rule to retrieve the warranty date when a new computer is inserted into the table.
- Mark as Read
- Mark as New
- Bookmark
- Permalink
- Report Inappropriate Content
@Luiz Lucena can i check how can i script this to lookup the warranty information if i have multiple entitlements ?
- « Previous
-
- 1
- 2
- Next »