UNPKG

jinaga

Version:

Data management for web and mobile applications.

103 lines 3.06 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.computeObjectHash = exports.canonicalPredecessors = exports.verifyHash = exports.canonicalizeFact = exports.computeHash = void 0; const encoding_1 = require("../util/encoding"); function computeHash(fields, predecessors) { return computeObjectHash({ fields: fields, predecessors: canonicalPredecessors(predecessors) }); } exports.computeHash = computeHash; function canonicalizeFact(fields, predecessors) { return canonicalize({ fields: fields, predecessors: canonicalPredecessors(predecessors) }); } exports.canonicalizeFact = canonicalizeFact; function verifyHash(fact) { const computedHash = computeHash(fact.fields, fact.predecessors); return fact.hash === computedHash; } exports.verifyHash = verifyHash; function canonicalPredecessors(predecessors) { const result = {}; for (const role in predecessors) { const referenceMessages = predecessors[role]; if (Array.isArray(referenceMessages)) { result[role] = sortedPredecessors(referenceMessages); } else { result[role] = referenceMessages; } } return result; } exports.canonicalPredecessors = canonicalPredecessors; function sortedPredecessors(predecessors) { return predecessors.slice().sort((a, b) => { if (a.hash < b.hash) return -1; else if (a.hash > b.hash) return 1; if (a.type < b.type) return -1; else if (a.type > b.type) return 1; else return 0; }); } function computeObjectHash(obj) { if (!obj) return ''; const str = canonicalize(obj); return (0, encoding_1.computeStringHash)(str); } exports.computeObjectHash = computeObjectHash; function canonicalize(obj) { const pairs = []; for (const key in obj) { const value = obj[key]; pairs.push({ key, value }); } pairs.sort((a, b) => { if (a.key < b.key) return -1; else if (a.key > b.key) return 1; else return 0; }); const members = pairs.reduce((text, pair) => { if (text.length > 0) text += ','; text += '"' + pair.key + '":' + serialize(pair.value); return text; }, ''); return '{' + members + '}'; } function serialize(value) { if (typeof (value) === 'object') { if (value instanceof Date) { return 'Date.parse("' + value.toISOString() + '")'; } else if (Array.isArray(value)) { const values = value.reduce((text, element) => { if (text.length > 0) text += ','; text += serialize(element); return text; }, ''); return '[' + values + ']'; } else { return canonicalize(value); } } else { return JSON.stringify(value); } } //# sourceMappingURL=hash.js.map