JavaScript Object to MD5 Hash Converter
Convert any JavaScript object or JSON to an MD5 hash with deep recursive scanning and order-invariant array handling. No libraries needed.
About
Comparing two deeply nested JavaScript objects for structural equivalence is a non-trivial operation. A naive recursive equality check runs in O(n) time on every comparison and cannot be indexed or cached. This tool serializes any JSON-compatible object into a canonical form - sorting object keys lexicographically and normalizing array order - then computes the 128-bit MD5 digest per RFC 1321. The resulting 32-character hexadecimal string serves as a fingerprint: two objects produce identical hashes if and only if they are structurally equivalent (ignoring array element order). Objects containing function values at any depth are rejected, as functions lack a deterministic string representation.
The canonical serialization step is critical. Without it, {a:1, b:2} and {b:2, a:1} would produce different hashes despite logical equivalence. Similarly, arrays [1,2] and [2,1] are treated as identical sets. This makes the tool suitable for indexing object states in databases, cache invalidation keys, or regression test fixtures where insertion order is non-deterministic. The MD5 implementation here is pure JavaScript - no CryptoJS, no Underscore, no dependencies. Note: MD5 is not cryptographically secure for password hashing. It is used here strictly as a fast, compact fingerprint for equivalence testing.
Formulas
The MD5 algorithm processes an input message in 512-bit blocks. Each block undergoes 64 operations organized into 4 rounds of 16 operations. The four auxiliary functions are:
Each round operation follows the pattern:
where Mk is the k-th 32-bit word of the message block, Ti = floor(232 × |sin(i)|) is the per-round constant, s is the per-round shift amount, and ≪≪≪ denotes left circular rotation. The initial hash values are a0 = 0x67452301, b0 = 0xEFCDAB89, c0 = 0x98BADCFE, d0 = 0x10325476.
The canonical serialization before hashing follows this logic: for an object, sort all keys alphabetically, recurse into each value, and concatenate as key:value pairs. For an array, recursively serialize each element, sort the serialized strings lexicographically, then join. This ensures both key-order invariance and array-order invariance.
Reference Data
| Feature / Behavior | This Tool | Notes |
|---|---|---|
| Key order sensitivity | Order-invariant | Keys sorted lexicographically at every depth |
| Array order sensitivity | Order-invariant | Elements sorted by canonical serialized form |
| Nested objects | Fully recursive | No depth limit |
| Nested arrays | Fully recursive | Mixed types sorted by type then value |
| null values | Supported | Serialized as null |
| undefined values | Omitted | Matches JSON.stringify behavior |
| function values | Rejected | Error thrown with path to offending key |
| Boolean values | Supported | TRUE ≠ 1 |
| Number precision | IEEE 754 double | 0.1 + 0.2 ≠ 0.3 |
| Empty object {} | 99914b932bd37a50b983c5e7c90ae93b | MD5 of canonical {} |
| Empty array [] | d751713988987e9331980363e24189ce | MD5 of canonical [] |
| String encoding | UTF-8 | Full Unicode support |
| Max safe integer | 9007199254740991 | Beyond this, precision loss may alter hash |
| Hash output length | 32 hex characters | 128 bits |
| Collision probability | ≈ 1 in 2128 | Sufficient for equivalence testing |
| Algorithm | MD5 (RFC 1321) | Not suitable for cryptographic security |
| Dependencies | None | Pure vanilla JavaScript |
| Circular references | Rejected | Error thrown to prevent infinite recursion |
| NaN values | Serialized as null | Matches JSON.stringify behavior |
| Infinity values | Serialized as null | Matches JSON.stringify behavior |