New Case Study:See how Anthropic automated 95% of dependency reviews with Socket.Learn More
Socket
Sign inDemoInstall
Socket

structurae

Package Overview
Dependencies
Maintainers
1
Versions
75
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

structurae - npm Package Compare versions

Comparing version 2.1.0 to 2.2.0

lib/array-view-mixin.js

36

CHANGELOG.md

@@ -7,9 +7,21 @@ # Changelog

## [2.2.0] - 2020-02-26
### Added
- Support boolean type in ObjectView.
- Support type aliases in ObjectView.
- Cache ArrayView & TypedArrayView classes to avoid duplications.
- TypeView class to simplify creation of custom types for ObjectView.
### Changed
- (potentially breaking) Adding custom types to ObjectView is reworked.
Custom types are now expected to be extensions of existing *View classes.
A special TypeView class is added for types that extend number types.
## [2.1.0] - 2020-02-11
### Added
- BinaryProtocol class to simplify operating on tagged ObjectView
- BinaryProtocol class to simplify operating on tagged ObjectView.
## [2.0.1] - 2020-01-09
### Fixed
- TypeScript type declarations for ObjectView
- TypeScript type declarations for ObjectView.

@@ -19,9 +31,9 @@ ## [2.0.0] - 2019-11-21

Deprecated classes and methods:
- Remove RecordArray (consider using ObjectView instead)
- Remove StringArrayView (use ArrayView instead)
- Remove `toObject` methods of *View classes (use `toJSON` methods instead)
- Remove RecordArray (consider using ObjectView instead).
- Remove StringArrayView (use ArrayView instead).
- Remove `toObject` methods of *View classes (use `toJSON` methods instead).
### Changed
- Rename `BitField.fields` to `BitField.schema`, simplify the schema definition
- BitField no longer implicitly switches to using BigInts
- Rename `BitField.fields` to `BitField.schema`, simplify the schema definition.
- BitField no longer implicitly switches to using BigInts.
- Add BigBitField that uses BigInts for bitfields longer than 31 bits.

@@ -34,3 +46,3 @@ - BitFieldMixin automatically switches to BigBitField if the size of the bitfield exceeds 31 bits.

### Added
- Support default field values in ObjectView
- Support default field values in ObjectView.

@@ -43,11 +55,11 @@ ### Changed

### Added
- Add BitFieldMixin
- Add BitFieldMixin.
### Fixed
- Avoid BigInts in RecordArray if not supported
- Avoid BigInts in RecordArray if not supported.
## [1.7.4] - 2019-09-21
### Added
- Add ObjectViewMixin and expose ArrayView
- Add ObjectView#getView
- Add ObjectViewMixin and expose ArrayView.
- Add ObjectView#getView.

@@ -54,0 +66,0 @@ ## [1.7.3] - 2019-09-13

@@ -200,6 +200,24 @@ // Type definitions for structurae

type ViewType = typeof ArrayView | typeof ObjectView | typeof TypedArrayView | typeof StringView;
type ViewType = typeof ArrayView | typeof ObjectView | typeof TypedArrayView | typeof StringView | typeof TypeView;
type View = ObjectView | ArrayView | TypedArrayView | StringView;
type View = ObjectView | ArrayView | TypedArrayView | StringView | TypeView;
declare class TypeView extends DataView {
static isPrimitive: true;
private static offset: number;
private static littleEndian: true;
private static objectLength: number;
get(): number;
set(value: number): this;
toJSON(): number;
static getLength(): number;
static from(value: number, view?: TypeView): TypeView;
static of(): TypeView;
static get(position: number, view: View): number;
static set(position: number, value: number, view: View): void;
}
export declare function TypeViewMixin(type: PrimitiveFieldType, littleEndian?: boolean): typeof TypeView;
export declare class ArrayView extends DataView {

@@ -236,5 +254,2 @@ size: number;

View?: ViewType;
getter?: string;
setter?: string;
itemLength?: number;
default?: any;

@@ -255,2 +270,3 @@ }

static isInitialized: boolean;
static isPrimitive: false;
private static fields: string[];

@@ -261,9 +277,9 @@ private static objectLength: number;

get(field: string): number | View;
private getObject(position: number, field: ObjectViewField): object;
private getTypedArray(position: number, field: ObjectViewField): ArrayLike<number>;
private getPrimitive(position: number, View: ViewType): object;
private getObject(position: number, View: ViewType, length: number): object;
getValue(field: string): any;
getView(field: string): View;
set(field: string, value: any): this;
private setObject(position: number, value: object, field: ObjectViewField): void;
private setTypedArray(position: number, value: ArrayLike<number>, field: ObjectViewField): void;
private setPrimitive(position: number, value: number, View: ViewType): void;
private setObject(position: number, value: object, View: ViewType, length: number): void;
setView(field: string, value: View): this;

@@ -274,3 +290,2 @@ toJSON(): object;

static initialize(): void;
private static getFieldKind(field: ObjectViewField): string;
}

@@ -306,6 +321,4 @@

size: number;
static typeGetter: string;
static typeSetter: string;
static offset: number;
static littleEndian: boolean;
static View: TypeView;
static itemLength: number;

@@ -312,0 +325,0 @@ get(index: number): number;

@@ -16,8 +16,10 @@ const BitField = require('./lib/bit-field');

const WeightedAdjacencyMatrixMixin = require('./lib/weighted-adjacency-matrix');
const { ArrayView, ArrayViewMixin } = require('./lib/array-view');
const ArrayView = require('./lib/array-view');
const { ArrayViewMixin, TypedArrayViewMixin } = require('./lib/array-view-mixin');
const CollectionView = require('./lib/collection-view');
const { ObjectView, ObjectViewMixin } = require('./lib/object-view');
const StringView = require('./lib/string-view');
const TypedArrayViewMixin = require('./lib/typed-array-view');
const BinaryProtocol = require('./lib/binary-protocol');
const TypeViewMixin = require('./lib/type-view');
const BooleanView = require('./lib/boolean-view');

@@ -63,2 +65,4 @@ /**

BinaryProtocol,
TypeViewMixin,
BooleanView,
};

@@ -88,3 +88,3 @@ /**

for (let i = 0; i < size; i++) {
json[i] = this.get(i).toJSON();
json[i] = this.getValue(i);
}

@@ -146,23 +146,2 @@ return json;

/**
* Creates an ArrayView class for a given ObjectView class.
*
* @param {Class<ObjectView>|Class<StringView>} ObjectViewClass
* @param {number} [itemLength]
* @returns {Class<ArrayView>}
*/
function ArrayViewMixin(ObjectViewClass, itemLength) {
if (ObjectViewClass.initialize && !ObjectViewClass.isInitialized) {
ObjectViewClass.initialize();
}
class Base extends ArrayView {}
Base.View = ObjectViewClass;
Base.itemLength = ObjectViewClass.objectLength || itemLength;
return Base;
}
module.exports = {
ArrayView,
ArrayViewMixin,
};
module.exports = ArrayView;
const StringView = require('./string-view');
const { ArrayViewMixin } = require('./array-view');
const TypedArrayViewMixin = require('./typed-array-view');
const { typeOffsets, typeGetters, typeSetters } = require('./utilities');
const { ArrayViewMixin, TypedArrayViewMixin } = require('./array-view-mixin');
const TypeViewMixin = require('./type-view');
const BooleanView = require('./boolean-view');
/**
* @typedef {Class<ArrayView>|Class<ObjectView>|Class<TypedArrayView>|Class<StringView>} ViewType
* @typedef {Class<ArrayView>|Class<ObjectView>|Class<TypedArrayView>
* |Class<StringView>|Class<TypeView>} ViewType
*/

@@ -31,5 +32,2 @@

* @property {ViewType} [View]
* @property {string} [getter]
* @property {string} [setter]
* @property {number} [itemLength]
* @property {*} [default]

@@ -59,7 +57,5 @@ */

get(field) {
const {
getter, start, kind, littleEndian, View, length,
} = this.constructor.schema[field];
if (kind === 'number') return this[getter](start, littleEndian);
return new View(this.buffer, this.byteOffset + start, length);
const { start, View, length } = this.constructor.schema[field];
return View.isPrimitive ? this.getPrimitive(start, View)
: new View(this.buffer, this.byteOffset + start, length);
}

@@ -70,9 +66,7 @@

* @param {number} position
* @param {ObjectViewField} field
* @returns {Object}
* @param {ViewType} View
* @returns {number}
*/
getObject(position, field) {
const { View, length } = field;
const view = new View(this.buffer, this.byteOffset + position, length);
return view.toJSON();
getPrimitive(position, View) {
return View.get(position, this);
}

@@ -83,13 +77,8 @@

* @param {number} position
* @param {ObjectViewField} field
* @returns {Array<number>}
* @param {ViewType} View
* @param {number} length
* @returns {Object}
*/
getTypedArray(position, field) {
const { View, size } = field;
const { typeGetter, offset, littleEndian } = View;
const result = new Array(size);
for (let i = 0; i < size; i++) {
result[i] = this[typeGetter](position + (i << offset), littleEndian);
}
return result;
getObject(position, View, length) {
return new View(this.buffer, this.byteOffset + position, length).toJSON();
}

@@ -104,6 +93,4 @@

getValue(field) {
const options = this.constructor.schema[field];
const { start, getter, kind } = options;
const arg = kind === 'number' ? options.littleEndian : options;
return this[getter](start, arg);
const { start, View, length } = this.constructor.schema[field];
return View.isPrimitive ? this.getPrimitive(start, View) : this.getObject(start, View, length);
}

@@ -130,8 +117,8 @@

set(field, value) {
const options = this.constructor.schema[field];
const {
kind, start, setter, littleEndian,
} = options;
const arg = kind === 'number' ? littleEndian : options;
this[setter](start, value, arg);
const { start, View, length } = this.constructor.schema[field];
if (View.isPrimitive) {
this.setPrimitive(start, value, View);
} else {
this.setObject(start, value, View, length);
}
return this;

@@ -143,10 +130,8 @@ }

* @param {number} position
* @param {Object} value
* @param {ObjectViewField} field
* @param {number} value
* @param {ViewType} View
* @returns {void}
*/
setObject(position, value, field) {
const { View, length } = field;
const view = new View(this.buffer, this.byteOffset + position, length);
View.from(value, view);
setPrimitive(position, value, View) {
View.set(position, value, this);
}

@@ -157,15 +142,10 @@

* @param {number} position
* @param {ArrayLike<number>} value
* @param {ObjectViewField} field
* @param {Object} value
* @param {ViewType} View
* @param {number} length
* @returns {void}
*/
setTypedArray(position, value, field) {
const { View, size, length } = field;
const { typeSetter, offset, littleEndian } = View;
new Uint8Array(this.buffer, this.byteOffset + position, length)
.fill(0);
const max = (size < value.length ? size : value.length);
for (let i = 0; i < max; i++) {
this[typeSetter](position + (i << offset), value[i], littleEndian);
}
setObject(position, value, View, length) {
const view = new View(this.buffer, this.byteOffset + position, length);
View.from(value, view);
}

@@ -269,9 +249,6 @@

field.start = lastOffset;
const kind = this.getFieldKind(field);
if (Reflect.has(this.types, kind)) {
field.kind = kind;
this.types[kind](field);
} else {
throw TypeError(`Type "${field.type}" is not a valid type.`);
}
const type = typeof field.type !== 'string' ? 'object' : field.type;
if (!Reflect.has(this.types, type)) throw TypeError(`Type "${field.type}" is not a valid type.`);
const definition = typeof this.types[type] === 'string' ? this.types[this.types[type]] : this.types[type];
if (definition) definition(field);
lastOffset += field.length;

@@ -284,32 +261,2 @@ }

}
/**
* @private
* @param {ObjectViewField} field
* @returns {string}
*/
static getFieldKind(field) {
const { type, size } = field;
switch (type) {
case 'int8':
case 'uint8':
case 'int16':
case 'uint16':
case 'int32':
case 'uint32':
case 'float32':
case 'float64':
case 'bigint64':
case 'biguint64':
if (size) return 'typedarray';
return 'number';
case 'string':
if (size) return 'array';
return 'string';
default:
if (typeof type === 'string') return type;
if (size) return 'array';
return 'object';
}
}
}

@@ -321,2 +268,13 @@

ObjectView.types = {
int8: 'number',
uint8: 'number',
int16: 'number',
uint16: 'number',
int32: 'number',
uint32: 'number',
float32: 'number',
float64: 'number',
bigint64: 'number',
biguint64: 'number',
/**

@@ -326,9 +284,8 @@ * @param {ObjectViewField} field

*/
number(field) {
const { type, littleEndian } = field;
field.View = TypedArrayViewMixin(type, littleEndian);
field.length = 1 << typeOffsets[type];
field.getter = typeGetters[type];
field.setter = typeSetters[type];
boolean(field) {
const { size } = field;
field.View = size ? ArrayViewMixin(BooleanView) : BooleanView;
field.length = field.View.getLength(size || 1);
},
/**

@@ -338,9 +295,8 @@ * @param {ObjectViewField} field

*/
typedarray(field) {
number(field) {
const { type, littleEndian, size } = field;
field.View = TypedArrayViewMixin(type, littleEndian);
field.length = field.View.getLength(size);
field.getter = 'getTypedArray';
field.setter = 'setTypedArray';
field.View = size ? TypedArrayViewMixin(type, littleEndian) : TypeViewMixin(type, littleEndian);
field.length = field.View.getLength(size || 1);
},
/**

@@ -351,6 +307,7 @@ * @param {ObjectViewField} field

string(field) {
field.View = StringView;
field.getter = 'getObject';
field.setter = 'setObject';
const { size, length } = field;
field.View = size ? ArrayViewMixin(StringView, length) : StringView;
field.length = size ? field.View.getLength(size) : field.length;
},
/**

@@ -361,19 +318,5 @@ * @param {ObjectViewField} field

object(field) {
const { type } = field;
field.View = type;
field.length = type.getLength();
field.getter = 'getObject';
field.setter = 'setObject';
},
/**
* @param {ObjectViewField} field
* @returns {void}
*/
array(field) {
const { type, size, length } = field;
field.View = type === 'string' ? ArrayViewMixin(StringView, length) : ArrayViewMixin(type);
const { type, size } = field;
field.View = size ? ArrayViewMixin(type) : type;
field.length = field.View.getLength(size);
field.getter = 'getObject';
field.setter = 'setObject';
field.itemLength = field.View.itemLength;
},

@@ -390,2 +333,5 @@ };

/** @type {boolean} */
ObjectView.isPrimitive = false;
/**

@@ -392,0 +338,0 @@ * @private

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

const { typeGetters, typeSetters, typeOffsets } = require('./utilities');
/**

@@ -16,4 +14,4 @@ * A DataView based TypedArray that supports endianness and can be set at any offset.

get(index) {
const { typeGetter, offset, littleEndian: le } = this.constructor;
return this[typeGetter](index << offset, le);
const { View } = this.constructor;
return View.get(index << View.offset, this);
}

@@ -29,4 +27,4 @@

set(index, value) {
const { typeSetter, offset, littleEndian: le } = this.constructor;
this[typeSetter](index << offset, value, le);
const { View } = this.constructor;
View.set(index << View.offset, value, this);
return this;

@@ -41,3 +39,3 @@ }

get size() {
return this.byteLength >> this.constructor.offset;
return this.byteLength >> this.constructor.View.offset;
}

@@ -74,3 +72,3 @@

static getLength(size) {
return size << this.offset;
return size << this.View.offset;
}

@@ -86,8 +84,12 @@

static from(value, array) {
const dataArray = array || this.of(value.length);
const { size } = dataArray;
const view = array || this.of(value.length);
if (array) {
new Uint8Array(array.buffer, array.byteOffset, array.byteLength)
.fill(0);
}
const { size } = view;
for (let i = 0; i < size; i++) {
dataArray.set(i, value[i]);
view.set(i, value[i]);
}
return dataArray;
return view;
}

@@ -108,48 +110,11 @@

/**
* @type {string}
* @type {Class<TypeView>}
*/
TypedArrayView.typeGetter = '';
TypedArrayView.View = undefined;
/**
* @type {string}
*/
TypedArrayView.typeSetter = '';
/**
* @type {number}
*/
TypedArrayView.offset = 0;
TypedArrayView.itemLength = 0;
/**
* @type {boolean}
*/
TypedArrayView.littleEndian = false;
const TypedArrayViews = Object.keys(typeGetters).reduce((result, type) => {
class BE extends TypedArrayView {}
BE.typeGetter = typeGetters[type];
BE.typeSetter = typeSetters[type];
BE.offset = typeOffsets[type];
BE.littleEndian = false;
class LE extends TypedArrayView {}
LE.typeGetter = typeGetters[type];
LE.typeSetter = typeSetters[type];
LE.offset = typeOffsets[type];
LE.littleEndian = true;
result[0][type] = BE;
result[1][type] = LE;
return result;
}, { 0: {}, 1: {} });
/**
* @param {string} type
* @param {boolean} [littleEndian]
* @returns {Class<Base>}
*/
function TypedArrayViewMixin(type, littleEndian) {
return TypedArrayViews[+!!littleEndian][type];
}
module.exports = TypedArrayViewMixin;
module.exports = TypedArrayView;
{
"name": "structurae",
"version": "2.1.0",
"version": "2.2.0",
"description": "Data structures for performance-sensitive modern JavaScript applications.",

@@ -5,0 +5,0 @@ "main": "index.js",

@@ -59,3 +59,3 @@ # Structurae

The fields are defined in ObjectView.schema and can be of any primitive type supported by DataView,
their arrays, strings, or other objects and arrays of objects. The data is laid out sequentially with fixed sizes, hence,
their arrays, booleans, strings, or other objects and arrays of objects. The data is laid out sequentially with fixed sizes, hence,
variable length arrays and optional fields are not supported (for those check out [CollectionView](https://github.com/zandaqo/structurae#CollectionView)).

@@ -136,33 +136,33 @@

You can add your own field types to ObjectView, for example an ObjectView that supports booleans:
You can add your own field types to ObjectView, for example an ObjectView that supports Date:
```javascript
class BooleanView extends ObjectView {
getBoolean(position) {
return !!this.getUint8(position);
const { TypeViewMixin } = require('structurae');
class DateView extends TypeViewMixin('float64', true) {
static get(position, view) {
return new Date(super.get(position, view));
}
setBoolean(position, value) {
this.setUint8(position, value ? 1 : 0);
static set(position, value, view) {
super.set(position, +value, view);
}
}
BooleanView.schema = {
a: { type: 'boolean' },
class View extends ObjectView {}
View.schema = {
a: { type: 'date' },
};
BooleanView.types = {
View.types = {
...ObjectView.types,
boolean(field) {
field.View = DataView;
field.length = 1;
field.getter = 'getBoolean';
field.setter = 'setBoolean';
date(field) {
field.View = DateView;
field.length = 8;
},
};
BooleanView.initialize();
View.initialize();
const bool = BooleanView.from({ a: true });
bool.getValue('a')
//=> true
bool.set('a', false);
bool.toJSON();
//=> { a: false }
const date = View.from({ a: new Date(0) });
date.getValue('a')
//=> Thu Jan 01 1970 00:00:00 GMT+0000
date.set('a', new Date(1e8));
date.toJSON();
//=> { a: Fri Jan 02 1970 03:46:40 GMT+0000 }
```

@@ -348,3 +348,3 @@

We can of course define ObjectViews separately, however we will have to specify that tag field by ourselves in that case.
We can define ObjectViews separately, however, we will have to specify the tag field by ourselves in that case.
```javascript

@@ -351,0 +351,0 @@ const View = ObjectViewMixin({

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