Error comparing date in test with jasmine

Viewed 762

I have an error when comparing "date" in a test in Angular. The test shows the error but in the log itself it is correct.

my test:

it('myTest', () => {
      const today = new Date();
      component.minDate = null;
      component.maxDate = null;

      spyOnProperty(component, 'isRange').and.returnValue(false);
      component['setActivateDate'](null);

      spyOn(component, <any>'verifyActivateDate').and.callThrough();

      expect(component.activateDate).toEqual(today);
    });

Log with "error"

Error: Expected Date(Wed Nov 17 2021 20:28:54 GMT+0000 (Coordinated Universal Time)) to equal Date(Wed Nov 17 2021 20:28:54 GMT+0000 (Coordinated Universal Time)).
        at <Jasmine>

2 Answers

The dates you are comparing appear equal since the string representation only presents the value to the second. Your dates are equal up until that point but do differ in the millisecond range, which is not displayed (but part of the equality check).

You could either use a library (e.g. dayjs) for the comparision, or you could implement an "almost equal" check yourself.

// Pass the dates you want to compare and an "accuracy" value.
// The accuracy removes that number of digits from the timestamp,  of
// so the default value of "3" means "remove the last 3 digits", which
// effectively means you are only comparing up until seconds
const expectDatesToNearlyEqual = (d1: Date, d2: Date, accuracy: number = 3) => {
   // Timestamp of first date, removing "accuracy" amount of digits from the end
   const d1Time = Math.floor(+d1 / (accuracy * 10));  
   // Timestamp of second date, removing "accuracy" amount of digits from the end
   const d2Time = Math.floor(+d2 / (accuracy * 10));

   // Expect the timestamps to equal, if they are not, print a nice message (optional).
   expect(d1Time).withContext(`${d1} and ${d2} are not equal`).toEqual(d2Time);
}

Watch out and be careful guys... In my case pipeline on server which run unit tests crushed with only one particular unit test... out of 600 others. This unit test basicly compared strings, which included dates with times and time zones. And guess what, it was the time zone which made only that one particular unit test to fail on the server (server is in different time zone than me). That unit test passes every time on my localhost. One of the values in that particular comparison was made with locale, and it included locale time zone. Me writing that unit test, expected my local time zone, instead of server time zone. But since jenkins pipeline run on server, it used server locale. So the fix was to ignore timezone (basicly substring it out), in that one particular case. Spent around 3 hours, before I finally thought about time zones.

Related