UNPKG

@endo/marshal

Version:

marshal: encoding and deconding of Passable subgraphs

71 lines (59 loc) 1.88 kB
/// <reference types="ses"/> import { Fail } from '@endo/errors'; import { makeMarshal } from './marshal.js'; /** @import {Passable} from '@endo/pass-style' */ const { freeze } = Object; /** @type {import('./types.js').ConvertValToSlot<any>} */ const doNotConvertValToSlot = val => Fail`Marshal's stringify rejects presences and promises ${val}`; /** @type {import('./types.js').ConvertSlotToVal<any>} */ const doNotConvertSlotToVal = (slot, _iface) => Fail`Marshal's parse must not encode any slots ${slot}`; const badArrayHandler = harden({ get: (_target, name, _receiver) => { if (name === 'length') { return 0; } // `throw` is noop since `Fail` throws. But linter confused throw Fail`Marshal's parse must not encode any slot positions ${name}`; }, }); /** * `freeze` but not `harden` the proxy target so it remains trapping. * Thus, it should not be shared outside this module. * * @see https://github.com/endojs/endo/blob/master/packages/ses/docs/preparing-for-stabilize.md */ const arrayTarget = freeze(/** @type {any[]} */ ([])); const badArray = new Proxy(arrayTarget, badArrayHandler); const { serialize, unserialize } = makeMarshal( doNotConvertValToSlot, doNotConvertSlotToVal, { errorTagging: 'off', // TODO fix tests to works with smallcaps. serializeBodyFormat: 'capdata', }, ); /** * @param {Passable} val * @returns {string} */ const stringify = val => serialize(val).body; harden(stringify); /** * @param {string} str * @returns {unknown} */ const parse = str => unserialize( // `freeze` but not `harden` since the `badArray` proxy and its target // must remain trapping. // See https://github.com/endojs/endo/blob/master/packages/ses/docs/preparing-for-stabilize.md freeze({ body: str, slots: badArray, }), ); harden(parse); export { stringify, parse };