xsor

0.1.0 • Public • Published

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.

Package Sidebar

Install

npm i xsor

Weekly Downloads

0

Version

0.1.0

License

CC0-1.0

Last publish

Collaborators

  • shawnbot