Last active
December 31, 2016 18:57
-
-
Save ross-nordstrom/19adb142a5743f2bc54276159291b94d to your computer and use it in GitHub Desktop.
Demonstration of using RxJS to implement a recursive API Poller. This is an improvement on the simple `Observable.interval()` approach, because we won't kill long-running queries.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
const rxjs = require('rxjs'); | |
/** | |
* The entrypoint function. Pass it the thing to call | |
*/ | |
function dynamicPoll(pollFunc/*, delayFunc*/) { | |
// A recursive stream, which triggers an API call | |
let i = 0; // just here for debugging | |
const trigger = new rxjs.BehaviorSubject(i++); | |
// The polling observable. | |
// While subscribed-to, it will continually call the "API", then queue up the next call | |
// Simple extensions: | |
// - Delay the recursive API call (perhaps dynamic delay based on the previous call's latency) | |
// - Use closure state to implement incremental queries (e.g. maintain and use a 'modifiedSince' option) | |
return trigger.concatMap(() => pollFunc(/*query, options*/)).map(res => { | |
trigger.next(i++); // RECURSE! | |
return res; | |
}); | |
} | |
/** | |
* Mock API call | |
* Uses a delay to emulate an API with variable latency | |
* @return { time:string, delay:number, records:string[] } | |
*/ | |
function fakeApi(/*query, options*/) { | |
const delay = random(250, 10*1000); // random delay between 250ms - 10s | |
const fakeRes = { time: shortDate(), delay: delay, records: ['fake api response'] }; | |
return rxjs.Observable.of(fakeRes).delay(delay); | |
} | |
function random(min, max) { | |
return Math.round(Math.random() * (max - min) + min); | |
} | |
function shortDate() { | |
return new Date().toTimeString().slice(0,8); // e.g. "11:35:13" | |
} | |
function demo() { | |
console.warn('START DEMO'); | |
let myDemo = dynamicPoll(fakeApi).subscribe(res => console.info('API Res: ' + JSON.stringify(res))); | |
setTimeout(() => { | |
myDemo.unsubscribe(); | |
console.warn('END DEMO'); | |
}, 60*1000); | |
} | |
// TO RUN, SIMPLY: | |
// demo(); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Example output: (just copy/paste the Gist into a node console