Skip to content

Instantly share code, notes, and snippets.

@jhusain
Created April 3, 2015 02:37
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save jhusain/9575b97f25f50018a7e9 to your computer and use it in GitHub Desktop.
Save jhusain/9575b97f25f50018a7e9 to your computer and use it in GitHub Desktop.
requirebin sketch
// When you click the button on the right, this program
// retrieves a stock quote from a stubbed method. If the
// button is clicked while a (stubbed/fake) network request
// is in-flight, then the fake request is cancelled and
// a new one is issued. To confirm this, press the button
// several times and notice that only one stock quote is
// returned.
var Task = require('task-lib');
var getQuoteButton = document.getElementById('getQuote');
var priceTextBox = document.getElementById('price');
// would like to use XHR, but no cross-site scripting.
// Task.timeout does cancel though - it calls clearTimeout
function getQuote(symbol) {
return Task.
timeout(2000).
when(function() { return (Math.random()* 100).toFixed(2); });
}
// The method above is the stubbed version of the method below.
// This method won't work here because it would be a cross-site
// request.
/*
function getQuote(symbol) {
return new Task((resolve, reject) => {
var xhr = new XMLHttpRequest(),
url = 'https://query.yahooapis.com/v1/public/yql?q=select%20LastTradePriceOnly%20from%20yahoo.finance.quote%20where%20symbol%20in%20(%22' + symbol + '%22)&format=json&diagnostics=true&env=store%3A%2F%2Fdatatables.org%2Falltableswithkeys&callback=';
xhr.open('get', url, true);
xhr.onreadystatechange = function() {
var status;
var data;
// https://xhr.spec.whatwg.org/#dom-xmlhttprequest-readystate
if (xhr.readyState == 4) { // `DONE`
status = xhr.status;
if (status == 200) {
data = JSON.parse(xhr.responseText).query.results.quote.LastTradePriceOnly;
resolve(data);
} else {
reject(status);
}
}
};
xhr.send();
// the cancellation action to perform when the Task is no longer observed.
return { dispose: () => xhr.abort() };
});
}
*/
var outgoingRequest;
function waitForQuote() {
// if there's a request in-flight, cancel it
if (outgoingRequest) {
outgoingRequest.dispose();
outgoingRequest = undefined;
}
outgoingRequest =
Task.
nextEvent(getQuoteButton, 'click').
// auto-flatten result just like then
when(function() {
return getQuote('NFLX');
}).
// run and await the result
run(function(val) {
priceTextBox.value = val;
waitForQuote();
});
};
waitForQuote();
require=function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o<r.length;o++)s(r[o]);return s}({1:[function(require,module,exports){module.exports=function(){var events=require("events");var domain={};domain.createDomain=domain.create=function(){var d=new events.EventEmitter;function emitError(e){d.emit("error",e)}d.add=function(emitter){emitter.on("error",emitError)};d.remove=function(emitter){emitter.removeListener("error",emitError)};d.run=function(fn){try{fn()}catch(err){this.emit("error",err)}return this};d.dispose=function(){this.removeAllListeners();return this};return d};return domain}.call(this)},{events:2}],2:[function(require,module,exports){function EventEmitter(){this._events=this._events||{};this._maxListeners=this._maxListeners||undefined}module.exports=EventEmitter;EventEmitter.EventEmitter=EventEmitter;EventEmitter.prototype._events=undefined;EventEmitter.prototype._maxListeners=undefined;EventEmitter.defaultMaxListeners=10;EventEmitter.prototype.setMaxListeners=function(n){if(!isNumber(n)||n<0||isNaN(n))throw TypeError("n must be a positive number");this._maxListeners=n;return this};EventEmitter.prototype.emit=function(type){var er,handler,len,args,i,listeners;if(!this._events)this._events={};if(type==="error"){if(!this._events.error||isObject(this._events.error)&&!this._events.error.length){er=arguments[1];if(er instanceof Error){throw er}throw TypeError('Uncaught, unspecified "error" event.')}}handler=this._events[type];if(isUndefined(handler))return false;if(isFunction(handler)){switch(arguments.length){case 1:handler.call(this);break;case 2:handler.call(this,arguments[1]);break;case 3:handler.call(this,arguments[1],arguments[2]);break;default:len=arguments.length;args=new Array(len-1);for(i=1;i<len;i++)args[i-1]=arguments[i];handler.apply(this,args)}}else if(isObject(handler)){len=arguments.length;args=new Array(len-1);for(i=1;i<len;i++)args[i-1]=arguments[i];listeners=handler.slice();len=listeners.length;for(i=0;i<len;i++)listeners[i].apply(this,args)}return true};EventEmitter.prototype.addListener=function(type,listener){var m;if(!isFunction(listener))throw TypeError("listener must be a function");if(!this._events)this._events={};if(this._events.newListener)this.emit("newListener",type,isFunction(listener.listener)?listener.listener:listener);if(!this._events[type])this._events[type]=listener;else if(isObject(this._events[type]))this._events[type].push(listener);else this._events[type]=[this._events[type],listener];if(isObject(this._events[type])&&!this._events[type].warned){var m;if(!isUndefined(this._maxListeners)){m=this._maxListeners}else{m=EventEmitter.defaultMaxListeners}if(m&&m>0&&this._events[type].length>m){this._events[type].warned=true;console.error("(node) warning: possible EventEmitter memory "+"leak detected. %d listeners added. "+"Use emitter.setMaxListeners() to increase limit.",this._events[type].length);if(typeof console.trace==="function"){console.trace()}}}return this};EventEmitter.prototype.on=EventEmitter.prototype.addListener;EventEmitter.prototype.once=function(type,listener){if(!isFunction(listener))throw TypeError("listener must be a function");var fired=false;function g(){this.removeListener(type,g);if(!fired){fired=true;listener.apply(this,arguments)}}g.listener=listener;this.on(type,g);return this};EventEmitter.prototype.removeListener=function(type,listener){var list,position,length,i;if(!isFunction(listener))throw TypeError("listener must be a function");if(!this._events||!this._events[type])return this;list=this._events[type];length=list.length;position=-1;if(list===listener||isFunction(list.listener)&&list.listener===listener){delete this._events[type];if(this._events.removeListener)this.emit("removeListener",type,listener)}else if(isObject(list)){for(i=length;i-->0;){if(list[i]===listener||list[i].listener&&list[i].listener===listener){position=i;break}}if(position<0)return this;if(list.length===1){list.length=0;delete this._events[type]}else{list.splice(position,1)}if(this._events.removeListener)this.emit("removeListener",type,listener)}return this};EventEmitter.prototype.removeAllListeners=function(type){var key,listeners;if(!this._events)return this;if(!this._events.removeListener){if(arguments.length===0)this._events={};else if(this._events[type])delete this._events[type];return this}if(arguments.length===0){for(key in this._events){if(key==="removeListener")continue;this.removeAllListeners(key)}this.removeAllListeners("removeListener");this._events={};return this}listeners=this._events[type];if(isFunction(listeners)){this.removeListener(type,listeners)}else{while(listeners.length)this.removeListener(type,listeners[listeners.length-1])}delete this._events[type];return this};EventEmitter.prototype.listeners=function(type){var ret;if(!this._events||!this._events[type])ret=[];else if(isFunction(this._events[type]))ret=[this._events[type]];else ret=this._events[type].slice();return ret};EventEmitter.listenerCount=function(emitter,type){var ret;if(!emitter._events||!emitter._events[type])ret=0;else if(isFunction(emitter._events[type]))ret=1;else ret=emitter._events[type].length;return ret};function isFunction(arg){return typeof arg==="function"}function isNumber(arg){return typeof arg==="number"}function isObject(arg){return typeof arg==="object"&&arg!==null}function isUndefined(arg){return arg===void 0}},{}],3:[function(require,module,exports){var process=module.exports={};process.nextTick=function(){var canSetImmediate=typeof window!=="undefined"&&window.setImmediate;var canMutationObserver=typeof window!=="undefined"&&window.MutationObserver;var canPost=typeof window!=="undefined"&&window.postMessage&&window.addEventListener;if(canSetImmediate){return function(f){return window.setImmediate(f)}}var queue=[];if(canMutationObserver){var hiddenDiv=document.createElement("div");var observer=new MutationObserver(function(){var queueList=queue.slice();queue.length=0;queueList.forEach(function(fn){fn()})});observer.observe(hiddenDiv,{attributes:true});return function nextTick(fn){if(!queue.length){hiddenDiv.setAttribute("yes","no")}queue.push(fn)}}if(canPost){window.addEventListener("message",function(ev){var source=ev.source;if((source===window||source===null)&&ev.data==="process-tick"){ev.stopPropagation();if(queue.length>0){var fn=queue.shift();fn()}}},true);return function nextTick(fn){queue.push(fn);window.postMessage("process-tick","*")}}return function nextTick(fn){setTimeout(fn,0)}}();process.title="browser";process.browser=true;process.env={};process.argv=[];function noop(){}process.on=noop;process.addListener=noop;process.once=noop;process.off=noop;process.removeListener=noop;process.removeAllListeners=noop;process.emit=noop;process.binding=function(name){throw new Error("process.binding is not supported")};process.cwd=function(){return"/"};process.chdir=function(dir){throw new Error("process.chdir is not supported")}},{}],4:[function(require,module,exports){(function(process){"use strict";var rawAsap=require("./raw");var freeTasks=[];module.exports=asap;function asap(task){var rawTask;if(freeTasks.length){rawTask=freeTasks.pop()}else{rawTask=new RawTask}rawTask.task=task;rawTask.domain=process.domain;rawAsap(rawTask)}function RawTask(){this.task=null;this.domain=null}RawTask.prototype.call=function(){if(this.domain){this.domain.enter()}var threw=true;try{this.task.call();threw=false;if(this.domain){this.domain.exit()}}finally{if(threw){rawAsap.requestFlush()}this.task=null;this.domain=null;freeTasks.push(this)}}}).call(this,require("_process"))},{"./raw":5,_process:3}],5:[function(require,module,exports){(function(process){"use strict";var domain;var hasSetImmediate=typeof setImmediate==="function";module.exports=rawAsap;function rawAsap(task){if(!queue.length){requestFlush();flushing=true}queue[queue.length]=task}var queue=[];var flushing=false;var index=0;var capacity=1024;function flush(){while(index<queue.length){var currentIndex=index;index=index+1;queue[currentIndex].call();if(index>capacity){for(var scan=0;scan<index;scan++){queue[scan]=queue[scan+index]}queue.length-=index;index=0}}queue.length=0;index=0;flushing=false}rawAsap.requestFlush=requestFlush;function requestFlush(){var parentDomain=process.domain;if(parentDomain){if(!domain){domain=require("domain")}domain.active=process.domain=null}if(flushing&&hasSetImmediate){setImmediate(flush)}else{process.nextTick(flush)}if(parentDomain){domain.active=process.domain=parentDomain}}}).call(this,require("_process"))},{_process:3,domain:1}],"task-lib":[function(require,module,exports){"use strict";var _slicedToArray=function(arr,i){if(Array.isArray(arr)){return arr}else if(Symbol.iterator in Object(arr)){var _arr=[];for(var _iterator=arr[Symbol.iterator](),_step;!(_step=_iterator.next()).done;){_arr.push(_step.value);if(i&&_arr.length===i)break}return _arr}else{throw new TypeError("Invalid attempt to destructure non-iterable instance")}};var _createComputedClass=function(){function defineProperties(target,props){for(var i=0;i<props.length;i++){var prop=props[i];prop.configurable=true;if(prop.value)prop.writable=true;Object.defineProperty(target,prop.key,prop)}}return function(Constructor,protoProps,staticProps){if(protoProps)defineProperties(Constructor.prototype,protoProps);if(staticProps)defineProperties(Constructor,staticProps);return Constructor}}();var _classCallCheck=function(instance,Constructor){if(!(instance instanceof Constructor)){throw new TypeError("Cannot call a class as a function")}};var noop=function noop(){};var identity=function identity(v){return v};var noopSubscription=Object.seal({dispose:function(){}});var asap=require("asap");var Task=function(){function Task(run){_classCallCheck(this,Task);this._run=run;this._observers=Object.create(null);this._uuid=0;this._length=0}_createComputedClass(Task,[{key:"_addSubscriber",value:function _addSubscriber(resolve,reject){var _this=this;var id=this._uuid,subscription;this._uuid++;this._length++;subscription={dispose:function(){var cbs=_this._observers[id];if(cbs){delete _this._observers[id];_this._length--;if(_this._length===0){_this._subscription.dispose();_this._subscription=undefined}}}};this._observers[id]=[resolve,reject,subscription];return subscription}},{key:"run",value:function run(){var _this=this;var resolveFn=arguments[0]===undefined?noop:arguments[0];var rejectFn=arguments[1]===undefined?noop:arguments[1];var self=this,id=this._uuid,observing=true;if(self.error){asap(function(){if(observing)rejectFn(self.error)});return{dispose:function(){return observing=false}}}else if("value"in self){asap(function(){if(observing)resolveFn(self.value)});return{dispose:function(){return observing=false}}}else if(this._length>0){return this._addSubscriber(resolveFn,rejectFn)}else{this._subscription={dispose:function(){return observing=false}};asap(function(){if(observing){_this._subscription=_this._run(function(value){_this.value=value;Object.keys(_this._observers).forEach(function(key){var _observers$key=_slicedToArray(_this._observers[key],3);var resolveFn=_observers$key[0];var _=_observers$key[1];var subscription=_observers$key[2];subscription.dispose();if(resolveFn){resolveFn(value)}})},function(error){_this.error=error;Object.keys(_this._observers).forEach(function(key){var _observers$key=_slicedToArray(_this._observers[key],3);var _=_observers$key[0];var rejectFn=_observers$key[1];var subscription=_observers$key[2];subscription.dispose();if(rejectFn){rejectFn(error)}})})||noopSubscription}});return this._addSubscriber(resolveFn,rejectFn)}}},{key:"catch",value:function _catch(onerror){return this.when(identity,onerror)}},{key:"when",value:function when(projection,onerror){var self=this;return new Task(function(resolve,reject){var subscription=self.run(function(x){try{var nextTask=Task.resolve(projection(x));subscription=nextTask.run(resolve,onerror||reject)}catch(e){onerror&&onerror(e)||reject(e)}},reject);return{dispose:function dispose(){if(subscription){subscription.dispose();subscription=undefined}}}})}},{key:"then",value:function then(resolve,reject){this.run(resolve,reject);return this}}]);return Task}();Task.all=function(args){return new Task(function(resolve,reject){var tasks=args.map(function(val){return Task.resolve(val)}),subscription,results=[],resultCount=0,subscriptions=tasks.map(function(task,index){return task.run(function(val){results[index]=val;resultCount++;if(resultCount==tasks.length){resolve(results)}},function(error){reject(error);subscription.dispose()})});return subscription={dispose:function(){if(subscriptions){subscriptions.forEach(function(sub){return sub.dispose()});subscriptions=undefined}}}})};Task.race=function(args){return new Task(function(resolve,reject){var tasks=args.map(function(val){return Task.resolve(val)}),subscription,results=[],resultCount=0,subscriptions=tasks.map(function(task,index){return task.run(function(val){resolve(val);subscription.dispose()},function(error){reject(error);subscription.dispose()})});return subscription={dispose:function(){if(subscriptions){subscriptions.forEach(function(sub){return sub.dispose()});subscriptions=undefined}}}})};Task.resolve=function(v){var task;if(v instanceof Task){return v}else if(v!==null&&v.then){task=new Task(function(resolve,reject){var observing=true;v.then(function(v){if(observing)resolve(v)},function(e){if(observing)reject(e)});return{dispose:function(){observing=false}}});task.run();return task}else{return new Task(function(resolve,reject){resolve(v)})}};Task.reject=function(e){return new Task(function(resolve,reject){reject(e)})};Task.timeout=function(time){return new Task(function run(resolve,reject){var handle=setTimeout(function(){resolve()},time);return{dispose:function dispose(){clearTimeout(handle)}}})};Task.nextEvent=function(element,eventName){var useCapture=arguments[2]===undefined?false:arguments[2];var syncHandler=arguments[3]===undefined?noop:arguments[3];return new Task(function run(resolve){var handler=function handler(e){syncHandler(e);resolve(e)};element.addEventListener(eventName,handler,useCapture);return{dispose:function(){return element.removeEventListener(eventName,handler)}}})};Task.fnFromNodeCallback=function(fn){return new Task(function run(resolve,reject){fn(function(error,data){if(error){reject(error)}else{resolve(data)}})})};module.exports=Task},{asap:4}]},{},[]);var Task=require("task-lib");var getQuoteButton=document.getElementById("getQuote");var priceTextBox=document.getElementById("price");function getQuote(symbol){return Task.timeout(2e3).when(function(){return(Math.random()*100).toFixed(2)})}var outgoingRequest;function waitForQuote(){if(outgoingRequest){outgoingRequest.dispose();outgoingRequest=undefined}outgoingRequest=Task.nextEvent(getQuoteButton,"click").when(function(){return getQuote("NFLX")}).run(function(val){priceTextBox.value=val;waitForQuote()})}waitForQuote();
{
"name": "requirebin-sketch",
"version": "1.0.0",
"dependencies": {
"task-lib": "0.0.8"
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment