Updating list upon ionic storage set() completion

Two primary reasons:

Change detection

$ ts-node
> import {BehaviorSubject} from "rxjs";
> import {distinctUntilChanged} from "rxjs/operators";
> import {clone} from "lodash";
> let s$ = new BehaviorSubject<number[]>([]);
> s$.subscribe(nv => console.log("raw " + JSON.stringify(nv)));
raw []
> s$.pipe(distinctUntilChanged()).subscribe(nv => console.log("duc " + JSON.stringify(nv)));
duc []
> s$.next([1]);
raw [1]
duc [1]

happy so far

> let nv = clone(s$.value); nv.push(2); s$.next(nv);
raw [1,2]
duc [1,2]

still cruising, but here comes the patch of black ice

> let xv = s$.value; xv.push(3); s$.next(xv);
raw [1,2,3]

…and crickets from the duc subscription, because it can’t recognize anything as “changed” except the top-level reference.

Aliasing

$ ts-node
> import {BehaviorSubject} from "rxjs";
> let s$ = new BehaviorSubject<number[]>([]);
> let elsewhere: number[] = [];
> let sub1 = s$.subscribe(nv => elsewhere = nv);
> s$.next([1]);
> elsewhere;
[ 1 ]

So far, so good, but now we have aliased elsewhere to the array buried deep within s$.

> sub1.unsubscribe();
> elsewhere === s$.value;
true

ruh roh

> let v = s$.value;
> v.push(2);
> elsewhere;
[ 1, 2 ]

Well, customers$.next is expecting an array, but Array.push returns the array length (this is just an excuse for me to dunk on JavaScript some more…please don’t take it personally…it was totally clear what you meant). Hopefully the underlying question is addressed sufficiently above.

1 Like