npm install obsobs is a powerful implementation of observable properties that can be used on both the client-side and the server-side.
Together with rivets.js it can serve as a lightweight alternative to Knockout.js.
 

  

``sh`
npm install obs
`sh`
git clone https://github.com/pluma/obs.git
cd obs
npm install
make && make dist
`sh`
component install pluma/obs
Download the latest minified CommonJS release and add it to your project.
Make sure you also have a compatible copy of sublish.
Learn more about CommonJS modules.
Download the latest minified AMD release and add it to your project.
Make sure you also have a compatible copy of sublish.
Get the latest distribution bundle (~4.8 kB minified or ~1.4 kB gzipped, includes sublish 2.0.0) and download it to your project.
`html`
This makes the obs module available in the global namespace.
If you are already using sublish in your project, you can download the latest minified standalone release (~4.0 kB minified or ~1.2 kB gzipped) instead.
`javascript
var obs = require('obs');
var x = obs.prop(2),
y = obs.prop(5),
sum = obs.computed(function() {
return x() + y();
}, [x, y]),
product = obs.computed(function() {
return x() * y();
}, [x, y]);
console.log('sum is currently ' + sum());
// 'sum is currently 7'
console.log('product is currently ' + product());
// 'product is currently 10'
sum.subscribe(function(value, old) {
console.log('sum is now ' + value + ' (was: ' + old + ')');
});
product.subscribe(function(value, old) {
console.log('product is now ' + value + ' (was: ' + old + ')');
});
x(3);
// 'sum is now 8 (was: 7)'
// 'product is now 15 (was: 10)'
console.log('sum is currently ' + sum());
// 'sum is currently 8'
y(8);
// 'sum is now 11 (was: 8)'
// 'product is now 24 (was: 15)'
`
`javascript`
var obs = require('obs');
var firstname = obs.prop('John'),
lastname = obs.prop('Doe'),
fullname = obs.computed({
compute: function() {
return firstname() + ' ' + lastname();
},
write: function(value) {
var tokens = (value || '').split(' ');
firstname(tokens[0]);
lastname(tokens.slice(1).join(' '));
},
watch: [firstname, lastname]
});
console.log(fullname()); // John Doe
fullname('Konrad von Zuse');
console.log(firstname()); // Konrad
console.log(lastname()); // von Zuse
Try it on jsfiddle.
`html`
Hello !
The current UNIX time is:
`css`
#view {
font: 16px Verdana, Arial, sans-serif;
}
#view div {
padding: 10px;
}
`javascript`
var colors = [
'rgba(255,0,0,0.5)', 'rgba(255,255,0,0.5)',
'rgba(0,255,0,0.5)', 'rgba(0,255,255,0.5)',
'rgba(0,0,255,0.5)', 'rgba(255,0,255,0.5)'
];
function resolveKeypath(obj, keypath) {
keypath.split('.').forEach(function(key) {
if (key) {
obj = obj[key];
}
});
return obj;
}
javascript
rivets.configure({
prefix: 'rv',
adapter: {
subscribe: function(obj, keypath, callback) {
resolveKeypath(obj, keypath).subscribe(callback);
},
unsubscribe: function(obj, keypath, callback) {
resolveKeypath(obj, keypath).unsubscribe(callback);
},
read: function(obj, keypath) {
return resolveKeypath(obj, keypath)();
},
publish: function(obj, keypath, value) {
resolveKeypath(obj, keypath)(value);
}
}
});rivets.binders.bgcolor = function(el, value) {
el.style.backgroundColor = value;
};
`$3
`javascript
var viewModel = {
now: obs.prop(+new Date()),
color: obs.prop(colors[0]),
user: {
name: obs.prop('User')
}
};var view = rivets.bind($('#view'), viewModel);
setInterval(function() {
viewModel.now(+new Date());
viewModel.color(colors[
Math.floor(Math.random() * colors.length)
]);
}, 3000);
`API
obs: Abstract observables
This provides the base functionality for observables. You probably want to use
obs.prop and obs.computed instead of calling obs directly.$3
Creates an observable.
#### options.context (optional)
The context the observable's
read and write functions will be executed in.Defaults to the observable instance if not explicitly set.
#### options.read:Function and options.write:Function (optional)
The functions to be called when the observable is read from or written to.
An error will be raised if the observable is read from but no
read function was defined, or if it is written to and no write function was defined.#### options.watched:Array (optional)
An array of objects this observable subscribes to. If the value is not an array, it will be wrapped in one. Each object should have a
subscribe method and (optionally) an unsubscribe method.#### options.onNotify:Function (optional)
Function to be called when an object the observable is watching changes. Defaults to the observable's
notify method, effectively turning the observable into a relay.$3
Calls the observable's
read function with its context.$3
Calls the observable's
write function with its context and the given value.$3
Adds the given callback function to this observable's list of subscribers.
The callback will be called with the observable's new and old value as its arguments whenever the observable's value is updated (even if the new value is equal to the old value).
$3
Removes the given callback function from this observable's list of subscribers. The callback will no longer be called when the observable's value changes.
Returns
false if the callback could not be found in the list of subscribers or true otherwise.NOTE: Remember to use the exact function that was passed to
observable.subscribe.$3
Returns the observable's current value without invoking its
read function.$3
Sets the observable's initial value to its current value and clears its
dirty flag.$3
Resets the observable to its initial value (or
undefined), then calls notify().$3
Updates the observable's
dirty flag, then notifies all subscribers with the its current and previous value.$3
Adds the given dependencies to this observable. Each dependency should have a
subscribe and unsubscribe method. Whenever one of the dependencies changes, this observable's onNotify function will be called.$3
Removes the given dependencies by calling their
unsubscribe methods. The observable will no longer be notified when their values change.$3
Removes all of the observable's dependencies. Equivalent to calling
observable.unwatch for each dependency.$3
An object containing attributes that will be applied to new observables.
obs.prop: Observable properties
This provides a simple wrapper around
obs useful for observables that should just act as a single value storage.$3
Creates an observable property (optionally initialized with the given value).
$3
Returns the property's current value.
$3
Sets the property's current value to
newValue and notifies all subscribers.obs.computed: Computed observables
This provides a simple wrapper around
obs to create observables that depend on other observables and have values that should be computed dynamically, e.g. composite values of other observables.$3
Creates a computed observable observable. The observable's value will be set to the return value of the given function
compute and updated whenever any of the watch functions changes.If
write is passed, that function will be used when the computed observable is passed a value.The list of
watch functions can be an array containing any kind of object that supports the subscribe and (optionally) unsubscribe methods (e.g. an instance of sublish.PubSub).$3
Creates a computed observable property with the given options.
#### options.compute:Function (optional)
The function this computed observable will use to generate its value. If this option is not provided, the observable will be write-only.
#### options.write:Function (optional)
The function this computed observable will use when it is passed a value. If this option is not provided, the observable will be read-only.
#### options.watch:Array (optional)
See above. This option has no effect if no
read function is provided. If a single object is passed instead of an array, the object will automatically be wrapped in an array.#### options.context (optional)
The context the
compute and write functions will be executed in. Defaults to the computed observable itself.$3
Returns the computed property's current value. For lazy computed observables, this will trigger the function evaluation and notify any subscribers.
$3
See
obs.computed(…). The created observable will only call its compute function to update its value when it is explicitly read from.$3
See
obs.computed(options)` and above.The MIT/Expat license. For more information, see http://pluma.mit-license.org/ or the accompanying LICENSE file.