Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Socket
Sign inDemoInstall

lib0

Package Overview
Dependencies
Maintainers
1
Versions
113
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

lib0 - npm Package Compare versions

Comparing version 0.0.5 to 0.0.6

.nyc_output/317fc422-f87c-4e82-96aa-626977a5fda9.json

2

.nyc_output/processinfo/index.json

@@ -1,1 +0,1 @@

{"processes":{"52a87e06-c81a-40bf-9c84-fa6e0982a66b":{"parent":null,"children":[]}},"files":{},"externalIds":{}}
{"processes":{"317fc422-f87c-4e82-96aa-626977a5fda9":{"parent":null,"children":[]}},"files":{},"externalIds":{}}

@@ -5,2 +5,3 @@ /**

import * as buffer from './buffer.js'
import * as binary from './binary.js'

@@ -185,6 +186,6 @@ /**

while (true) {
let r = decoder.arr[decoder.pos++]
num = num | ((r & 0b1111111) << len)
const r = decoder.arr[decoder.pos++]
num = num | ((r & binary.BITS7) << len)
len += 7
if (r < 1 << 7) {
if (r < binary.BIT8) {
return num >>> 0 // return unsigned number!

@@ -200,2 +201,35 @@ }

/**
* Read signed integer (32bit) with variable length.
* 1/8th of the storage is used as encoding overhead.
* * numbers < 2^7 is stored in one bytlength
* * numbers < 2^14 is stored in two bylength
*
* @function
* @param {Decoder} decoder
* @return {number} An unsigned integer.length
*/
export const readVarInt = decoder => {
let r = decoder.arr[decoder.pos++]
let num = r & binary.BITS6
let len = 6
const sign = (r & binary.BIT7) > 0 ? -1 : 1
if ((r & binary.BIT8) === 0) {
// don't continue reading
return sign * num
}
while (true) {
r = decoder.arr[decoder.pos++]
num = num | ((r & binary.BITS7) << len)
len += 7
if (r < binary.BIT8) {
return sign * num
}
/* istanbul ignore if */
if (len > 41) {
throw new Error('Integer out of range!')
}
}
}
/**
* Look ahead and read varUint without incrementing position

@@ -215,2 +249,16 @@ *

/**
* Look ahead and read varUint without incrementing position
*
* @function
* @param {Decoder} decoder
* @return {number}
*/
export const peekVarInt = decoder => {
const pos = decoder.pos
const s = readVarInt(decoder)
decoder.pos = pos
return s
}
/**
* Read string of variable length

@@ -256,1 +304,73 @@ * * varUint is used to store the length of the string

}
/**
* @param {Decoder} decoder
* @param {number} len
* @return {DataView}
*/
export const readFromDataView = (decoder, len) => {
const dv = new DataView(decoder.arr.buffer, decoder.arr.byteOffset + decoder.pos, len)
decoder.pos += len
return dv
}
/**
* @param {Decoder} decoder
*/
export const readFloat32 = decoder => readFromDataView(decoder, 4).getFloat32(0)
/**
* @param {Decoder} decoder
*/
export const readFloat64 = decoder => readFromDataView(decoder, 8).getFloat64(0)
/**
* @param {Decoder} decoder
*/
export const readBigInt64 = decoder => readFromDataView(decoder, 8).getBigInt64(0)
/**
* @param {Decoder} decoder
*/
export const readBigUint64 = decoder => readFromDataView(decoder, 8).getBigUint64(0)
/**
* @type {Array<function(Decoder):any>}
*/
const readAnyLookupTable = [
decoder => undefined, // CASE 127: undefined
decoder => null, // CASE 126: null
readVarInt, // CASE 125: integer
readFloat32, // CASE 124: float32
readFloat64, // CASE 123: float64
readBigInt64, // CASE 122: bigint
decoder => false, // CASE 121: boolean (false)
decoder => true, // CASE 120: boolean (true)
readVarString, // CASE 119: string
decoder => { // CASE 118: object<string,any>
const len = readVarUint(decoder)
/**
* @type {Object<string,any>}
*/
const obj = {}
for (let i = 0; i < len; i++) {
const key = readVarString(decoder)
obj[key] = readAny(decoder)
}
return obj
},
decoder => { // CASE 117: array<any>
const len = readVarUint(decoder)
const arr = []
for (let i = 0; i < len; i++) {
arr.push(readAny(decoder))
}
return arr
},
readVarUint8Array // CASE 116: Uint8Array
]
/**
* @param {Decoder} decoder
*/
export const readAny = decoder => readAnyLookupTable[127 - readUint8(decoder)](decoder)

@@ -5,2 +5,3 @@ 'use strict';

var binary = require('./binary.js');
require('./map.js');

@@ -193,6 +194,6 @@ require('./string.js');

while (true) {
let r = decoder.arr[decoder.pos++];
num = num | ((r & 0b1111111) << len);
const r = decoder.arr[decoder.pos++];
num = num | ((r & binary.BITS7) << len);
len += 7;
if (r < 1 << 7) {
if (r < binary.BIT8) {
return num >>> 0 // return unsigned number!

@@ -208,2 +209,35 @@ }

/**
* Read signed integer (32bit) with variable length.
* 1/8th of the storage is used as encoding overhead.
* * numbers < 2^7 is stored in one bytlength
* * numbers < 2^14 is stored in two bylength
*
* @function
* @param {Decoder} decoder
* @return {number} An unsigned integer.length
*/
const readVarInt = decoder => {
let r = decoder.arr[decoder.pos++];
let num = r & binary.BITS6;
let len = 6;
const sign = (r & binary.BIT7) > 0 ? -1 : 1;
if ((r & binary.BIT8) === 0) {
// don't continue reading
return sign * num
}
while (true) {
r = decoder.arr[decoder.pos++];
num = num | ((r & binary.BITS7) << len);
len += 7;
if (r < binary.BIT8) {
return sign * num
}
/* istanbul ignore if */
if (len > 41) {
throw new Error('Integer out of range!')
}
}
};
/**
* Look ahead and read varUint without incrementing position

@@ -223,2 +257,16 @@ *

/**
* Look ahead and read varUint without incrementing position
*
* @function
* @param {Decoder} decoder
* @return {number}
*/
const peekVarInt = decoder => {
const pos = decoder.pos;
const s = readVarInt(decoder);
decoder.pos = pos;
return s
};
/**
* Read string of variable length

@@ -265,2 +313,74 @@ * * varUint is used to store the length of the string

/**
* @param {Decoder} decoder
* @param {number} len
* @return {DataView}
*/
const readFromDataView = (decoder, len) => {
const dv = new DataView(decoder.arr.buffer, decoder.arr.byteOffset + decoder.pos, len);
decoder.pos += len;
return dv
};
/**
* @param {Decoder} decoder
*/
const readFloat32 = decoder => readFromDataView(decoder, 4).getFloat32(0);
/**
* @param {Decoder} decoder
*/
const readFloat64 = decoder => readFromDataView(decoder, 8).getFloat64(0);
/**
* @param {Decoder} decoder
*/
const readBigInt64 = decoder => readFromDataView(decoder, 8).getBigInt64(0);
/**
* @param {Decoder} decoder
*/
const readBigUint64 = decoder => readFromDataView(decoder, 8).getBigUint64(0);
/**
* @type {Array<function(Decoder):any>}
*/
const readAnyLookupTable = [
decoder => undefined, // CASE 127: undefined
decoder => null, // CASE 126: null
readVarInt, // CASE 125: integer
readFloat32, // CASE 124: float32
readFloat64, // CASE 123: float64
readBigInt64, // CASE 122: bigint
decoder => false, // CASE 121: boolean (false)
decoder => true, // CASE 120: boolean (true)
readVarString, // CASE 119: string
decoder => { // CASE 118: object<string,any>
const len = readVarUint(decoder);
/**
* @type {Object<string,any>}
*/
const obj = {};
for (let i = 0; i < len; i++) {
const key = readVarString(decoder);
obj[key] = readAny(decoder);
}
return obj
},
decoder => { // CASE 117: array<any>
const len = readVarUint(decoder);
const arr = [];
for (let i = 0; i < len; i++) {
arr.push(readAny(decoder));
}
return arr
},
readVarUint8Array // CASE 116: Uint8Array
];
/**
* @param {Decoder} decoder
*/
const readAny = decoder => readAnyLookupTable[127 - readUint8(decoder)](decoder);
exports.Decoder = Decoder;

@@ -273,4 +393,11 @@ exports.clone = clone;

exports.peekUint8 = peekUint8;
exports.peekVarInt = peekVarInt;
exports.peekVarString = peekVarString;
exports.peekVarUint = peekVarUint;
exports.readAny = readAny;
exports.readBigInt64 = readBigInt64;
exports.readBigUint64 = readBigUint64;
exports.readFloat32 = readFloat32;
exports.readFloat64 = readFloat64;
exports.readFromDataView = readFromDataView;
exports.readTailAsUint8Array = readTailAsUint8Array;

@@ -281,2 +408,3 @@ exports.readUint16 = readUint16;

exports.readUint8Array = readUint8Array;
exports.readVarInt = readVarInt;
exports.readVarString = readVarString;

@@ -283,0 +411,0 @@ exports.readVarUint = readVarUint;

@@ -5,2 +5,3 @@ 'use strict';

var binary = require('./binary.js');
require('./map.js');

@@ -10,2 +11,4 @@ require('./string.js');

var buffer = require('./buffer.js');
var math = require('./math.js');
var number = require('./number.js');

@@ -19,5 +22,2 @@ /**

const bits7 = 0b1111111;
const bits8 = 0b11111111;
/**

@@ -78,2 +78,18 @@ * A BinaryEncoder handles the encoding to an Uint8Array.

/**
* Verify that it is possible to write `len` bytes wtihout checking. If
* necessary, a new Buffer with the required length is attached.
*
* @param {Encoder} encoder
* @param {number} len
*/
const verifyLen = (encoder, len) => {
const bufferLen = encoder.cbuf.length;
if (bufferLen - encoder.cpos < len) {
encoder.bufs.push(buffer.createUint8ArrayViewFromArrayBuffer(encoder.cbuf.buffer, 0, encoder.cpos));
encoder.cbuf = new Uint8Array(math.max(bufferLen, len) * 2);
encoder.cpos = 0;
}
};
/**
* Write one byte to the encoder.

@@ -86,5 +102,6 @@ *

const write = (encoder, num) => {
if (encoder.cpos === encoder.cbuf.length) {
const bufferLen = encoder.cbuf.length;
if (encoder.cpos === bufferLen) {
encoder.bufs.push(encoder.cbuf);
encoder.cbuf = new Uint8Array(encoder.cbuf.length * 2);
encoder.cbuf = new Uint8Array(bufferLen * 2);
encoder.cpos = 0;

@@ -129,3 +146,3 @@ }

*/
const writeUint8 = (encoder, num) => write(encoder, num & bits8);
const writeUint8 = write;

@@ -140,3 +157,3 @@ /**

*/
const setUint8 = (encoder, pos, num) => set(encoder, pos, num & bits8);
const setUint8 = set;

@@ -151,4 +168,4 @@ /**

const writeUint16 = (encoder, num) => {
write(encoder, num & bits8);
write(encoder, (num >>> 8) & bits8);
write(encoder, num & binary.BITS8);
write(encoder, (num >>> 8) & binary.BITS8);
};

@@ -164,4 +181,4 @@ /**

const setUint16 = (encoder, pos, num) => {
set(encoder, pos, num & bits8);
set(encoder, pos + 1, (num >>> 8) & bits8);
set(encoder, pos, num & binary.BITS8);
set(encoder, pos + 1, (num >>> 8) & binary.BITS8);
};

@@ -178,3 +195,3 @@

for (let i = 0; i < 4; i++) {
write(encoder, num & bits8);
write(encoder, num & binary.BITS8);
num >>>= 8;

@@ -194,3 +211,3 @@ }

for (let i = 0; i < 4; i++) {
set(encoder, pos + i, num & bits8);
set(encoder, pos + i, num & binary.BITS8);
num >>>= 8;

@@ -210,10 +227,36 @@ }

const writeVarUint = (encoder, num) => {
while (num >= 0b10000000) {
write(encoder, 0b10000000 | (bits7 & num));
while (num > binary.BITS7) {
write(encoder, binary.BIT8 | (binary.BITS7 & num));
num >>>= 7;
}
write(encoder, bits7 & num);
write(encoder, binary.BITS7 & num);
};
/**
* Write a variable length integer.
*
* Encodes integers in the range from [-2147483648, -2147483647].
*
* @function
* @param {Encoder} encoder
* @param {number} num The number that is to be encoded.
*/
const writeVarInt = (encoder, num) => {
let isNegative = false;
if (num < 0) {
num = -num;
isNegative = true;
}
// |- whether to continue reading |- whether is negative |- number
write(encoder, (num > binary.BITS6 ? binary.BIT8 : 0) | (isNegative ? binary.BIT7 : 0) | (binary.BITS6 & num));
num >>>= 6;
// We don't need to consider the case of num === 0 so we can use a different
// pattern here than above.
while (num > 0) {
write(encoder, (num > binary.BITS7 ? binary.BIT8 : 0) | (binary.BITS7 & num));
num >>>= 7;
}
};
/**
* Write a variable length string.

@@ -274,2 +317,165 @@ *

/**
* Create an DataView of the next `len` bytes. Use it to write data after
* calling this function.
*
* @example
* // write float32 using DataView
* const dv = writeOnDataView(encoder, 4)
* dv.setFloat32(0, 1.1)
* // read float32 using DataView
* const dv = readFromDataView(encoder, 4)
* dv.getFloat32(0) // => 1.100000023841858 (leaving it to the reader to find out why this is the correct result)
*
* @param {Encoder} encoder
* @param {number} len
* @return {DataView}
*/
const writeOnDataView = (encoder, len) => {
verifyLen(encoder, len);
const dview = new DataView(encoder.cbuf.buffer, encoder.cpos, len);
encoder.cpos += len;
return dview
};
/**
* @param {Encoder} encoder
* @param {number} num
*/
const writeFloat32 = (encoder, num) => writeOnDataView(encoder, 4).setFloat32(0, num);
/**
* @param {Encoder} encoder
* @param {number} num
*/
const writeFloat64 = (encoder, num) => writeOnDataView(encoder, 8).setFloat64(0, num);
/**
* @param {Encoder} encoder
* @param {bigint} num
*/
const writeBigInt64 = (encoder, num) => writeOnDataView(encoder, 8).setBigInt64(0, num);
/**
* @param {Encoder} encoder
* @param {bigint} num
*/
const writeBigUint64 = (encoder, num) => writeOnDataView(encoder, 8).setBigUint64(0, num);
/**
* Check if a number can be encoded as a 32 bit float.
*
* @param {number} num
* @return {boolean}
*/
const isFloat32 = num => {
const dv = new DataView(new ArrayBuffer(4));
dv.setFloat32(0, num);
return dv.getFloat32(0) === num
};
/**
* Encode data with efficient binary format.
*
* Differences to JSON:
* • Transforms data to a binary format (not to a string)
* • Encodes undefined, NaN, and ArrayBuffer (these can't be represented in JSON)
* • Numbers are efficiently encoded either as a variable length integer, as a
* 32 bit float, as a 64 bit float, or as a 64 bit bigint.
*
* Encoding table:
*
* | Data Type | Prefix | Encoding Method | Comment |
* | ------------------- | -------- | ------------------ | ------- |
* | undefined | 127 | | Functions, symbol, and everything that cannot be identified is encoded as undefined |
* | null | 126 | | |
* | integer | 125 | writeVarInt | Only encodes 32 bit signed integers |
* | float32 | 124 | writeFloat32 | |
* | float64 | 123 | writeFloat64 | |
* | bigint | 122 | writeBigInt64 | |
* | boolean (false) | 121 | | True and false are different data types so we save the following byte |
* | boolean (true) | 120 | | - 0b01111000 so the last bit determines whether true or false |
* | string | 119 | writeVarString | |
* | object<string,any> | 118 | custom | Writes {length} then {length} key-value pairs |
* | array<any> | 117 | custom | Writes {length} then {length} json values |
* | Uint8Array | 116 | writeVarUint8Array | We use Uint8Array for any kind of binary data |
*
* Reasons for the decreasing prefix:
* We need the first bit for extendability (later we may want to encode the
* prefix with writeVarUint). The remaining 7 bits are divided as follows:
* [0-30] the beginning of the data range is used for custom purposes
* (defined by the function that uses this library)
* [31-127] the end of the data range is used for data encoding by
* lib0/encoding.js
*
* @param {Encoder} encoder
* @param {undefined|null|number|bigint|boolean|string|Object|Array|ArrayBuffer} data
*/
const writeAny = (encoder, data) => {
switch (typeof data) {
case 'string':
// TYPE 119: STRING
write(encoder, 119);
writeVarString(encoder, data);
break
case 'number':
if (number.isInteger(data) && data <= binary.BITS31) {
// TYPE 125: INTEGER
write(encoder, 125);
writeVarInt(encoder, data);
} else if (isFloat32(data)) {
// TYPE 124: FLOAT32
write(encoder, 124);
writeFloat32(encoder, data);
} else {
// TYPE 123: FLOAT64
write(encoder, 123);
writeFloat64(encoder, data);
}
break
case 'bigint':
// TYPE 122: BigInt
write(encoder, 122);
writeBigInt64(encoder, data);
break
case 'object':
if (data === null) {
// TYPE 126: null
write(encoder, 126);
} else if (data instanceof Array) {
// TYPE 117: Array
write(encoder, 117);
writeVarUint(encoder, data.length);
for (let i = 0; i < data.length; i++) {
writeAny(encoder, data[i]);
}
} else if (data instanceof Uint8Array) {
// TYPE 116: ArrayBuffer
write(encoder, 116);
writeVarUint8Array(encoder, data);
} else {
// TYPE 118: Object
write(encoder, 118);
const keys = Object.keys(data);
writeVarUint(encoder, keys.length);
for (let i = 0; i < keys.length; i++) {
const key = keys[i];
writeVarString(encoder, key);
writeAny(encoder, data[key]);
}
}
break
case 'boolean':
// TYPE 120/121: boolean (true/false)
write(encoder, data ? 120 : 121);
break
case 'symbol':
case 'function':
case 'undefined':
default:
// TYPE 127: undefined
write(encoder, 127);
}
};
exports.Encoder = Encoder;

@@ -284,3 +490,9 @@ exports.createEncoder = createEncoder;

exports.write = write;
exports.writeAny = writeAny;
exports.writeBigInt64 = writeBigInt64;
exports.writeBigUint64 = writeBigUint64;
exports.writeBinaryEncoder = writeBinaryEncoder;
exports.writeFloat32 = writeFloat32;
exports.writeFloat64 = writeFloat64;
exports.writeOnDataView = writeOnDataView;
exports.writeUint16 = writeUint16;

@@ -290,2 +502,3 @@ exports.writeUint32 = writeUint32;

exports.writeUint8Array = writeUint8Array;
exports.writeVarInt = writeVarInt;
exports.writeVarString = writeVarString;

@@ -292,0 +505,0 @@ exports.writeVarUint = writeVarUint;

@@ -10,6 +10,6 @@ 'use strict';

var dom = require('./dom.js');
var math = require('./math.js');
var eventloop = require('./eventloop.js');
var json = require('./json.js');
var symbol = require('./symbol.js');
var math = require('./math.js');

@@ -16,0 +16,0 @@ const BOLD = symbol.create();

@@ -5,2 +5,5 @@ 'use strict';

var binary = require('./binary.js');
var math = require('./math.js');
/**

@@ -13,4 +16,14 @@ * @module number

const LOWEST_INT32 = 1 << 31;
const HIGHEST_INT32 = binary.BITS31;
const isInteger = Number.isInteger || (num => typeof num === 'number' && isFinite(num) && math.floor(num) === num);
const isNaN = Number.isNaN;
exports.HIGHEST_INT32 = HIGHEST_INT32;
exports.LOWEST_INT32 = LOWEST_INT32;
exports.MAX_SAFE_INTEGER = MAX_SAFE_INTEGER;
exports.MIN_SAFE_INTEGER = MIN_SAFE_INTEGER;
exports.isInteger = isInteger;
exports.isNaN = isNaN;
//# sourceMappingURL=number.js.map

@@ -14,6 +14,6 @@ 'use strict';

require('./dom.js');
var math = require('./math.js');
require('./eventloop.js');
var json = require('./json.js');
require('./symbol.js');
var math = require('./math.js');
var logging = require('./logging.js');

@@ -20,0 +20,0 @@ var object = require('./object.js');

@@ -8,6 +8,6 @@ /**

import * as buffer from './buffer.js'
import * as math from './math.js'
import * as number from './number.js'
import * as binary from './binary.js'
const bits7 = 0b1111111
const bits8 = 0b11111111
/**

@@ -68,2 +68,18 @@ * A BinaryEncoder handles the encoding to an Uint8Array.

/**
* Verify that it is possible to write `len` bytes wtihout checking. If
* necessary, a new Buffer with the required length is attached.
*
* @param {Encoder} encoder
* @param {number} len
*/
const verifyLen = (encoder, len) => {
const bufferLen = encoder.cbuf.length
if (bufferLen - encoder.cpos < len) {
encoder.bufs.push(buffer.createUint8ArrayViewFromArrayBuffer(encoder.cbuf.buffer, 0, encoder.cpos))
encoder.cbuf = new Uint8Array(math.max(bufferLen, len) * 2)
encoder.cpos = 0
}
}
/**
* Write one byte to the encoder.

@@ -76,5 +92,6 @@ *

export const write = (encoder, num) => {
if (encoder.cpos === encoder.cbuf.length) {
const bufferLen = encoder.cbuf.length
if (encoder.cpos === bufferLen) {
encoder.bufs.push(encoder.cbuf)
encoder.cbuf = new Uint8Array(encoder.cbuf.length * 2)
encoder.cbuf = new Uint8Array(bufferLen * 2)
encoder.cpos = 0

@@ -119,3 +136,3 @@ }

*/
export const writeUint8 = (encoder, num) => write(encoder, num & bits8)
export const writeUint8 = write

@@ -130,3 +147,3 @@ /**

*/
export const setUint8 = (encoder, pos, num) => set(encoder, pos, num & bits8)
export const setUint8 = set

@@ -141,4 +158,4 @@ /**

export const writeUint16 = (encoder, num) => {
write(encoder, num & bits8)
write(encoder, (num >>> 8) & bits8)
write(encoder, num & binary.BITS8)
write(encoder, (num >>> 8) & binary.BITS8)
}

@@ -154,4 +171,4 @@ /**

export const setUint16 = (encoder, pos, num) => {
set(encoder, pos, num & bits8)
set(encoder, pos + 1, (num >>> 8) & bits8)
set(encoder, pos, num & binary.BITS8)
set(encoder, pos + 1, (num >>> 8) & binary.BITS8)
}

@@ -168,3 +185,3 @@

for (let i = 0; i < 4; i++) {
write(encoder, num & bits8)
write(encoder, num & binary.BITS8)
num >>>= 8

@@ -184,3 +201,3 @@ }

for (let i = 0; i < 4; i++) {
set(encoder, pos + i, num & bits8)
set(encoder, pos + i, num & binary.BITS8)
num >>>= 8

@@ -200,10 +217,36 @@ }

export const writeVarUint = (encoder, num) => {
while (num >= 0b10000000) {
write(encoder, 0b10000000 | (bits7 & num))
while (num > binary.BITS7) {
write(encoder, binary.BIT8 | (binary.BITS7 & num))
num >>>= 7
}
write(encoder, bits7 & num)
write(encoder, binary.BITS7 & num)
}
/**
* Write a variable length integer.
*
* Encodes integers in the range from [-2147483648, -2147483647].
*
* @function
* @param {Encoder} encoder
* @param {number} num The number that is to be encoded.
*/
export const writeVarInt = (encoder, num) => {
let isNegative = false
if (num < 0) {
num = -num
isNegative = true
}
// |- whether to continue reading |- whether is negative |- number
write(encoder, (num > binary.BITS6 ? binary.BIT8 : 0) | (isNegative ? binary.BIT7 : 0) | (binary.BITS6 & num))
num >>>= 6
// We don't need to consider the case of num === 0 so we can use a different
// pattern here than above.
while (num > 0) {
write(encoder, (num > binary.BITS7 ? binary.BIT8 : 0) | (binary.BITS7 & num))
num >>>= 7
}
}
/**
* Write a variable length string.

@@ -263,1 +306,164 @@ *

}
/**
* Create an DataView of the next `len` bytes. Use it to write data after
* calling this function.
*
* @example
* // write float32 using DataView
* const dv = writeOnDataView(encoder, 4)
* dv.setFloat32(0, 1.1)
* // read float32 using DataView
* const dv = readFromDataView(encoder, 4)
* dv.getFloat32(0) // => 1.100000023841858 (leaving it to the reader to find out why this is the correct result)
*
* @param {Encoder} encoder
* @param {number} len
* @return {DataView}
*/
export const writeOnDataView = (encoder, len) => {
verifyLen(encoder, len)
const dview = new DataView(encoder.cbuf.buffer, encoder.cpos, len)
encoder.cpos += len
return dview
}
/**
* @param {Encoder} encoder
* @param {number} num
*/
export const writeFloat32 = (encoder, num) => writeOnDataView(encoder, 4).setFloat32(0, num)
/**
* @param {Encoder} encoder
* @param {number} num
*/
export const writeFloat64 = (encoder, num) => writeOnDataView(encoder, 8).setFloat64(0, num)
/**
* @param {Encoder} encoder
* @param {bigint} num
*/
export const writeBigInt64 = (encoder, num) => writeOnDataView(encoder, 8).setBigInt64(0, num)
/**
* @param {Encoder} encoder
* @param {bigint} num
*/
export const writeBigUint64 = (encoder, num) => writeOnDataView(encoder, 8).setBigUint64(0, num)
/**
* Check if a number can be encoded as a 32 bit float.
*
* @param {number} num
* @return {boolean}
*/
const isFloat32 = num => {
const dv = new DataView(new ArrayBuffer(4))
dv.setFloat32(0, num)
return dv.getFloat32(0) === num
}
/**
* Encode data with efficient binary format.
*
* Differences to JSON:
* • Transforms data to a binary format (not to a string)
* • Encodes undefined, NaN, and ArrayBuffer (these can't be represented in JSON)
* • Numbers are efficiently encoded either as a variable length integer, as a
* 32 bit float, as a 64 bit float, or as a 64 bit bigint.
*
* Encoding table:
*
* | Data Type | Prefix | Encoding Method | Comment |
* | ------------------- | -------- | ------------------ | ------- |
* | undefined | 127 | | Functions, symbol, and everything that cannot be identified is encoded as undefined |
* | null | 126 | | |
* | integer | 125 | writeVarInt | Only encodes 32 bit signed integers |
* | float32 | 124 | writeFloat32 | |
* | float64 | 123 | writeFloat64 | |
* | bigint | 122 | writeBigInt64 | |
* | boolean (false) | 121 | | True and false are different data types so we save the following byte |
* | boolean (true) | 120 | | - 0b01111000 so the last bit determines whether true or false |
* | string | 119 | writeVarString | |
* | object<string,any> | 118 | custom | Writes {length} then {length} key-value pairs |
* | array<any> | 117 | custom | Writes {length} then {length} json values |
* | Uint8Array | 116 | writeVarUint8Array | We use Uint8Array for any kind of binary data |
*
* Reasons for the decreasing prefix:
* We need the first bit for extendability (later we may want to encode the
* prefix with writeVarUint). The remaining 7 bits are divided as follows:
* [0-30] the beginning of the data range is used for custom purposes
* (defined by the function that uses this library)
* [31-127] the end of the data range is used for data encoding by
* lib0/encoding.js
*
* @param {Encoder} encoder
* @param {undefined|null|number|bigint|boolean|string|Object|Array|ArrayBuffer} data
*/
export const writeAny = (encoder, data) => {
switch (typeof data) {
case 'string':
// TYPE 119: STRING
write(encoder, 119)
writeVarString(encoder, data)
break
case 'number':
if (number.isInteger(data) && data <= binary.BITS31) {
// TYPE 125: INTEGER
write(encoder, 125)
writeVarInt(encoder, data)
} else if (isFloat32(data)) {
// TYPE 124: FLOAT32
write(encoder, 124)
writeFloat32(encoder, data)
} else {
// TYPE 123: FLOAT64
write(encoder, 123)
writeFloat64(encoder, data)
}
break
case 'bigint':
// TYPE 122: BigInt
write(encoder, 122)
writeBigInt64(encoder, data)
break
case 'object':
if (data === null) {
// TYPE 126: null
write(encoder, 126)
} else if (data instanceof Array) {
// TYPE 117: Array
write(encoder, 117)
writeVarUint(encoder, data.length)
for (let i = 0; i < data.length; i++) {
writeAny(encoder, data[i])
}
} else if (data instanceof Uint8Array) {
// TYPE 116: ArrayBuffer
write(encoder, 116)
writeVarUint8Array(encoder, data)
} else {
// TYPE 118: Object
write(encoder, 118)
const keys = Object.keys(data)
writeVarUint(encoder, keys.length)
for (let i = 0; i < keys.length; i++) {
const key = keys[i]
writeVarString(encoder, key)
writeAny(encoder, data[key])
}
}
break
case 'boolean':
// TYPE 120/121: boolean (true/false)
write(encoder, data ? 120 : 121)
break
case 'symbol':
case 'function':
case 'undefined':
default:
// TYPE 127: undefined
write(encoder, 127)
}
}

@@ -0,1 +1,4 @@

import * as math from './math.js'
import * as binary from './binary.js'
/**

@@ -7,1 +10,7 @@ * @module number

export const MIN_SAFE_INTEGER = Number.MIN_SAFE_INTEGER
export const LOWEST_INT32 = 1 << 31
export const HIGHEST_INT32 = binary.BITS31
export const isInteger = Number.isInteger || (num => typeof num === 'number' && isFinite(num) && math.floor(num) === num)
export const isNaN = Number.isNaN
{
"name": "lib0",
"version": "0.0.5",
"version": "0.0.6",
"description": "",
"dependencies": {},
"devDependencies": {
"@types/node": "^11.13.0",
"@types/node": "^11.13.18",
"fake-indexeddb": "^2.0.5",

@@ -35,3 +35,10 @@ "live-server": "^1.2.1",

},
"homepage": "https://github.com/dmonad/lib0#readme"
"homepage": "https://github.com/dmonad/lib0#readme",
"standard": {
"ignore": [
"/dist",
"/node_modules",
"/docs"
]
}
}

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is not supported yet

Sorry, the diff of this file is too big to display

Sorry, the diff of this file is not supported yet

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc