xsor
v0.1.0
Published
create object descriptors (accessors) backed by private variables
Downloads
6
Maintainers
Readme
xsor
This is a JavaScript module that eases the creation of object property descriptors (also known as "accessors") backed by pseudo-private variables. This saves you from having to mint unique symbols for your "private" data and focus on the logic of your application.
Code like this:
var MyClass = function() {
};
var x = '__x';
var onChangeX = function(value, previous) {
// logic for when stuff changes
};
MyClass.prototype = {
get x() {
return this[x];
},
set x(value) {
if (this[x] !== value) {
onChangeX.call(this, value, this[x]);
}
}
};
// "hide" __x from for..in loops
Object.defineProperty(MyClass, x, {enumerable: false});
becomes:
var MyClass = function() {
};
var xsor = require('xsor');
Object.defineProperty(MyClass.prototype, 'x', xsor(function(previous, value) {
// logic for when stuff changes
});
If you're unfamiliar with property descriptors, check out the docs for Object.defineProperty, Object.defineProperties and Object.create.
API
The module exports a top-level function that returns a property descriptor, and can be called in a couple of different ways. Generally speaking, descriptors are
xsor(change)
This is the simplest form, and creates a descriptor that fires the change
function whenever the value of any instance changes.
var xsor = require('xsor');
var obj = {};
Object.defineProperty(obj, 'value', xsor(function(value, previous) {
console.log('value changed from', previous, 'to', value);
}));
obj.value = 1;
// logs: "value changed from undefined to 1"
See below for more information on the change handler.
xsor(name [, options])
Creates a descriptor that refernces the private variable name
with the
following accepted options:
initial: value
Declares the initial value for this accessor, which will be returned by the first get.
change: function(value, previous, symbol)
Declares a change handler for the value of each individual instance,
where value
is the new value, previous
is the previous value (or
undefined
, if no initial value was set), and symbol
is the name
of the symbol used to access the private value.
If you return false
from this function, the change will not be
applied.
var xsor = require('xsor');
var x = {};
var change = function(value, previous, name) {
console.log(name, 'changed from', previous, 'to', value);
return value !== undefined;
};
Object.defineProperty(x, 'foo', xsor('foo', change));
x.foo = 1;
// logs: "foo changed from undefined to 1"
x.foo = 2;
// logs: "foo changed from 1 to 2"
parse: function(value, symbol)
Declares a parse function for the input value, which will be called whenever the value is set, but before the change handler. The return value is the parsed or coerced value. For instance, to coerce values to numbers, you could do:
var xsor = require('xsor');
var assert = require('assert');
var Thing = function() {
};
Object.defineProperty(MyClass.prototype, 'size', xsor({
parse: Number,
initial: 0
});
var instance = new Thing();
instance.size = '1';
assert.strictEqual(instance.size, 1);
enumerable: true
By default, descriptors returned by xsor()
are not enumerable, which means
that they won't be returned by Object.keys()
or iterated over by for..in
loops. You can make them enumerable by passing enumerable: true
.