SkeLLLa / node-object-hash

Node.js object hash library with properties/arrays sorting to provide constant hashes. It also provides a method that returns sorted object strings that can be used for object comparison without hashes.
https://savelife.in.ua/en/donate-en/
MIT License
85 stars 20 forks source link

Hash of objects with custom prototype (created via constructor) #10

Closed DmitriyBerezin closed 6 years ago

DmitriyBerezin commented 6 years ago

I've tried your module to calculate hash of objects are created via constructor. Although two objects have different property values they hashes are equal. Here is an example:

const assert = require('assert')
const hasher = require('node-object-hash')().hash

class Test {
    constructor(id) {
        this.id = id
    }
}

const t1 = new Test(1)
const t2 = new Test(2)
const h1 = hasher(t1)
const h2 = hasher(t2)

assert.notEqual(h1, h2)
SkeLLLa commented 6 years ago

@DmitriyBerezin that's expected :). Unfortunately there's no way to predict what kind of structure will be in custom objects. It can contain different fields, properties, etc.

For custom objects it calculates hashes from constructor name + object's string representation which is the result of calling .toString() method. See https://github.com/SkeLLLa/node-object-hash/blob/master/objectSorter.js#L202

So if you need to get it work, then you'll need to implement proper .toString method. There you can choose only those properties that are valuable for your hash. Also you can use objectSorter method as well.

Something like this:

const {hash, sort} = require('node-object-hash')()

class Test {
...
        toString() {
                return sort({
                      id: this.id
                });
        }
}

See full example here: https://runkit.com/skellla/5a5e39f8463c7c001229d057

DmitriyBerezin commented 6 years ago

@SkeLLLa Thank you for this response and example! Now it clear for me.

SkeLLLa commented 6 years ago

Thanks to you too, @DmitriyBerezin. I'll add it later to Readme later.