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

enumerated-type

Package Overview
Dependencies
Maintainers
1
Versions
18
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

enumerated-type - npm Package Compare versions

Comparing version 0.1.0 to 0.2.0

VERSION.md

184

index.js

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

'use strict';
// 'use strict';

@@ -13,2 +13,106 @@ const isFunction = require("lodash.isfunction");

/**
* @return {string}
*/
function enumValueToString() {
return `[Symbol: Symbol(${this.name}) ${JSON.stringify(this)}]`;
}
function enumValueFunc(enumInst, enumName, props) {
const enumValue = function (name, value) {
// Object.setPrototypeOf(this, props);
Object.defineProperty(this, 'name', {
value: name,
writable: false,
enumerable: true,
});
if (typeof value === "object") {
const symbol = Symbol(name);
Object.defineProperty(this, '_value', {
value: symbol,
writable: false,
enumerable: false,
});
// // copy value props to enumValue
const valueKeys = Object.keys(value);
let j = valueKeys.length;
while (j--) {
const key = valueKeys[j];
const valueElement = value[key];
if (isFunction(valueElement) && valueElement.length === 0) {
Object.defineProperty(this, key, {
get: valueElement,
});
} else {
this[key] = isFunction(valueElement) ? valueElement.bind(this) : valueElement;
}
}
} else {
Object.defineProperty(this, '_value', {
value: value,
writable: false,
enumerable: false,
});
}
Object.freeze(this);
};
const propsProto = Object.create(props ? props : null);
// convert functions without arguments to getters
const propKeys = Object.keys(props);
let i = propKeys.length;
while (i--) {
const propKey = propKeys[i];
const propValue = propsProto[propKey];
if (isFunction(propValue) && propValue.length === 0) {
Object.defineProperty(propsProto.__proto__, propKey, {
get: propValue,
});
}
}
propsProto.enum = enumInst;
propsProto.name = enumName;
propsProto[Symbol.toPrimitive] = function (hint) {
if (hint === 'number') return this.enum.values.indexOf(this);
return this._value;
};
Object.defineProperty(propsProto, 'index', {
get: function () {
return this.enum.values.indexOf(this);
},
enumerable: true,
});
Object.defineProperty(propsProto, 'next', {
get: function () {
const values = this.enum.values;
const index = values.indexOf(this);
return index >= 0 && index + 1 < values.length ? values[index + 1] : UNDEFINED;
},
enumerable: true,
});
Object.defineProperty(propsProto, 'previous', {
get: function () {
const values = this.enum.values;
const index = values.indexOf(this);
return index >= 1 && index < values.length ? values[index - 1] : UNDEFINED;
},
enumerable: true,
});
Object.freeze(propsProto);
enumValue.prototype = propsProto;
return enumValue;
}
function Enum(enumName, keyName, values, props) {

@@ -26,9 +130,9 @@ if (keyName !== UNDEFINED && (typeof keyName !== "string" || keyName === '')) {

props = Object.create(props ? props : null);
props.constructor = Symbol;
props.enum = this;
const enumValueConstructor = enumValueFunc(this, enumName, props);
const names = Object.keys(values);
const keyNameValues = {};
const iMax = names.length;
let objectValues = 0;
let nonObjectValues = 0;
let functionValues = 0;
for (let i = 0; i < iMax; i++) {

@@ -38,12 +142,4 @@ const name = names[i];

const symbol = Symbol(name);
const enumValue = Object(symbol);
enumValue.__proto__ = props;
const enumValue = new enumValueConstructor(name, value);
Object.defineProperty(enumValue, 'name', {
value: name,
writable: false,
enumerable: true,
});
if (keyName !== UNDEFINED) {

@@ -58,15 +154,13 @@ if (value[keyName] === UNDEFINED) {

keyNameValues[value[keyName]] = enumValue;
}
} else {
if (value === UNDEFINED) {
throw `IllegalArgument, value of each enum value cannot be undefined`;
}
// copy value props to enumValue
const valueKeys = Object.keys(value);
let j = valueKeys.length;
while (j--) {
let key = valueKeys[j];
const valueElement = value[key];
enumValue[key] = isFunction(valueElement) ? valueElement.bind(enumValue) : valueElement;
if (keyNameValues[value] !== UNDEFINED) {
throw `IllegalArgument, enum with value of '${value}' is already defined by ${keyNameValues[value]._name}`;
}
keyNameValues[value] = enumValue;
}
Object.freeze(enumValue);
Object.defineProperty(this, name, {

@@ -78,6 +172,26 @@ value: enumValue,

if (typeof value === 'object') {
if (isFunction(value)) {
functionValues++;
} else {
objectValues++;
}
} else {
nonObjectValues++;
}
enumValues.push(enumValue);
}
enumValues.sort((a, b) => a[keyName] > b[keyName] ? 1 : -1);
if (objectValues !== 0 && nonObjectValues !== 0) {
// inconsistent value types
throw `IllegalArgument, enum values must all be objects or all non-objects, got ${objectValues} object values, ${nonObjectValues} non-object values`;
}
if (keyName !== UNDEFINED) {
enumValues.sort((a, b) => a[keyName] > b[keyName] ? 1 : -1);
} else {
enumValues.sort((a, b) => a._value > b._value ? 1 : -1);
}
Object.freeze(enumValues);

@@ -109,2 +223,18 @@

});
} else {
const enumKeys = enumValues.map(value => value._value);
Object.defineProperty(this, 'keys', {
value: enumKeys,
writable: false,
enumerable: false,
});
// define property with value to return matching enumValue to the key
Object.defineProperty(this, 'value', {
value: function (key) {
return forEach.call(enumValues, (enumValue) => {
if (enumValue._value === key) return BREAK(enumValue);
});
},
});
}

@@ -140,6 +270,6 @@

Enum.prototype[Symbol.toStringTag] = function toString() {
return this.name;
Enum.prototype.toString = function toString() {
return '[object Enum(' + this.name + ')]';
};
module.exports = Enum;

2

package.json
{
"name": "enumerated-type",
"version": "0.1.0",
"version": "0.2.0",
"description": "enum type for javascript",

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

@@ -21,5 +21,140 @@ # enumerated-type

Use `new Enum(enumName, keyPropName, values, commonProperties)` to define an enum for given
values. The property values of the `values` object can be objects/arrays/functions or
non-objects. If
```javascript
const Enum = require("enumerated-type");
const StepType = new Enum("StepType", "stepTypeId", {
duty: { stepTypeId: 1, isDuty: true, },
variable: { stepTypeId: 2, isVariable: true, },
optional: { stepTypeId: 3, isOptional: true, },
xor: { stepTypeId: 4, isGateway: true, isXor: true, },
and: { stepTypeId: 5, isGateway: true, isAnd: true, },
combineXor: { stepTypeId: 6, isGateway: true, isXor: true, isCombined: true, },
combineAnd: { stepTypeId: 7, isGateway: true, isAnd: true, isCombined: true, },
}, {
isDuty: false,
isVariable: false,
isOptional: false,
isGateway: false,
isXor: false,
isAnd: false,
isCombined: false,
});
```
`commonProperties` are used for each enum value for its prototype, therefore they provide a
default value when the enum value does not define the property directly:
```javascript
const values = [];
for (let value of StepType) {
values.push({
isAnd: value.isAnd,
isCombined: value.isCombined,
isDuty: value.isDuty,
isGateway: value.isGateway,
isOptional: value.isOptional,
isVariable: value.isVariable,
isXor: value.isXor,
name: value.name,
stepTypeId: value.stepTypeId,
});
}
expect(values).toEqual([
{ "isAnd": false, "isCombined": false, "isDuty": true, "isGateway": false, "isOptional": false, "isVariable": false, "isXor": false, "name": "duty", "stepTypeId": 1, },
{ "isAnd": false, "isCombined": false, "isDuty": false, "isGateway": false, "isOptional": false, "isVariable": true, "isXor": false, "name": "variable", "stepTypeId": 2, },
{ "isAnd": false, "isCombined": false, "isDuty": false, "isGateway": false, "isOptional": true, "isVariable": false, "isXor": false, "name": "optional", "stepTypeId": 3, },
{ "isAnd": false, "isCombined": false, "isDuty": false, "isGateway": true, "isOptional": false, "isVariable": false, "isXor": true, "name": "xor", "stepTypeId": 4, },
{ "isAnd": true, "isCombined": false, "isDuty": false, "isGateway": true, "isOptional": false, "isVariable": false, "isXor": false, "name": "and", "stepTypeId": 5, },
{ "isAnd": false, "isCombined": true, "isDuty": false, "isGateway": true, "isOptional": false, "isVariable": false, "isXor": true, "name": "combineXor", "stepTypeId": 6, },
{ "isAnd": true, "isCombined": true, "isDuty": false, "isGateway": true, "isOptional": false, "isVariable": false, "isXor": false, "name": "combineAnd", "stepTypeId": 7, },
]);
```
Use enum values as property names:
```javascript
let obj = {};
obj['duty'] = "++duty";
obj[StepType.duty] = "--duty";
obj[StepType.variable] = "--variable";
obj[StepType.optional] = "--optional";
obj[StepType.xor] = "--xor";
obj[StepType.and] = "--and";
obj[StepType.combineXor] = "--combineXor";
obj[StepType.combineAnd] = "--combineAnd";
expect(obj.duty).toEqual('++duty');
let values = [];
StepType.forEach(value => {
values.push(obj[value]);
});
expect(values).toEqual([
"--duty",
"--variable",
"--optional",
"--xor",
"--and",
"--combineXor",
"--combineAnd",
]);
```
### Enum Instance Properties
* `.name` : name of the enum passed to constructor
* `.values` : array of enum values sorted by `keyPropName` if provided or by value if non-object
values.
* `.keys` : array of enum key properties if keyPropName was passed to constructor, otherwise
array of enum values which were not objects
* `[keyPropName](key)`: function taking key and returning enum value whose `keyPropName` equals
the value of the key. Only defined if `keyPropName` is defined and is a string. Convenience
method for converting key property value to an enum value.
* `.value(key)`: function taking the a value and returning enum value whose value equals the
key. Only defined if `keyPropName` is not defined.
* `.forEach`: function (callback, defaultResult) taking a callback function(value, index,
values) and optional default result if callback does not return `BREAK(result)` or
`RETURN(result)`. see [for-each-break]
* `.map`: function (callback) taking a callback function(value, index, values) and returning
array of values returned my callback, unless callback returns `BREAK(result)` or
`RETURN(result)`. see [for-each-break]
* `.filter`: function (callback) taking a callback function(value, index, values) and returning
array of values for which callback result tested true, unless callback returns `BREAK(result)`
or `RETURN(result)`. see [for-each-break]
* `[Symbol.iterator]`: iterator over enum values
* `[Symbol.hasInstance]`: handles `instanceof` and returns true when left hand side is an enum
value of this enum instance.
* `.toString`: returns `[object Enum(enumName)]`
### Enum Value Instance Properties
In addition to enum value properties passed for the value each enum value has the following
additional properties:
* `.enum`: parent enum instance.
* `.name`: name of the enum value (property name in values object passed to `Enum()`
constructor.
* `._value`: Symbol(name) symbol instance for the property name of the enum value.
* `.index`: the enum value's index within enum instances values array.
* `.next`: enum value after this enum or `undefined` if last enum value.
* `.previous`: enum value before this enum or `undefined` if first enum value.
* `[Symbol.toPrimitive]`: returns `_value` property for `string` or `default` hint, for `number`
returns the enum value's index within enum instances values array.
Functions passed in as property values for enum value properties or `commonProperties` will have
`this` set to the enum value instance. Any functions which take no arguments (ie.
function.length === 0) will be converted to getters of the enum value instance and should not
use the function call syntax.
## License
MIT, see [LICENSE.md](http://github.com/vsch/enumerated-type/blob/master/LICENSE.md) for details.
MIT, see [LICENSE.md](http://github.com/vsch/enumerated-type/blob/master/LICENSE.md) for
details.
[for-each-break]: http://github.com/vsch/for-each-break/blob/master/README.md
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