Date format subtraction issue with GlideDateTime

mattystern
Kilo Sage

Hello,

I have a field within a scoped application for my customer service team which calculates "Resolution Days." I am currently using a business rule to calculate this by getting the "Inquiry Date" and "Resolution Date" fields and subtracting the two, then converting this to days from milliseconds. This was working fine until I added my European user base. It seems the subtraction is having trouble subtracting dates in dd-MM-yyyy format and coming up with incorrect results, as the system default is MM-dd-yyyy.

I tried to change this by setting the GlideDateTime's format with setDisplayValue. However, this is throwing an error:
exception: org.mozilla.javascript.EvaluatorException: Can't find method com.glide.glideobject.GlideDateTime.subtract(undefined,com.glide.glideobject.GlideDateTime).

Below is my business rule:

(function executeRule(current, previous /*null when async*/) {
	//store inquiry and resolution dates
	var inquiryDate = current.getDisplayValue('u_inquiry_date');
	var resolutionDate = current.getDisplayValue('u_resolution_date');


	if(inquiryDate != ''){
		//starts new GlideDateTime object using inquiryDate
		var startDate = new GlideDateTime (inquiryDate);
		//line which is not working 
	//	startDate = startDate.setDisplayValue(inquiryDate, "MM-dd-yyyy HH:mm:ss");
		var endDate = new GlideDateTime(gs.nowDateTime());
		if(current.getValue('u_state') != 'Open' && resolutionDate != ''){
			endDate = new GlideDateTime(resolutionDate);
	//		endDate = endDate.setDisplayValue(resolutionDate, "MM-dd-yyyy HH:mm:ss");
		}
		var dur = GlideDateTime.subtract(startDate, endDate);
		//convert the answer from milliseconds to days
		var days = dur.getNumericValue() /  (1000*60*60*24);
		if(days < 1){
			days = 1;
		}
		current.u_resolution_time = days;
	}
	else{
		current.u_resolution_time = 0;
	}

})(current, previous);

I likely think this is just me not understanding the syntax of using the setDisplayValue() method and how it works. I have read the developer documentation on setDisplayValue, but it is not sinking in for me. Can anyone offer assistance on when I should be converting the date's format / how this is achieved or just general tips for this? Thanks!

1 ACCEPTED SOLUTION

DrewW
Mega Sage
Mega Sage

Try the below.  It should be doing everything in GMT.

Also why do you care if its open before you use the resolution date?  Why not just check if it has a value and if it does then use it?

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

	if(current.u_inquiry_date){
		var startDate = current.u_inquiry_date.getGlideObject();
		var endDate = new GlideDateTime();
		if(current.getValue('u_state') != 'Open' && current.u_resolution_date){
			endDate = current.u_resolution_date.getGlideObject();
		}
		var dur = endDate.getNumericValue() - startDate.getNumericValue();
		//convert the answer from milliseconds to days
		var days = dur /  (1000*60*60*24);
		if(days < 1){
			days = 1;
		}
		current.u_resolution_time = days;
	} else {
		current.u_resolution_time = 0;
	}

})(current, previous);

View solution in original post

5 REPLIES 5

-O-
Kilo Patron
Kilo Patron

You should not be using date display values on server side - it just complicates things while adding nothing to the outcome. If you insist, you should on one hand use .getDisplayValueInternal() instead on the other hand use it throughout. It returns the date and time value in the system format.

All that also means you can't use new GlideDateTime (inquiryDate);: it expects inquiryDate to be the date and time in the system TZ (UTC by default), but it will most likely not be as the value has been obtained using a display value method - which returns the date and time in the current user's TZ.

That is why, just don't use the display value methods on server side.

Thank you Janos. This helps explain things for me and will be useful to come back to in the future!

You're most welcome 🙂

DrewW
Mega Sage
Mega Sage

Try the below.  It should be doing everything in GMT.

Also why do you care if its open before you use the resolution date?  Why not just check if it has a value and if it does then use it?

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

	if(current.u_inquiry_date){
		var startDate = current.u_inquiry_date.getGlideObject();
		var endDate = new GlideDateTime();
		if(current.getValue('u_state') != 'Open' && current.u_resolution_date){
			endDate = current.u_resolution_date.getGlideObject();
		}
		var dur = endDate.getNumericValue() - startDate.getNumericValue();
		//convert the answer from milliseconds to days
		var days = dur /  (1000*60*60*24);
		if(days < 1){
			days = 1;
		}
		current.u_resolution_time = days;
	} else {
		current.u_resolution_time = 0;
	}

})(current, previous);