IT:AD:Observables

Summary

An observable is an event stream object wrapped around a target. It is listened to by one or more subscribers.

One thing that threw me at first was 'map'. It's really nothing more than the same as the often used combination of a) create a new array, b) run every item through the func and add it to the array, c) return the array wrapped in an observable. That's it.

The following is a simple demonstration of how an Observable can be made to watch a target (in this case an array), and raise events when the target is modified.

function CreateArray(){
return [
  {id:1,text:"Adam"},
  {id:2,text:"Betty",cat:"A"},
  {id:3,text:"Candy",cat:"A"},
  {id:4,text:"David",cat:"B"},
  {id:5,text:"Eric",cat:"A"},
  {id:6,text:"Frank",cat:"A"},
  {id:7,text:"Gareth",cat:"A"},
]
}
console.clear();
console.log('---')
console.log("Let's start off easy: scalars are not observable:");
var s = "Adam";
var o = Rx.Observable.of(s)
o.subscribe(x=>console.log(x));
s = "Bob";
o.subscribe(x=>console.log(x));

console.log('---')
console.log("...but objects and arrays are:");
var s = ["Adam"];
var o = Rx.Observable.from(s);
o.subscribe(x=>console.log(x));
s[0] = "Bobby";
o.subscribe(x=>console.log(x)); 
            
//create a standard array:
var orig,src,b,o2,o3,a,a1,a2;
orig = src = CreateArray();
console.log('---')
console.log('Arrays can be observed:')
var $src = Rx.Observable.from(src);
console.log('---')
console.log("Subscribe is the result. But note it is as discrete events for each item, and *not an array*...")
$src.subscribe (x=>console.log(`-:${x.text}`))
console.log('---')
console.log("The observable 'observes' changes in the target...")
src.shift();
src.push(  {id:8,text:"Harry",cat:"A"});
src.push(  {id:9,text:"Indy",cat:"A"});
$src.filter(x=>x.cat=='A').take(2).forEach(x => console.log(`A:Hi ${x.text}`));
console.log('---')
console.log('WARN: ... does not catch array replacement:')
src = [{id:1,text:"James",cat:"C"},]
$src.forEach(x => console.log(`B:Hi ${x.text}`));
//--------------------
  console.log('---')
  console.log('...the subscribe is the output of last event *not the array*:');
  $src.map(x=>x).map(x=>x).map(x=>x).map(x=>x).subscribe(x=>a=x);
  console.log(a);

//--------------------
//var $o = Rx.Observable.from([]);
//$o.do(x=>x.push({id:10,text:"James",cat:"D"})).delay(1000).subscribe(x=>a=x);
//a.forEach(x=>console.log(`###: ${x}`));


//var s2 = a2.forEach(x=>console.log(`###: ${x}`));
//--------------------
var btn = document.getElementById('btn');
var o2 = Rx.Observable.fromEvent(btn,'mouseover');
var s2 = o2.forEach(
    (x)=>{console.log('over!');s.dispose();},
  null,
  (x)=>x.console.log('done!'));


console.log(`To simulate a request, you can use 'to':`);
var response = {data:JSON.stringify(CreateArray())};
Rx.Observable.of(response).delay(1000).map(x=>JSON.parse(x.data)).subscribe(x=>console.log(x))

console.log(`You can also use 'from' but it has to be iterable`);
var response = [{data:JSON.stringify(CreateArray())}];
Rx.Observable.from(response).delay(1000).map(x=>JSON.parse(x.data)).subscribe(x=>console.log(x)); 

This produces:

Console was cleared
 ---
 Let's start off easy: scalars are not observable:
 Adam
 Adam
 ---
 ...but objects and arrays are:
 Adam
 Bobby
 ---
 Arrays can be observed:
 ---
 Subscribe is the result. But note it is as discrete events for each item, and *not an array*...
 -:Adam
 -:Betty
 -:Candy
 -:David
 -:Eric
 -:Frank
 -:Gareth
 ---
 The observable 'observes' changes in the target...
 A:Hi Betty
 A:Hi Candy
 ---
 WARN: ... does not catch array replacement:
 B:Hi Betty
 B:Hi Candy
 B:Hi David
 B:Hi Eric
 B:Hi Frank
 B:Hi Gareth
 B:Hi Harry
 B:Hi Indy
 ---
 ...the subscribe is the output of last event *not the array*:
 Object {id: 9, text: "Indy", cat: "A"}
 To simulate a request, you can use 'to':
 You can also use 'from' but it has to be iterable
 [Object, Object, Object, Object, Object, Object, Object]
 [Object, Object, Object, Object, Object, Object, Object]0: Object1: Object2: Object3: Object4: Object5: Object6: Objectlength: 7__proto__: Array(0)