chai: Deep equal with symbols as keys does not fail

Hi,

The following test should fail but doesn’t:

let test = Symbol('test')
expect({[test]: 1}).to.deep.equal({[test]: 2})

Thanks! Florent

About this issue

  • Original URL
  • State: closed
  • Created 7 years ago
  • Reactions: 6
  • Comments: 18 (8 by maintainers)

Most upvoted comments

There is a simple workaround: Node.js util.inspect

Example:

const { inspect } = require('util');
const { expect } = require('chai');

const foo = { [Symbol('a')]: ['1'] }; // also works with Sequelize operator, eg [Op.in]
const bar = { [Symbol('a')]: ['1'] };

const fooSerialized = inspect(foo, { depth: null });
const barSerialized = inspect(bar, { depth: null });

expect(fooSerialized).to.deep.equal(barSerialized);

@shvaikalesh Hi. I have one real-world use case for symbols. Sequelize module recently implemented their operators using Symbols, since it’s more secure ( http://docs.sequelizejs.com/manual/tutorial/querying.html#operators ). Now, it’s much more tedious to write unit tests, in order to test these operators. It’s still possible, but quite challenging.

Check this. this is how it could look if chai would assert Symbols correctly:

expect(result).to.be.deep.equal({
  'name': {
    [Op.and]: [
      {
        [Op.or]: [
          { [Op.notIn]: [ 'lolipop', 'zork' ] },
          { [Op.eq]: null }
        ]
      },
      { [Op.in]: [ 'good', 'very-good' ] },
    ]
  }
});

( All the values inside Op are symbols.)

But, now, in order to test this, i have to do some totally crazy stuff.

For those who do not want to compare objects using inspect, you can instead use lodash method isEqual.

import { isEqual } from 'lodash'

const foo = { [Symbol('a')]: ['1'] }; 
const bar = { [Symbol('a')]: ['1'] };

expect(isEqual(foo, bar)).to.be.true;

Definitely useful for testing out queries with sequelize. +1