1.0.1 • Published 2 years ago

serialize-es6 v1.0.1

Weekly downloads
-
License
ISC
Repository
-
Last release
2 years ago

serialize-es6 1.0.0

Go directly to the Usage section if you want only the quick rundown.

This package provides the stringify() and parse() functions for serialization and deserialization of complex elements, which are defined to be any element that can be built from plain(*) objects, plain functions, ES6 data-types, and Node's Buffer. Circular references are handled. Like JSON, String validation is provided, i.e, when parsing an invalid string an exception will be thrown indicating why the string is invalid.

(*) A plain object is an object whose internal prototype is Object.prototype, and whose properties are enumerable, writable, and configurable. In particular this includes literal objects. A plain function is a function that relies only on its local variables, the "this" object, and global variables. This for example rules out class methods.

Stringification is closely modeled after console notation, i.e., stringify(x) is based on the string seen when you write console.log(x). See Console-Notation.md for a comparison.

It's emphasized that the objects handled can be very complex.

  • Data-types can have properties that themselves are complex.
    • For example, Booleans can have properties that are DataViews whose properties are Maps.
  • Keys of Sets and key/values of Maps may be complex objects.
    • For example, Sets may have members that are Maps whose keys are ArrayBuffers and values are TypedArrays.
  • Circular and duplicate references may have ends in the members of a Set, the keys and values of a Map, or the buffers of DataViews/TypedArrays/Buffers.
  • Plain functions are handled, and themselves may have complex properties.

Of particular note, this packages does not handle property descriptors. As a consequence it also neither handles non-enumerable properties nor getters/setters. A future package, tentatively named Serialize-Advanced will handle these, and the two packages will be kept separate. See the Serialize vs Serialize-Advanced section in Supplement.md.

If you don't need the complexity, the author also has the json-es6 package.

Exports

Export 1Description
stringify(x,max, tab)Serializes the object x. max and tab are optional parameters.
stringify parameterparameter description
maxmax = 0 results in pretty formatting. Otherwise compact formatting where once max+ characters are written a new line is started. Defaults to 100.
tabThe character or string used for tabbing according to object depth. Defaults to two spaces \x20\x20.
Export 2Description
parse(s)Parses the string s to obtain a primitive or object. Validates the string: exception thrown if invalid with explanation.

Usage

const {stringify, parse} = require('serialize-es6')

const x = object built from plain objects, plain 
    functions, ES6-data-types, and Node's Buffer

const sx = stringify(x)     // serialize x

const y = parse(sx)         // deserialize

const sy = stringify(y)     // serialize y

console.log(sx === sy)      // logs true

y is a deep copy of x (*). Any circular or duplicate references 
in x are preserved in y.

(*) Since the internal states of Symbols, WeakSets, and WeakMaps
    can't be read, these three data-types can not be serialized.
    Thus if the object tree of x has any of these data-types
    then the caveat is that y will not be a deep copy of x
    because the internal states of the corresponding 
    Symbols/WeakSets/WeakMaps will be different.   

Formatting Serialization

Pretty Formatting

If you want human readability, choose pretty formatting. Otherwise, it's not all that possible to make output highly readable.

const {stringify, parse} = require('Serialize')

const x = very complex object built from plain objects, 
          ES6-data-types, and Node's Buffer

const sx = stringify(x, 0)     // serialize x

const y = parse(sx)             // deserialize

const sy = stringify(y, 0)     // serialize y

console.log(sx === sy)          // logs true

Since the second parameter is 0, the serialiation sx will be 
formatted in "pretty" fashion, nicely tabbed according to object 
depth, i.e, it's close to one item per line, and is very readable.

Compact Formatting

const {stringify, parse} = require('Serialize')

const x = very complex object built from plain objects, 
          ES6-data-types, and Node's Buffer

const sx = stringify(x, 30)     // serialize x

const y = parse(sx)             // deserialize

const sy = stringify(y, 30)     // serialize y

console.log(sx === sy)          // logs true

Since the second paramteter is greater than 0, the serialiation 
sx will be formatted in "compact" fashion. Once the algorithm 
realizes that a line has passed 30 characters in length it 
will look for a good break to start a new line nicely tabbed 
according to object depth.

The default second parameter is 100.

An Example of a Complex Object that is Complicated

const x = new Set([
    new Uint8Array([5,6]).buffer,
    new Map([[/abc/g,2]]),
    ])

x.a = {a:new Date(), b:x} // circular reference
x.c = function foo() {const x = this; }
    
x is a complex object because it has been built from Sets, Maps, 
ArrayBuffers, plain objects, Dates, and plain functions.     

stringify(x, 30), a compact form, is displayed below

Set {ArrayBuffer(2) {5 6}, Map {
    RegExp(/abc/g) => 2},
  'a':{'a':Date(2022-06-11T13:25:45.074Z),
    'b':@}, 'c':function foo() {const x = this; }}

    As you can see it's not totally run-in like JSON, but
    if you want total readabiltiy, use pretty notation by
    changing the second parameter 30 to 0. See Supplement.md

Testing

Testing before publication was extensive.

Version History

VersionPublishedRemarks
1.0.06-11-2022Serialization idea originally from meouzer.com published in 2019. Meouzer.com like this package serialized "everything". Go there if you want to see the browser's Window serialized.