hoophq / sequence

Immutable, scalable, and easy to use ledger service.
Apache License 2.0
493 stars 31 forks source link

`map->md5` is not predictive #11

Closed didiercrunch closed 3 years ago

didiercrunch commented 4 years ago

The function sequence.crypto/map->md5 does not return the same output for inputs that are semantically the same. An example is given in the bellow code.

(let [m {:foo 300 :toto 600}
      t (assoc (assoc {} :toto 600) :foo 300)]
  (println m (map->md5 m)) ;; {:foo 300, :toto 600} d8a50edd5aeb65be51deb87eefc48f93
  (println t (map->md5 t)))  ;; {:toto 600, :foo 300} 52a197cb51d65d93a047df1b7fa994aa

The root cause of the issue is that part that convert a map to a byte array. JSON is a predictive mechanism to do such thing. It is very easy to find two different json serialization of the same underlying data structure; {"foo": 4} and {"foo": 4} comes immediately to my minds.

The solution involves walking the data data structure in a predictable way and compute the hash while doing this. I am sure there is a java library that already implements this logic for you.

andriosrobert commented 4 years ago

@didiercrunch would love to get your review on #14