├── .babelrc ├── .gitignore ├── LICENSE ├── README.md ├── chapter-01 ├── declarative │ ├── addOne.js │ ├── double.js │ ├── impure_bad.js │ ├── pure_good.js │ └── push.js ├── imperative │ ├── addOne.js │ └── double.js ├── jquery │ ├── index.html │ └── timingSenseTest.js └── rxjs │ ├── index.html │ └── timingSenseTest.js ├── chapter-02 └── src │ ├── create_Observable │ ├── create_new.js │ ├── create_new_simplified.js │ ├── create_new_with_complete.js │ ├── from_array.js │ ├── interval_stream.js │ ├── interval_stream_with_complete.js │ ├── operator.js │ ├── unsubscribe_without_cancel.js │ ├── unsubscrible.js │ └── with_error.js │ ├── import_Observable.js │ ├── import_Observable_add.js │ ├── import_Observable_bind.js │ └── import_Rx.js ├── chapter-03 ├── .gitignore └── src │ ├── call │ └── double.js │ ├── custom │ ├── map │ │ ├── simple.js │ │ ├── useBind.js │ │ ├── useLift.js │ │ ├── useLift2.js │ │ ├── withException.js │ │ └── withUnsubscribe.js │ └── use_prototype.js │ ├── lettable │ ├── filter_map.js │ ├── let.js │ ├── map.js │ ├── range.js │ ├── tripleMap.js │ ├── useMap.js │ └── useMapFilter.js │ └── operator │ ├── array.js │ ├── class.js │ └── operator.js ├── chapter-04 └── creation │ └── src │ ├── ajax │ └── index.html │ ├── defer │ ├── forPromise.js │ └── index.js │ ├── empty │ └── index.js │ ├── from │ ├── fromArguments.js │ ├── fromArray.js │ ├── fromGenerator.js │ ├── fromObservable.js │ ├── fromPromiseReject.js │ ├── fromPromiseResolve.js │ └── fromString.js │ ├── fromEvent │ ├── fromDomEven.html │ └── fromNodeEventEmitter.js │ ├── fromEventPattern │ └── fromNodeEventEmitter.js │ ├── fromPromise │ ├── with_function.js │ └── with_instance.js │ ├── generate │ ├── index.js │ ├── range.js │ └── string.js │ ├── interval │ ├── index.js │ └── interval_from_1.js │ ├── never │ └── index.js │ ├── of │ └── index.js │ ├── range │ ├── index.js │ └── range_map.js │ ├── repeat │ ├── index.js │ └── repeat_sub.js │ ├── repeatWhen │ ├── with_interval.js │ ├── with_notif.js │ └── with_overlap.js │ ├── throw │ ├── _throw.js │ └── index.js │ └── timer │ ├── index.js │ ├── one_argument.js │ └── with_date.js ├── chapter-05 └── combination │ └── src │ ├── combineAll │ ├── glitch.js │ ├── index.js │ ├── never_end.js │ └── with_internal.js │ ├── combineLatest │ ├── glitch │ │ ├── glitch.html │ │ └── show.js │ ├── static.js │ ├── with_map.js │ ├── with_multiple_of.js │ ├── with_of.js │ ├── with_project.js │ ├── with_timer.js │ └── with_timer_of.js │ ├── concat │ ├── differnt_types.js │ ├── instance.js │ ├── multiple_source.js │ └── static.js │ ├── concatAll │ ├── index.js │ ├── throw.js │ └── with_interval.js │ ├── exhaust │ ├── index.js │ └── with_interval_2.js │ ├── forkJoin │ └── index.js │ ├── merge │ ├── instance.js │ ├── limit_concurrent.js │ ├── static.js │ └── with_of.js │ ├── mergeAll │ ├── index.js │ ├── limit_concurrent.js │ ├── throw.js │ └── with_interval.js │ ├── race │ ├── instance.js │ └── static.js │ ├── startWith │ ├── index.js │ ├── multiple.js │ └── with_concat.js │ ├── switch │ ├── index.js │ ├── with_interval.js │ └── with_interval_2.js │ ├── withLatestFrom │ ├── glitch │ │ ├── no_glitch.html │ │ └── show.js │ └── index.js │ ├── zip │ ├── instance.js │ ├── not_same_size.js │ ├── static.js │ ├── with_of_interval.js │ └── with_project.js │ └── zipAll │ ├── index.js │ ├── never_end.js │ └── with_interval.js ├── chapter-06 ├── conditional │ └── src │ │ ├── defaultIfEmpty │ │ ├── empty.js │ │ ├── noDefault.js │ │ └── notEmpty.js │ │ ├── every │ │ ├── index.js │ │ └── interval.js │ │ ├── find │ │ ├── index.js │ │ ├── notFound.js │ │ └── withIndex.js │ │ ├── findIndex │ │ ├── index.js │ │ └── notFound.js │ │ └── isEmpty │ │ ├── delayedEmpty.js │ │ ├── empty.js │ │ ├── error.js │ │ ├── negative.js │ │ └── never.js └── math │ └── src │ ├── count │ ├── index.js │ ├── with_of.js │ └── with_timer.js │ ├── max │ └── index.js │ ├── min │ ├── index.js │ └── object.js │ └── reduce │ ├── average.js │ ├── max.js │ └── sum.js ├── chapter-07 └── filter │ └── src │ ├── audit │ ├── index.js │ └── random.js │ ├── auditTime │ └── index.js │ ├── debounce │ ├── control.js │ └── index.js │ ├── debounceTime │ ├── index.js │ ├── random.js │ └── with_filter.js │ ├── distinct │ ├── index.js │ ├── with_flush.js │ └── with_selector.js │ ├── distinctKey │ └── index.js │ ├── distinctUntilChanged │ ├── index.js │ └── with_compare.js │ ├── distinctUntilKeyChanged │ └── index.js │ ├── elementAt │ └── index.js │ ├── filter │ ├── even.js │ └── with_interval.js │ ├── first │ ├── index.js │ ├── notFound.js │ ├── withDefault.js │ └── withIndex.js │ ├── ignoreElements │ ├── in_filter.js │ └── index.js │ ├── last │ ├── index.js │ ├── notFound.js │ ├── withDefault.js │ ├── withIndex.js │ └── with_interval.js │ ├── sample │ ├── index.js │ ├── random.js │ └── sample.html │ ├── sampleTime │ ├── index.js │ └── random.js │ ├── single │ ├── error.js │ └── index.js │ ├── skip │ ├── index.js │ ├── skipError.js │ └── skipInterval.js │ ├── skipWhile │ └── index.js │ ├── take │ ├── index.js │ └── takeCountWhile.js │ ├── takeLast │ ├── index.js │ ├── nevenEnd.js │ └── with_take.js │ ├── takeUntil │ ├── countClick.html │ ├── index.js │ └── onError.js │ ├── takeWhile │ ├── index.js │ └── take.js │ ├── throttle │ ├── control.js │ └── index.js │ └── throttleTime │ ├── index.js │ ├── random.js │ └── with_filter.js ├── chapter-08 └── transform │ └── src │ ├── buffer │ ├── endless.js │ └── withComplete.js │ ├── bufferCount │ ├── index.js │ └── withStartBufferEvery.js │ ├── bufferTime │ ├── index.js │ └── with2Args.js │ ├── bufferToggle │ ├── index.js │ └── overlap.js │ ├── bufferWhen │ └── index.js │ ├── concatMap │ ├── drag_drop.html │ └── index.js │ ├── concatMapTo │ └── index.js │ ├── exhaustMap │ └── index.js │ ├── exhaustMapTo │ └── index.js │ ├── expand │ └── index.js │ ├── groupBy │ ├── group_event.html │ ├── index.js │ └── with_mergeAll.js │ ├── map │ ├── better.js │ └── index.js │ ├── mapTo │ ├── in_map.js │ └── index.js │ ├── mergeMap │ ├── api.html │ └── index.js │ ├── mergeScan │ ├── index.js │ └── with_delay.js │ ├── pairwise │ └── index.js │ ├── partition │ └── index.js │ ├── pluck │ └── index.js │ ├── scan │ └── index.js │ ├── switchMap │ └── index.js │ ├── window │ └── index.js │ ├── windowCount │ └── index.js │ ├── windowTime │ └── index.js │ ├── windowToggle │ ├── index.js │ └── overlap.js │ └── windowWhen │ └── index.js ├── chapter-09 └── error-handling │ └── src │ ├── async_error.js │ ├── error │ ├── catch │ │ ├── caught.js │ │ ├── index.js │ │ ├── nocatch.js │ │ ├── passError.js │ │ └── recover.js │ ├── finally │ │ └── index.js │ ├── retry │ │ └── index.js │ └── retryWhen │ │ ├── delayRetry.js │ │ ├── index.js │ │ ├── retry.js │ │ ├── retryHotStream.js │ │ ├── retryOverlap.js │ │ ├── retryWithDelay.js │ │ └── retryWithExpotentialDelay.js │ ├── nested_callback.js │ ├── promise │ ├── chain.html │ ├── error_handling.html │ └── stargazer.html │ ├── try_catch_async.js │ ├── try_catch_finally.js │ ├── xmlhttp.html │ └── xmlhttp_with_trycatch.html ├── chapter-10 └── multicast │ └── src │ ├── multicast │ ├── connect.js │ ├── defaultObservableIfEmpty.js │ ├── no_connect.js │ ├── no_selector_diamond.js │ ├── refCount.js │ ├── refCount_with_factory.js │ ├── refCount_with_factory_2.js │ ├── refCount_without_factory.js │ ├── takeWhileInclusive.js │ ├── with_selector.js │ ├── with_selector_diamond.js │ └── with_selector_subscribe.js │ ├── publish │ ├── defaultObservableIfEmpty.js │ ├── implementation.js │ └── lateSub.js │ ├── publishBehavior │ └── index.js │ ├── publishLast │ └── index.js │ ├── publishReplay │ ├── index.js │ ├── withBothArgument.js │ ├── withBufferSize.js │ └── withWindowTime.js │ ├── share │ ├── index.js │ └── lateSub.js │ └── subject │ ├── broadcast.js │ ├── error.js │ ├── error_handled.js │ ├── makeHot.js │ ├── merge_multi_upstream.js │ ├── multi_downstream.js │ ├── multi_upstream.js │ ├── multicast.js │ ├── no_subject.js │ ├── observer_observable.js │ ├── un_reusable.js │ ├── un_reusable_error.js │ ├── unicast.js │ └── unsubscribe.js ├── chapter-11 └── scheduler │ └── src │ ├── callstack │ ├── Promise_vs_setTimeout.js │ ├── nextTick_vs_setTimeout.js │ └── range.js │ ├── customScheduler │ ├── index.js │ └── range.js │ ├── eventloop │ ├── index.js │ ├── interval_asap.js │ └── recursive_queue.js │ ├── observeOn │ ├── index.js │ └── time.js │ ├── operators │ ├── merge_range.js │ └── merge_range_2.js │ ├── performance │ ├── range.js │ └── range_asap.js │ ├── scheduler │ ├── asap_vs_async.js │ ├── interval_asap.js │ ├── queue_vs_async.js │ ├── range.js │ ├── range_asap.js │ ├── range_async.js │ └── range_queue.js │ └── subscribeOn │ ├── index.js │ └── no_subscribeOn.js ├── chapter-12 ├── counter │ ├── counter.js │ ├── counter.testable.js │ └── index.html ├── debugging │ ├── .babelrc │ ├── package-lock.json │ ├── package.json │ └── src │ │ ├── debug.js │ │ ├── do_in_pipe.js │ │ └── use_do.js ├── search │ ├── index.html │ └── search.js └── unit_testing │ ├── .babelrc │ ├── .gitignore │ ├── package-lock.json │ ├── package.json │ ├── src │ ├── counter.js │ ├── search.js │ ├── sum.js │ └── sum.simple.js │ └── test │ ├── counter.test.js │ ├── glitch.test.js │ ├── helpers │ ├── marble-testing.js │ └── test-helper.js │ ├── sample.test.js │ ├── search.test.js │ ├── stream.test.js │ ├── stream_with_helpers.test.js │ ├── stupid.test.js │ └── sum.test.js ├── chapter-13 └── react-rxjs │ ├── react-container │ ├── .gitignore │ ├── README.md │ ├── package-lock.json │ ├── package.json │ ├── public │ │ ├── favicon.ico │ │ ├── index.html │ │ └── manifest.json │ └── src │ │ ├── App.css │ │ ├── App.js │ │ ├── Counter.js │ │ ├── index.css │ │ └── index.js │ ├── rxjs-async │ ├── README.md │ ├── package-lock.json │ ├── package.json │ ├── public │ │ ├── favicon.ico │ │ ├── index.html │ │ └── manifest.json │ └── src │ │ ├── App.css │ │ ├── App.js │ │ ├── Counter.js │ │ ├── index.css │ │ └── index.js │ ├── rxjs-container │ ├── .gitignore │ ├── README.md │ ├── package-lock.json │ ├── package.json │ ├── public │ │ ├── favicon.ico │ │ ├── index.html │ │ └── manifest.json │ └── src │ │ ├── App.css │ │ ├── App.js │ │ ├── Counter.js │ │ ├── index.css │ │ └── index.js │ ├── rxjs-hoc │ ├── .gitignore │ ├── README.md │ ├── package-lock.json │ ├── package.json │ ├── public │ │ ├── favicon.ico │ │ ├── index.html │ │ └── manifest.json │ └── src │ │ ├── App.css │ │ ├── App.js │ │ ├── Counter.js │ │ ├── StopWatch.js │ │ ├── index.css │ │ ├── index.js │ │ └── observe.js │ ├── rxjs-subject │ ├── README.md │ ├── package-lock.json │ ├── package.json │ ├── public │ │ ├── favicon.ico │ │ ├── index.html │ │ └── manifest.json │ └── src │ │ ├── App.css │ │ ├── App.js │ │ ├── Counter.js │ │ ├── index.css │ │ └── index.js │ └── simple │ ├── .gitignore │ ├── README.md │ ├── package-lock.json │ ├── package.json │ ├── public │ ├── favicon.ico │ ├── index.html │ └── manifest.json │ └── src │ ├── App.css │ ├── App.js │ ├── CountButton.js │ ├── Counter.js │ ├── index.css │ └── index.js ├── chapter-14 └── redux-rxjs │ ├── observable │ ├── .gitignore │ ├── README.md │ ├── package-lock.json │ ├── package.json │ ├── public │ │ ├── favicon.ico │ │ ├── index.html │ │ └── manifest.json │ └── src │ │ ├── ActionTypes.js │ │ ├── Actions.js │ │ ├── App.css │ │ ├── App.js │ │ ├── Counter.js │ │ ├── Epic.js │ │ ├── Reducer.js │ │ ├── Store.js │ │ ├── index.css │ │ └── index.js │ ├── reactive-store │ ├── .gitignore │ ├── README.md │ ├── package-lock.json │ ├── package.json │ ├── public │ │ ├── favicon.ico │ │ ├── index.html │ │ └── manifest.json │ └── src │ │ ├── ActionTypes.js │ │ ├── Actions.js │ │ ├── App.css │ │ ├── App.js │ │ ├── Counter.js │ │ ├── Reducer.js │ │ ├── Store.js │ │ ├── createReactiveStore.js │ │ ├── index.css │ │ └── index.js │ └── simple │ ├── .gitignore │ ├── README.md │ ├── package-lock.json │ ├── package.json │ ├── public │ ├── favicon.ico │ ├── index.html │ └── manifest.json │ └── src │ ├── ActionTypes.js │ ├── Actions.js │ ├── App.css │ ├── App.js │ ├── Counter.js │ ├── Reducer.js │ ├── Store.js │ ├── index.css │ └── index.js ├── chapter-15 └── breakout │ ├── breakout.js │ ├── index.html │ └── style.css ├── dissect_rxjs.jpg ├── package-lock.json └── package.json /.babelrc: -------------------------------------------------------------------------------- 1 | { 2 | "presets": [ 3 | "env" 4 | ] 5 | } -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | 《深入浅出RxJS》已经由机械工业出版社发行,这个repo存放的是书中所有的代码。 2 | 3 | 配合响应式编程(包括React和RxJS)的探讨,作者会在知乎专栏《进击的React》中持续更新,欢迎关注。 4 | 5 | 任何技术问题可以通过[知乎](https://www.zhihu.com/people/morgancheng)私信或者值乎咨询,有问必答。 6 | 7 | 执行repo里的code,首先运行`npm install`安装对应依赖包,然后利用npx来执行对应的JavaScript文件,例如: 8 | 9 | ``` 10 | npx babel-node chapter-01/declarative/addOne.js 11 | ``` 12 | 13 | 部分代码在浏览器中执行,用浏览器打开对应HTML文件即可。 14 | 15 | ![alt text](https://github.com/mocheng/dissecting-rxjs/blob/master/dissect_rxjs.jpg) 16 | 17 | 18 | -------------------------------------------------------------------------------- /chapter-01/declarative/addOne.js: -------------------------------------------------------------------------------- 1 | 2 | function addOne(arr) { 3 | return arr.map(item => item + 1); 4 | } 5 | 6 | console.log(addOne([1, 2, 3])); 7 | -------------------------------------------------------------------------------- /chapter-01/declarative/double.js: -------------------------------------------------------------------------------- 1 | 2 | function double(arr) { 3 | return arr.map(item => item * 2); 4 | } 5 | 6 | 7 | const oneArray = [1, 2, 3]; 8 | const anotherArray = double(oneArray); 9 | // anotherArray的内容为[2, 4, 6] 10 | // oneArray的内容依然是[1, 2, 3] 11 | 12 | console.log(oneArray); 13 | console.log(anotherArray); 14 | -------------------------------------------------------------------------------- /chapter-01/declarative/impure_bad.js: -------------------------------------------------------------------------------- 1 | 2 | function arrayPush (arr, newValue) { 3 | arr.push(newValue); 4 | return arr; 5 | } 6 | 7 | function double(arr) { 8 | return arr.map(item => item * 2); 9 | } 10 | 11 | const originalArray = [1, 2, 3]; 12 | const pushedArray = arrayPush(originalArray, 4); 13 | const doubledPushedArray = double(pushedArray); 14 | const doubledOriginalArray = double(originalArray); 15 | 16 | console.log(originalArray); 17 | console.log(pushedArray); 18 | console.log(doubledPushedArray); 19 | console.log(doubledOriginalArray); 20 | -------------------------------------------------------------------------------- /chapter-01/declarative/pure_good.js: -------------------------------------------------------------------------------- 1 | 2 | function arrayPush (arr, newValue) { 3 | return [...arr, newValue]; 4 | } 5 | 6 | function double(arr) { 7 | return arr.map(item => item * 2); 8 | } 9 | 10 | const originalArray = [1, 2, 3]; 11 | const pushedArray = arrayPush(originalArray, 4); 12 | const doubledArray = double(pushedArray); 13 | 14 | console.log(originalArray); 15 | console.log(pushedArray); 16 | console.log(doubledArray); 17 | -------------------------------------------------------------------------------- /chapter-01/declarative/push.js: -------------------------------------------------------------------------------- 1 | 2 | function arrayPush (arr, newValue) { 3 | return [...arr, newValue]; 4 | } 5 | 6 | const oneArray = [1, 2, 3]; 7 | const anotherArray = arrayPush(oneArray, 4); 8 | 9 | console.log(oneArray); 10 | console.log(anotherArray); 11 | -------------------------------------------------------------------------------- /chapter-01/imperative/addOne.js: -------------------------------------------------------------------------------- 1 | 2 | function addOne(arr) { 3 | const results = [] 4 | for (let i = 0; i < arr.length; i++){ 5 | results.push(arr[i] + 1) 6 | } 7 | return results 8 | } 9 | 10 | console.log(addOne([1, 2, 3])); 11 | -------------------------------------------------------------------------------- /chapter-01/imperative/double.js: -------------------------------------------------------------------------------- 1 | 2 | function double(arr) { 3 | const results = [] 4 | for (let i = 0; i < arr.length; i++){ 5 | results.push(arr[i] * 2) 6 | } 7 | return results 8 | } 9 | 10 | console.log(double([1, 2, 3])); 11 | -------------------------------------------------------------------------------- /chapter-01/jquery/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |
5 |
测试你对时间的感觉.
6 | 7 |
你的时间: 毫秒
8 |
9 |
10 | 11 | 12 | 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-01/jquery/timingSenseTest.js: -------------------------------------------------------------------------------- 1 | $(function() { 2 | var startTime; 3 | 4 | $('#hold-me').mousedown(function() { 5 | startTime = new Date(); 6 | }) 7 | 8 | $('#hold-me').mouseup(function() { 9 | if (startTime) { 10 | const elapsedMilliseconds = (new Date() - startTime); 11 | 12 | startTime = null; 13 | $('#hold-time').text(elapsedMilliseconds); 14 | 15 | $.ajax('https://timing-sense-score-board.herokuapp.com/score/' + elapsedMilliseconds).done((res) => { 16 | $('#rank').text('你超过了' + res.rank + '% 的用户'); 17 | }); 18 | } 19 | }) 20 | }) 21 | -------------------------------------------------------------------------------- /chapter-01/rxjs/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |
5 |
测试你对时间的感觉.
6 | 7 |
你的时间: 毫秒
8 |
9 |
10 | 11 | 12 | 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-02/src/create_Observable/create_new.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | 3 | const onSubscribe = observer => { 4 | observer.next(1); 5 | observer.next(2); 6 | observer.next(3); 7 | }; 8 | 9 | const source$ = new Observable(onSubscribe); 10 | 11 | const theObserver = { 12 | next: item => console.log(item) 13 | } 14 | source$.subscribe(theObserver); 15 | 16 | -------------------------------------------------------------------------------- /chapter-02/src/create_Observable/create_new_simplified.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | 3 | const source$ = new Observable(observer => { 4 | observer.next(1); 5 | observer.next(2); 6 | observer.next(3); 7 | }); 8 | 9 | source$.subscribe(console.log); 10 | 11 | -------------------------------------------------------------------------------- /chapter-02/src/create_Observable/create_new_with_complete.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs'; 3 | 4 | const onSubscribe = observer => { 5 | observer.next(1); 6 | observer.next(2); 7 | observer.next(3); 8 | observer.complete(); 9 | }; 10 | 11 | const source$ = new Observable(onSubscribe); 12 | 13 | const theObserver = { 14 | next: item => console.log(item), 15 | complete: () => console.log('No More Data') 16 | } 17 | source$.subscribe(theObserver); 18 | 19 | -------------------------------------------------------------------------------- /chapter-02/src/create_Observable/from_array.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/from'; 3 | 4 | const arr = [1, 2, 3]; 5 | const source$ = Observable.from(arr); 6 | 7 | source$.subscribe(console.log); 8 | 9 | -------------------------------------------------------------------------------- /chapter-02/src/create_Observable/interval_stream.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | 3 | const onSubscribe = observer => { 4 | let number = 1; 5 | const handle = setInterval(() => { 6 | observer.next(number++); 7 | if (number > 3) { 8 | clearInterval(handle); 9 | } 10 | }, 1000); 11 | }; 12 | 13 | const source$ = new Observable(onSubscribe); 14 | 15 | const theObserver = { 16 | next: item => console.log(item) 17 | } 18 | source$.subscribe(theObserver); 19 | 20 | -------------------------------------------------------------------------------- /chapter-02/src/create_Observable/interval_stream_with_complete.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | 3 | const onSubscribe = observer => { 4 | let number = 1; 5 | const handle = setInterval(() => { 6 | observer.next(number++); 7 | if (number > 3) { 8 | clearInterval(handle); 9 | observer.complete(); 10 | } 11 | }, 1000); 12 | }; 13 | 14 | const source$ = new Observable(onSubscribe); 15 | 16 | const theObserver = { 17 | next: item => console.log(item), 18 | complete: () => console.log('No More Data') 19 | } 20 | source$.subscribe(theObserver); 21 | 22 | -------------------------------------------------------------------------------- /chapter-02/src/create_Observable/operator.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/operator/map'; 3 | 4 | const onSubscribe = observer => { 5 | observer.next(1); 6 | observer.next(2); 7 | observer.next(3); 8 | }; 9 | 10 | const source$ = Observable.create(onSubscribe); 11 | 12 | source$.map(x => x*x).subscribe(console.log); 13 | 14 | -------------------------------------------------------------------------------- /chapter-02/src/create_Observable/unsubscribe_without_cancel.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | 3 | const onSubscribe = observer => { 4 | let number = 1; 5 | const handle = setInterval(() => { 6 | console.log('in onSubscribe ', number); 7 | observer.next(number++); 8 | }, 1000); 9 | 10 | return { 11 | unsubscribe: () => { 12 | //clearInterval(handle); 13 | } 14 | }; 15 | }; 16 | 17 | const source$ = new Observable(onSubscribe); 18 | const subscription = source$.subscribe(item => console.log(item)); 19 | 20 | setTimeout(() => { 21 | subscription.unsubscribe(); 22 | }, 3500); 23 | 24 | -------------------------------------------------------------------------------- /chapter-02/src/create_Observable/unsubscrible.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | 3 | const onSubscribe = observer => { 4 | let number = 1; 5 | const handle = setInterval(() => { 6 | observer.next(number++); 7 | }, 1000); 8 | 9 | return { 10 | unsubscribe: () => { 11 | clearInterval(handle); 12 | } 13 | }; 14 | }; 15 | 16 | const source$ = new Observable(onSubscribe); 17 | const subscription = source$.subscribe(item => console.log(item)); 18 | 19 | setTimeout(() => { 20 | subscription.unsubscribe(); 21 | }, 3500); 22 | 23 | -------------------------------------------------------------------------------- /chapter-02/src/create_Observable/with_error.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | 3 | const onSubscribe = observer => { 4 | observer.next(1); 5 | observer.error('Someting Wrong'); 6 | observer.complete(); 7 | }; 8 | 9 | const source$ = new Observable(onSubscribe); 10 | 11 | const theObserver = { 12 | next: item => console.log(item), 13 | error: err => console.log(err), 14 | complete: () => console.log('No More Data'), 15 | } 16 | source$.subscribe(theObserver); 17 | 18 | -------------------------------------------------------------------------------- /chapter-02/src/import_Observable.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | 4 | const source$ = Observable.create((observer) => { 5 | observer.next(1); 6 | observer.next(2); 7 | observer.next(3); 8 | }); 9 | 10 | source$.subscribe(console.log); 11 | 12 | -------------------------------------------------------------------------------- /chapter-02/src/import_Observable_add.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | 4 | const source$ = Observable.of(1, 2, 3); 5 | 6 | source$.subscribe(console.log); 7 | 8 | -------------------------------------------------------------------------------- /chapter-02/src/import_Observable_bind.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {of} from 'rxjs/observable/of'; 3 | 4 | const source$ = Observable::of(1, 2, 3); 5 | 6 | source$.subscribe(console.log); 7 | 8 | -------------------------------------------------------------------------------- /chapter-02/src/import_Rx.js: -------------------------------------------------------------------------------- 1 | import Rx from 'rxjs'; 2 | //import Rx from 'rxjs/Rx'; 3 | 4 | const source$ = Rx.Observable.of(1, 2, 3); 5 | 6 | source$.subscribe(console.log); 7 | 8 | -------------------------------------------------------------------------------- /chapter-03/.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | build 3 | -------------------------------------------------------------------------------- /chapter-03/src/call/double.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {of} from 'rxjs/observable/of'; 3 | import {map} from 'rxjs/operator/map'; 4 | 5 | Observable.prototype.double = function() { 6 | return this::map(x => x * 2); 7 | } 8 | 9 | const source$ = of(1, 2, 3); 10 | const result$ = source$.double(); 11 | 12 | result$.subscribe(value => console.log(value)); 13 | -------------------------------------------------------------------------------- /chapter-03/src/lettable/filter_map.js: -------------------------------------------------------------------------------- 1 | import Observable from 'rxjs/Observable'; 2 | import {range} from 'rxjs/observable/range'; 3 | import {map, filter} from 'rxjs/operators'; 4 | 5 | const source$ = range(1, 5).pipe( 6 | filter( x => x % 2 === 0), 7 | map(x => x * x) 8 | ); 9 | 10 | source$.subscribe(console.log); 11 | -------------------------------------------------------------------------------- /chapter-03/src/lettable/let.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/map'; 4 | import 'rxjs/add/operator/let'; 5 | 6 | const source$ = Observable.of(1, 2, 3); 7 | const double$ = obs$ => obs$.map(x => x * 2); 8 | const result$ = source$.let(double$); 9 | 10 | result$.subscribe(console.log); 11 | -------------------------------------------------------------------------------- /chapter-03/src/lettable/range.js: -------------------------------------------------------------------------------- 1 | import {range} from 'rxjs/observable/range'; 2 | 3 | const source$ = range(1, 5); 4 | 5 | source$.subscribe(console.log); 6 | -------------------------------------------------------------------------------- /chapter-03/src/lettable/tripleMap.js: -------------------------------------------------------------------------------- 1 | //import {Observable} from 'rxjs/Observable'; 2 | import {range} from 'rxjs/observable/range'; 3 | 4 | const tripleMap = fn => source$ => 5 | new Observable(observer => { 6 | return source$.subscribe({ 7 | next: x => { 8 | const result = fn(fn(fn(x))); 9 | observer.next(result); 10 | }, 11 | error: err => observer.error(err), 12 | complete: () => observer.complete() 13 | }); 14 | }); 15 | 16 | const source$ = range(1, 5).pipe( 17 | tripleMap(x => x * x) 18 | ); 19 | 20 | source$.subscribe({ 21 | next: console.log, 22 | complete: () => console.log('done') 23 | }); 24 | -------------------------------------------------------------------------------- /chapter-03/src/lettable/useMap.js: -------------------------------------------------------------------------------- 1 | import {of} from 'rxjs/observable/of'; 2 | import {map} from 'rxjs/operators'; 3 | //import {map} from 'rxjs/operators/map'; 4 | 5 | const source$ = of(1, 2, 3); 6 | const result$ = source$.pipe( 7 | map(x => x * 2) 8 | ); 9 | 10 | result$.subscribe(console.log); 11 | -------------------------------------------------------------------------------- /chapter-03/src/lettable/useMapFilter.js: -------------------------------------------------------------------------------- 1 | import {of} from 'rxjs/observable/of'; 2 | import {map, filter} from 'rxjs/operators'; 3 | 4 | const source$ = of(1, 2, 3); 5 | 6 | const result$ = source$.pipe( 7 | filter(x => x % 2 === 0), 8 | map(x => x * 2) 9 | ); 10 | 11 | result$.subscribe(console.log); 12 | -------------------------------------------------------------------------------- /chapter-03/src/operator/array.js: -------------------------------------------------------------------------------- 1 | const source = [1, 2, 3, 4]; 2 | 3 | const result = source.filter(x => x % 2 === 0).map(x => x * 2); 4 | 5 | console.log(result); 6 | 7 | 8 | -------------------------------------------------------------------------------- /chapter-03/src/operator/class.js: -------------------------------------------------------------------------------- 1 | function Programmer() { 2 | } 3 | 4 | Programmer.create = function() { 5 | console.log('Programmer.create'); 6 | return new Programmer(); 7 | }; 8 | 9 | Programmer.prototype.code = function() { 10 | console.log('Programmer.code'); 11 | return 'Hello World'; 12 | }; 13 | 14 | const morgan = Programmer.create(); 15 | morgan.code(); 16 | -------------------------------------------------------------------------------- /chapter-03/src/operator/operator.js: -------------------------------------------------------------------------------- 1 | import Rx from 'rxjs'; 2 | 3 | const source$ = Rx.Observable.of(1, 2, 3, 4); 4 | 5 | const result$ = source$.filter(x => x % 2 === 0).map(x => x * 2); 6 | 7 | result$.subscribe(console.log); 8 | 9 | 10 | -------------------------------------------------------------------------------- /chapter-04/creation/src/ajax/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |
5 | 6 |
7 |
8 | 9 | 23 | 24 | 25 | 26 | -------------------------------------------------------------------------------- /chapter-04/creation/src/defer/forPromise.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/defer'; 3 | import fetch from 'node-fetch'; 4 | 5 | const observableFactory = () => fetch('https://api.github.com/repos/ReactiveX/rxjs'); 6 | const source$ = Observable.defer(observableFactory); 7 | 8 | source$.subscribe(console.log); 9 | 10 | 11 | -------------------------------------------------------------------------------- /chapter-04/creation/src/defer/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/defer'; 3 | import 'rxjs/add/observable/of'; 4 | 5 | const observableFactory = () => Observable.of(1, 2, 3); 6 | const source$ = Observable.defer(observableFactory); 7 | 8 | source$.subscribe(console.log); 9 | source$.subscribe(console.log); 10 | 11 | 12 | -------------------------------------------------------------------------------- /chapter-04/creation/src/empty/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/empty'; 3 | 4 | const sourceStream$ = Observable.empty(); 5 | 6 | sourceStream$.subscribe( 7 | console.log, 8 | null, 9 | () => console.log('complete') 10 | ); 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-04/creation/src/from/fromArguments.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/from'; 3 | 4 | function toObservable() { 5 | return Observable.from(arguments); 6 | } 7 | 8 | const source$ = toObservable(1, 2, 3); 9 | 10 | source$.subscribe( 11 | console.log, 12 | error => console.log('catch', error), 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-04/creation/src/from/fromArray.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/from'; 3 | 4 | const source$ = Observable.from([1, 2, 3]); 5 | 6 | source$.subscribe( 7 | console.log, 8 | error => console.log('catch', error), 9 | () => console.log('complete') 10 | ); 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-04/creation/src/from/fromGenerator.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/from'; 3 | 4 | 5 | function * generateNumber(max) { 6 | for (let i=1; i<=max; ++i) { 7 | yield i; 8 | } 9 | } 10 | 11 | const sourceStream$ = Observable.from(generateNumber(3)); 12 | 13 | sourceStream$.subscribe( 14 | console.log, 15 | error => console.log('catch', error), 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-04/creation/src/from/fromObservable.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/from'; 4 | 5 | const another$ = Observable.of(1, 2, 3); 6 | const source$ = Observable.from(another$); 7 | 8 | source$.subscribe( 9 | console.log, 10 | error => console.log('catch', error), 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-04/creation/src/from/fromPromiseReject.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/from'; 3 | 4 | const promise = Promise.reject('oops'); 5 | const sourceStream$ = Observable.from(promise); 6 | 7 | sourceStream$.subscribe( 8 | console.log, 9 | error => console.log('catch', error), 10 | () => console.log('complete') 11 | ); 12 | 13 | 14 | -------------------------------------------------------------------------------- /chapter-04/creation/src/from/fromPromiseResolve.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/from'; 3 | 4 | const promise = Promise.resolve('good'); 5 | const sourceStream$ = Observable.from(promise); 6 | 7 | sourceStream$.subscribe( 8 | console.log, 9 | error => console.log('catch', error), 10 | () => console.log('complete') 11 | ); 12 | 13 | 14 | -------------------------------------------------------------------------------- /chapter-04/creation/src/from/fromString.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/from'; 3 | 4 | const source$ = Observable.from('abc'); 5 | 6 | source$.subscribe( 7 | console.log, 8 | error => console.log('catch', error), 9 | () => console.log('complete') 10 | ); 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-04/creation/src/fromEvent/fromDomEven.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |
5 | 6 |
0
7 |
8 | 9 | 18 | 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-04/creation/src/fromEvent/fromNodeEventEmitter.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import EventEmitter from 'events'; 3 | import 'rxjs/add/observable/fromEvent'; 4 | 5 | const emitter = new EventEmitter(); 6 | const source$ = Observable.fromEvent(emitter, 'msg'); 7 | 8 | source$.subscribe( 9 | console.log, 10 | error => console.log('catch', error), 11 | () => console.log('complete') 12 | ); 13 | 14 | emitter.emit('msg', 1); 15 | emitter.emit('msg', 2); 16 | emitter.emit('another-msg', 'oops'); 17 | emitter.emit('msg', 3); 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-04/creation/src/fromPromise/with_function.js: -------------------------------------------------------------------------------- 1 | //This doesn't work for RxJS v5 any more 2 | import {Observable} from 'rxjs/Observable'; 3 | import 'rxjs/add/observable/fromPromise'; 4 | import 'rxjs/add/operator/repeat'; 5 | 6 | let i = 0; 7 | const promiseFactory = () => { 8 | return Promise.resolve(i++); 9 | }; 10 | 11 | const source$ = Observable.fromPromise(promiseFactory).repeat(3); 12 | 13 | source$.subscribe(x => console.log(x)); 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-04/creation/src/fromPromise/with_instance.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/fromPromise'; 3 | import 'rxjs/add/operator/map'; 4 | 5 | const promise = Promise.resolve(1); 6 | 7 | const source$ = Observable.fromPromise(promise) 8 | .map(x => x * 2); 9 | 10 | source$.subscribe(x => console.log(x)); 11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /chapter-04/creation/src/generate/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/generate'; 3 | 4 | /* 5 | const result = []; 6 | for (let i=2; i<10; i+=2) { 7 | result.push(i*i); 8 | } 9 | 10 | console.log(result); 11 | */ 12 | 13 | 14 | const stream$ = Observable.generate( 15 | 2, 16 | value => value < 10, 17 | value => value + 2, 18 | value => value * value 19 | ); 20 | 21 | stream$.subscribe( 22 | console.log, 23 | null, 24 | () => console.log('complete') 25 | ); 26 | 27 | 28 | -------------------------------------------------------------------------------- /chapter-04/creation/src/generate/range.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/generate'; 3 | 4 | const range = (start, count) => { 5 | const max = start + count; 6 | return Observable.generate( 7 | start, 8 | value => value < max, 9 | value => value + 1, 10 | value => value 11 | ); 12 | }; 13 | 14 | range(1, 10).subscribe( 15 | console.log, 16 | null, 17 | () => console.log('complete') 18 | ); 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-04/creation/src/generate/string.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/generate'; 3 | 4 | const stream$ = Observable.generate( 5 | 'x', 6 | value => value.length <= 3, 7 | value => value + 'x', 8 | value => value 9 | ); 10 | 11 | stream$.subscribe( 12 | console.log, 13 | null, 14 | () => console.log('complete') 15 | ); 16 | 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-04/creation/src/interval/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | 4 | const source$ = Observable.interval(1000); 5 | 6 | source$.subscribe( 7 | console.log, 8 | null, 9 | () => console.log('complete') 10 | ); 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-04/creation/src/interval/interval_from_1.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/map'; 4 | 5 | const source$ = Observable.interval(1000); 6 | const result$ = source$.map(x => x + 1); 7 | 8 | result$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-04/creation/src/never/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/never'; 3 | 4 | const source$ = Observable.never(); 5 | 6 | source$.subscribe( 7 | console.log, 8 | null, 9 | () => console.log('complete') 10 | ); 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-04/creation/src/of/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | 4 | const source$ = Observable.of(1, 2, 3); 5 | 6 | source$.subscribe( 7 | console.log, 8 | null, 9 | () => console.log('complete') 10 | ); 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-04/creation/src/range/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | 4 | const source$ = Observable.range(1, 100); 5 | 6 | source$.subscribe( 7 | console.log, 8 | null, 9 | () => console.log('complete') 10 | ); 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-04/creation/src/range/range_map.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import 'rxjs/add/operator/map'; 4 | 5 | const source$ = Observable.range(1, 100).map(x => x * 2); 6 | 7 | source$.subscribe( 8 | console.log, 9 | null, 10 | () => console.log('complete') 11 | ); 12 | 13 | 14 | -------------------------------------------------------------------------------- /chapter-04/creation/src/repeat/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/repeat'; 4 | 5 | const source$ = Observable.of(1, 2, 3); 6 | const repeated$= source$.repeat(10); 7 | 8 | repeated$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-04/creation/src/repeat/repeat_sub.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/operator/repeat'; 3 | 4 | const source$ = Observable.create(observer => { 5 | console.log('on subscribe'); 6 | setTimeout(() => observer.next(1), 1000); 7 | setTimeout(() => observer.next(2), 2000); 8 | setTimeout(() => observer.next(3), 3000); 9 | setTimeout(() => observer.complete(), 4000); 10 | 11 | return { 12 | unsubscribe: () => { 13 | console.log('on unsubscribe'); 14 | } 15 | } 16 | }); 17 | const repeated$ = source$.repeat(2); 18 | 19 | //setInterval(() => console.log(), 50000); 20 | 21 | repeated$.subscribe( 22 | console.log, 23 | null, 24 | () => console.log('complete') 25 | ); 26 | 27 | 28 | 29 | -------------------------------------------------------------------------------- /chapter-04/creation/src/repeatWhen/with_interval.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/repeatWhen'; 5 | 6 | const notifier = () => { 7 | return Observable.interval(1000); 8 | }; 9 | 10 | const source$ = Observable.of(1, 2, 3); 11 | const repeated$ = source$.repeatWhen(notifier); 12 | 13 | repeated$.subscribe( 14 | console.log, 15 | null, 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-04/creation/src/repeatWhen/with_notif.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/repeatWhen'; 5 | import 'rxjs/add/operator/delay'; 6 | 7 | const notifier = (notification$) => { 8 | return notification$.delay(2000); 9 | }; 10 | 11 | const source$ = Observable.of(1, 2, 3); 12 | const repeated$ = source$.repeatWhen(notifier); 13 | 14 | repeated$.subscribe( 15 | console.log, 16 | null, 17 | () => console.log('complete') 18 | ); 19 | 20 | 21 | 22 | -------------------------------------------------------------------------------- /chapter-04/creation/src/throw/_throw.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {_throw} from 'rxjs/observable/throw'; 3 | 4 | const source$ = _throw(new Error('Oops')); 5 | 6 | source$.subscribe( 7 | console.log, 8 | error => console.log('catch', error), 9 | () => console.log('complete') 10 | ); 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-04/creation/src/throw/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/throw'; 3 | 4 | const source$ = Observable.throw(new Error('Oops')); 5 | 6 | source$.subscribe( 7 | console.log, 8 | error => console.log('catch', error), 9 | () => console.log('complete') 10 | ); 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-04/creation/src/timer/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | 4 | const source$ = Observable.timer(2000, 1000); 5 | 6 | source$.subscribe( 7 | console.log, 8 | null, 9 | () => console.log('complete') 10 | ); 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-04/creation/src/timer/one_argument.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | 4 | const source$ = Observable.timer(1000); 5 | 6 | source$.subscribe( 7 | console.log, 8 | null, 9 | () => console.log('complete') 10 | ); 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-04/creation/src/timer/with_date.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | 4 | const now = new Date(); 5 | const later = new Date(now.getTime() + 1000); 6 | const source$ = Observable.timer(later); 7 | 8 | source$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-05/combination/src/combineAll/glitch.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/combineAll'; 5 | import 'rxjs/add/operator/map'; 6 | import 'rxjs/add/operator/take'; 7 | 8 | const original$ = Observable.timer(0, 1000); 9 | const source1$ = original$.map(x => x+'a').take(3); 10 | const source2$ = original$.map(x => x+'b').take(3); 11 | const concated$ = Observable.of(source1$, source2$).combineAll(); 12 | 13 | concated$.subscribe( 14 | console.log, 15 | err => console.log('Error: ', err), 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-05/combination/src/combineAll/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/combineAll'; 5 | import 'rxjs/add/operator/map'; 6 | import 'rxjs/add/operator/take'; 7 | 8 | const source1$ = Observable.timer(0, 1000).map(x => x + 'a').take(3); 9 | const source2$ = Observable.timer(500, 1000).map(x => x + 'b').take(3); 10 | const concated$ = Observable.of(source1$, source2$).combineAll(); 11 | 12 | concated$.subscribe( 13 | console.log, 14 | err => console.log('Error: ', err), 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-05/combination/src/combineAll/never_end.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/observable/never'; 5 | import 'rxjs/add/operator/concat'; 6 | import 'rxjs/add/operator/combineAll'; 7 | import 'rxjs/add/operator/map'; 8 | import 'rxjs/add/operator/take'; 9 | 10 | const ho$ = Observable.interval(1000).take(2).concat(Observable.never()) 11 | .map(x => Observable.interval(1500).map(y => x+':'+y).take(2)); 12 | const concated$ = ho$.combineAll(); 13 | 14 | concated$.subscribe( 15 | console.log, 16 | err => console.log('Error: ', err), 17 | () => console.log('complete') 18 | ); 19 | 20 | -------------------------------------------------------------------------------- /chapter-05/combination/src/combineAll/with_internal.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/combineAll'; 5 | import 'rxjs/add/operator/map'; 6 | import 'rxjs/add/operator/take'; 7 | 8 | const ho$ = Observable.interval(1000) 9 | .take(2) 10 | .map(x => Observable.interval(1500).map(y => x+':'+y).take(2)); 11 | 12 | const concated$ = ho$.combineAll(); 13 | 14 | concated$.subscribe( 15 | console.log, 16 | err => console.log('Error: ', err), 17 | () => console.log('complete') 18 | ); 19 | 20 | -------------------------------------------------------------------------------- /chapter-05/combination/src/combineLatest/glitch/show.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/combineLatest'; 4 | import 'rxjs/add/operator/map'; 5 | 6 | const original$ = Observable.timer(0, 1000); 7 | const source1$ = original$.map(x => x+'a'); 8 | const source2$ = original$.map(x => x+'b'); 9 | const result$ = source1$.combineLatest(source2$); 10 | 11 | result$.subscribe( 12 | console.log, 13 | null, 14 | () => console.log('complete') 15 | ); 16 | 17 | 18 | 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-05/combination/src/combineLatest/static.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/combineLatest'; 4 | 5 | const source1$ = Observable.of('a', 'b', 'c'); 6 | const source2$ = Observable.of(1, 2, 3); 7 | 8 | const result$ = Observable.combineLatest(source1$, source2$); 9 | 10 | result$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-05/combination/src/combineLatest/with_map.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/combineLatest'; 4 | import 'rxjs/add/operator/map'; 5 | 6 | const source1$ = Observable.timer(500, 1000); 7 | const source2$ = Observable.timer(1000, 1000); 8 | const project = (a, b) => `${a} and ${b}`; 9 | const result$ = source1$.combineLatest(source2$) 10 | .map(arr => project(...arr)); 11 | 12 | result$.subscribe( 13 | console.log, 14 | null, 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | 20 | 21 | 22 | -------------------------------------------------------------------------------- /chapter-05/combination/src/combineLatest/with_multiple_of.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/combineLatest'; 4 | 5 | const source1$ = Observable.of('a', 'b', 'c'); 6 | const source2$ = Observable.of(1, 2, 3); 7 | const source3$ = Observable.of('x', 'y'); 8 | 9 | const result$ = source1$.combineLatest(source2$, source3$); 10 | 11 | result$.subscribe( 12 | console.log, 13 | null, 14 | () => console.log('complete') 15 | ); 16 | 17 | 18 | 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-05/combination/src/combineLatest/with_of.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/combineLatest'; 4 | 5 | const source1$ = Observable.of('a', 'b', 'c'); 6 | const source2$ = Observable.of(1, 2, 3); 7 | 8 | const result$ = source1$.combineLatest(source2$); 9 | 10 | result$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-05/combination/src/combineLatest/with_project.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/combineLatest'; 4 | 5 | const source1$ = Observable.timer(500, 1000); 6 | const source2$ = Observable.timer(1000, 1000); 7 | const project = (a, b) => `${a} and ${b}`; 8 | const result$ = source1$.combineLatest(source2$, project); 9 | 10 | result$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-05/combination/src/combineLatest/with_timer.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/combineLatest'; 4 | 5 | const source1$ = Observable.timer(500, 1000); 6 | const source2$ = Observable.timer(1000, 1000); 7 | const result$ = source1$.combineLatest(source2$); 8 | 9 | result$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-05/combination/src/combineLatest/with_timer_of.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/observable/of'; 4 | import 'rxjs/add/operator/combineLatest'; 5 | 6 | const source1$ = Observable.timer(500, 1000); 7 | const source2$ = Observable.of('a'); 8 | const result$ = source1$.combineLatest(source2$); 9 | 10 | result$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-05/combination/src/concat/differnt_types.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/concat'; 4 | 5 | const stream1$ = Observable.of(1, 2, 3); 6 | const stream2$ = Observable.of(4, 5, 6); 7 | const concatedStream$ = stream1$.concat(stream2$).concat('done'); 8 | 9 | concatedStream$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-05/combination/src/concat/instance.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/concat'; 4 | 5 | const source1$ = Observable.of(1, 2, 3); 6 | const source2$ = Observable.of(4, 5, 6); 7 | const concated$ = source1$.concat(source2$); 8 | 9 | concated$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-05/combination/src/concat/multiple_source.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/concat'; 4 | 5 | const source1$ = Observable.of(1, 2, 3); 6 | const source2$ = Observable.of(4, 5, 6); 7 | const source3$ = Observable.of(7, 8, 9); 8 | const concated$ = source1$.concat(source2$, source3$); 9 | 10 | concated$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-05/combination/src/concat/static.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/concat'; 4 | 5 | const source1 = Observable.of(1, 2, 3); 6 | const source2 = Observable.of(4, 5, 6); 7 | const concated$ = Observable.concat( 8 | source1, 9 | source2 10 | ); 11 | 12 | concated$.subscribe( 13 | console.log, 14 | null, 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-05/combination/src/concatAll/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/concatAll'; 5 | import 'rxjs/add/operator/map'; 6 | import 'rxjs/add/operator/take'; 7 | 8 | const source1$ = Observable.interval(1000).map(x => x + 'a').take(3); 9 | const source2$ = Observable.interval(1000).map(x => x + 'b').take(3); 10 | const concated$ = Observable.of(source1$, source2$).concatAll(); 11 | 12 | concated$.subscribe( 13 | console.log, 14 | err => console.log('Error: ', err), 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-05/combination/src/concatAll/throw.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/observable/throw'; 5 | import 'rxjs/add/operator/concatAll'; 6 | import 'rxjs/add/operator/map'; 7 | import 'rxjs/add/operator/take'; 8 | 9 | const source1$ = Observable.interval(1000).map(x => x + 'a').take(3); 10 | const source2$ = Observable.throw(new Error('oops')); 11 | const concated$ = Observable.of(source1$, source2$).concatAll(); 12 | 13 | concated$.subscribe( 14 | console.log, 15 | err => console.log('Error: ', err), 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-05/combination/src/concatAll/with_interval.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/concatAll'; 5 | import 'rxjs/add/operator/map'; 6 | import 'rxjs/add/operator/take'; 7 | 8 | const ho$ = Observable.interval(1000) 9 | .take(2) 10 | .map(x => Observable.interval(1500).map(y => x+':'+y).take(2)); 11 | 12 | const concated$ = ho$.concatAll(); 13 | 14 | concated$.subscribe( 15 | console.log, 16 | err => console.log('Error: ', err), 17 | () => console.log('complete') 18 | ); 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-05/combination/src/exhaust/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/exhaust'; 4 | import 'rxjs/add/operator/map'; 5 | import 'rxjs/add/operator/take'; 6 | 7 | const higherOrder$ = Observable.interval(1000) 8 | .map(() => Observable.interval(300).take(5)); 9 | const result$ = higherOrder$.exhaust(); 10 | 11 | result$.subscribe( 12 | console.log, 13 | err => console.log('Error: ', err), 14 | () => console.log('complete') 15 | ); 16 | 17 | 18 | -------------------------------------------------------------------------------- /chapter-05/combination/src/exhaust/with_interval_2.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/exhaust'; 5 | import 'rxjs/add/operator/map'; 6 | import 'rxjs/add/operator/take'; 7 | 8 | const ho$ = Observable.interval(1000) 9 | .take(3) 10 | .map(x => Observable.interval(700).map(y => x+':'+y).take(2)); 11 | const result$ = ho$.exhaust(); 12 | 13 | result$.subscribe( 14 | console.log, 15 | err => console.log('Error: ', err), 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-05/combination/src/forkJoin/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/observable/forkJoin'; 5 | import 'rxjs/add/operator/map'; 6 | import 'rxjs/add/operator/take'; 7 | 8 | const source1$ = Observable.interval(1000).map(x => x + 'a').take(1); 9 | const source2$ = Observable.interval(1000).map(x => x + 'b').take(3); 10 | const concated$ = Observable.forkJoin(source1$, source2$); 11 | 12 | concated$.subscribe( 13 | console.log, 14 | err => console.log('Error: ', err), 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-05/combination/src/merge/instance.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/map'; 4 | import 'rxjs/add/operator/merge'; 5 | 6 | const source1$ = Observable.timer(0, 1000).map(x => x+'A'); 7 | const source2$ = Observable.timer(500, 1000).map(x => x+'B'); 8 | const merged$ = source1$.merge(source2$); 9 | 10 | merged$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-05/combination/src/merge/limit_concurrent.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/map'; 4 | import 'rxjs/add/operator/merge'; 5 | 6 | const source1$ = Observable.timer(0, 1000).map(x => x+'A'); 7 | const source2$ = Observable.timer(500, 1000).map(x => x+'B'); 8 | const source3$ = Observable.timer(1000, 1000).map(x => x+'C'); 9 | const merged$ = source1$.merge(source2$, source3$, 2); 10 | 11 | merged$.subscribe( 12 | console.log, 13 | err => console.log('Error: ', err), 14 | () => console.log('complete') 15 | ); 16 | 17 | 18 | -------------------------------------------------------------------------------- /chapter-05/combination/src/merge/static.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/map'; 4 | import 'rxjs/add/observable/merge'; 5 | 6 | const source1 = Observable.timer(0, 1000).map(x => x+'A'); 7 | const source2 = Observable.timer(500, 1000).map(x => x+'B'); 8 | const merged$= Observable.merge(source1, source2); 9 | 10 | merged$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-05/combination/src/merge/with_of.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/merge'; 4 | 5 | const source1 = Observable.of(1, 2, 3); 6 | const source2 = Observable.of(4, 5, 6); 7 | const merged$= Observable.merge(source1, source2); 8 | 9 | merged$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-05/combination/src/mergeAll/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/mergeAll'; 5 | import 'rxjs/add/operator/map'; 6 | import 'rxjs/add/operator/take'; 7 | 8 | const source1$ = Observable.timer(0, 1000).map(x => x + 'a').take(3); 9 | const source2$ = Observable.timer(500, 1000).map(x => x + 'b').take(3); 10 | const concated$ = Observable.of(source1$, source2$).mergeAll(); 11 | 12 | concated$.subscribe( 13 | console.log, 14 | err => console.log('Error: ', err), 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-05/combination/src/mergeAll/limit_concurrent.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/mergeAll'; 5 | import 'rxjs/add/operator/map'; 6 | import 'rxjs/add/operator/take'; 7 | 8 | const source1$ = Observable.timer(0, 1000).map(x => x + 'a').take(3); 9 | const source2$ = Observable.timer(500, 1000).map(x => x + 'b').take(3); 10 | const concated$ = Observable.of(source1$, source2$).mergeAll(1); 11 | 12 | concated$.subscribe( 13 | console.log, 14 | err => console.log('Error: ', err), 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-05/combination/src/mergeAll/throw.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/observable/throw'; 5 | import 'rxjs/add/operator/mergeAll'; 6 | import 'rxjs/add/operator/map'; 7 | import 'rxjs/add/operator/take'; 8 | 9 | const source1$ = Observable.interval(1000).map(x => x + 'a').take(3); 10 | const source2$ = Observable.throw(new Error('oops')); 11 | const concated$ = Observable.of(source1$, source2$).mergeAll(); 12 | 13 | concated$.subscribe( 14 | console.log, 15 | err => console.log('Error: ', err), 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-05/combination/src/mergeAll/with_interval.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/mergeAll'; 5 | import 'rxjs/add/operator/map'; 6 | import 'rxjs/add/operator/take'; 7 | 8 | const ho$ = Observable.interval(1000) 9 | .take(2) 10 | .map(x => Observable.interval(1500).map(y => x+':'+y).take(2)); 11 | 12 | const concated$ = ho$.mergeAll(); 13 | 14 | concated$.subscribe( 15 | console.log, 16 | err => console.log('Error: ', err), 17 | () => console.log('complete') 18 | ); 19 | 20 | -------------------------------------------------------------------------------- /chapter-05/combination/src/race/instance.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/race'; 4 | import 'rxjs/add/operator/map'; 5 | 6 | const source1$ = Observable.timer(0, 2000).map(x => x+'a'); 7 | const source2$ = Observable.timer(500, 1000).map(x => x+'b'); 8 | const winner$ = source1$.race(source2$); 9 | 10 | winner$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-05/combination/src/race/static.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/observable/race'; 4 | import 'rxjs/add/operator/map'; 5 | 6 | const source1$ = Observable.timer(0, 2000).map(x => x+'a'); 7 | const source2$ = Observable.timer(500, 1000).map(x => x+'b'); 8 | const winner$ = Observable.race(source1$, source2$); 9 | 10 | winner$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-05/combination/src/startWith/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/startWith'; 4 | 5 | const original$ = Observable.timer(1000, 1000); 6 | const result$ = original$.startWith('start'); 7 | 8 | result$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-05/combination/src/startWith/multiple.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/startWith'; 4 | 5 | const original$ = Observable.timer(1000, 1000); 6 | const result$ = original$.startWith('a', 'b', 'c'); 7 | 8 | result$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-05/combination/src/startWith/with_concat.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/observable/of'; 4 | import 'rxjs/add/operator/concat'; 5 | 6 | const original$ = Observable.timer(1000, 1000); 7 | const result$ = Observable.of('start').concat(original$); 8 | 9 | result$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-05/combination/src/switch/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/switch'; 4 | import 'rxjs/add/operator/map'; 5 | 6 | const higherOrder$ = Observable.interval(1000).map(() => Observable.interval(300)); 7 | const result$ = higherOrder$.switch(); 8 | 9 | result$.subscribe( 10 | console.log, 11 | err => console.log('Error: ', err), 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-05/combination/src/switch/with_interval.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/switch'; 5 | import 'rxjs/add/operator/map'; 6 | import 'rxjs/add/operator/take'; 7 | 8 | const ho$ = Observable.interval(1000) 9 | .take(2) 10 | .map(x => Observable.interval(1500).map(y => x+':'+y).take(2)); 11 | const result$ = ho$.switch(); 12 | 13 | result$.subscribe( 14 | console.log, 15 | err => console.log('Error: ', err), 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-05/combination/src/switch/with_interval_2.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/switch'; 5 | import 'rxjs/add/operator/map'; 6 | import 'rxjs/add/operator/take'; 7 | 8 | const ho$ = Observable.interval(1000) 9 | .take(3) 10 | .map(x => Observable.interval(700).map(y => x+':'+y).take(2)); 11 | const result$ = ho$.switch(); 12 | 13 | result$.subscribe( 14 | console.log, 15 | err => console.log('Error: ', err), 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-05/combination/src/withLatestFrom/glitch/show.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/withLatestFrom'; 4 | import 'rxjs/add/operator/map'; 5 | 6 | const original$ = Observable.timer(0, 1000); 7 | const source1$ = original$.map(x => x+'a'); 8 | const source2$ = original$.map(x => x+'b'); 9 | const result$ = source1$.withLatestFrom(source2$); 10 | 11 | result$.subscribe( 12 | console.log, 13 | null, 14 | () => console.log('complete') 15 | ); 16 | 17 | 18 | 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-05/combination/src/withLatestFrom/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/withLatestFrom'; 4 | import 'rxjs/add/operator/map'; 5 | 6 | const source1$ = Observable.timer(0, 2000).map(x => 100 * x); 7 | const source2$ = Observable.timer(500, 1000); 8 | 9 | const result$ = source1$.withLatestFrom(source2$, (a,b)=> a+b); 10 | 11 | result$.subscribe( 12 | console.log, 13 | null, 14 | () => console.log('complete') 15 | ); 16 | 17 | 18 | 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-05/combination/src/zip/instance.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/zip'; 4 | 5 | const source1$ = Observable.of(1, 2, 3); 6 | const source2$ = Observable.of('a', 'b', 'c'); 7 | const zippedStream$ = source1$.zip(source2$); 8 | 9 | zippedStream$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-05/combination/src/zip/not_same_size.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/zip'; 4 | 5 | const source1$ = Observable.of(1, 2, 3); 6 | const source2$ = Observable.of('a', 'b', 'c', 'd'); 7 | const zippedStream$ = Observable.zip(source1$, source2$); 8 | 9 | zippedStream$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-05/combination/src/zip/static.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/zip'; 4 | 5 | const source1$ = Observable.of(1, 2, 3); 6 | const source2$ = Observable.of('a', 'b', 'c'); 7 | const zippedStream$ = Observable.zip(source1$, source2$); 8 | 9 | zippedStream$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-05/combination/src/zip/with_of_interval.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/zip'; 4 | import 'rxjs/add/observable/interval'; 5 | 6 | const source1$ = Observable.interval(1000); 7 | const source2$ = Observable.of('a', 'b', 'c'); 8 | const zippedStream$ = Observable.zip(source1$, source2$); 9 | 10 | zippedStream$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-05/combination/src/zip/with_project.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/zip'; 4 | 5 | const source1$ = Observable.of(1, 2, 3); 6 | const source2$ = Observable.of('a', 'b', 'c'); 7 | const zippedStream$ = source1$.zip(source2$, (x, y) => x+y); 8 | 9 | zippedStream$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-05/combination/src/zipAll/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/zipAll'; 5 | import 'rxjs/add/operator/map'; 6 | import 'rxjs/add/operator/take'; 7 | 8 | const source1$ = Observable.timer(0, 1000).map(x => x + 'a').take(3); 9 | const source2$ = Observable.timer(500, 1000).map(x => x + 'b').take(3); 10 | const concated$ = Observable.of(source1$, source2$).zipAll(); 11 | 12 | concated$.subscribe( 13 | console.log, 14 | err => console.log('Error: ', err), 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-05/combination/src/zipAll/never_end.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/observable/never'; 5 | import 'rxjs/add/operator/concat'; 6 | import 'rxjs/add/operator/zipAll'; 7 | import 'rxjs/add/operator/map'; 8 | import 'rxjs/add/operator/take'; 9 | 10 | const ho$ = Observable.interval(1000).take(2).concat(Observable.never()) 11 | .map(x => Observable.interval(1500).map(y => x+':'+y).take(2)); 12 | const concated$ = ho$.zipAll(); 13 | 14 | concated$.subscribe( 15 | console.log, 16 | err => console.log('Error: ', err), 17 | () => console.log('complete') 18 | ); 19 | 20 | -------------------------------------------------------------------------------- /chapter-05/combination/src/zipAll/with_interval.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/zipAll'; 5 | import 'rxjs/add/operator/map'; 6 | import 'rxjs/add/operator/take'; 7 | 8 | const ho$ = Observable.interval(1000) 9 | .take(2) 10 | .map(x => Observable.interval(1500).map(y => x+':'+y).take(2)); 11 | const concated$ = ho$.zipAll(); 12 | 13 | concated$.subscribe( 14 | console.log, 15 | err => console.log('Error: ', err), 16 | () => console.log('complete') 17 | ); 18 | 19 | -------------------------------------------------------------------------------- /chapter-06/conditional/src/defaultIfEmpty/empty.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/empty'; 3 | import 'rxjs/add/operator/defaultIfEmpty'; 4 | 5 | const source$ = Observable.empty(); 6 | const new$ = source$.defaultIfEmpty('this is default'); 7 | 8 | new$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-06/conditional/src/defaultIfEmpty/noDefault.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/empty'; 3 | import 'rxjs/add/operator/defaultIfEmpty'; 4 | 5 | const source$ = Observable.empty(); 6 | const new$ = source$.defaultIfEmpty(); 7 | 8 | new$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-06/conditional/src/defaultIfEmpty/notEmpty.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/defaultIfEmpty'; 4 | 5 | const source$ = Observable.interval(1000); 6 | const new$ = source$.defaultIfEmpty('this is default'); 7 | 8 | new$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-06/conditional/src/every/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/every'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | const every$ = source$.every(x => x > 0); 7 | 8 | every$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-06/conditional/src/every/interval.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/every'; 4 | 5 | const source$ = Observable.interval(1000); 6 | const every$ = source$.every(x => x < 3); 7 | 8 | every$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-06/conditional/src/find/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/find'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | const find$ = source$.find(x => x % 2 === 0); 7 | 8 | find$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-06/conditional/src/find/notFound.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/find'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | const find$ = source$.find(x => x > 10); 7 | 8 | find$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-06/conditional/src/find/withIndex.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/find'; 4 | import 'rxjs/add/operator/findIndex'; 5 | import 'rxjs/add/operator/zip'; 6 | 7 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 8 | const isEven = x => x % 2 === 0; 9 | const find$ = source$.find(isEven); 10 | const findIndex$ = source$.findIndex(isEven); 11 | 12 | const zipped$ = find$.zip(findIndex$); 13 | 14 | zipped$.subscribe( 15 | console.log, 16 | null, 17 | () => console.log('complete') 18 | ); 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-06/conditional/src/findIndex/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/findIndex'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | const findIndex$ = source$.findIndex(x => x % 2 === 0); 7 | 8 | findIndex$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-06/conditional/src/findIndex/notFound.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/findIndex'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | const findIndex$ = source$.findIndex(x => x > 10); 7 | 8 | findIndex$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-06/conditional/src/isEmpty/delayedEmpty.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/operator/isEmpty'; 3 | 4 | const source$ = Observable.create(observer => { 5 | setTimeout(() => observer.complete(1), 1000); 6 | }); 7 | const isEmpty$ = source$.isEmpty(); 8 | 9 | isEmpty$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-06/conditional/src/isEmpty/empty.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/empty'; 3 | import 'rxjs/add/operator/isEmpty'; 4 | 5 | const source$ = Observable.empty(); 6 | const isEmpty$ = source$.isEmpty(); 7 | 8 | isEmpty$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-06/conditional/src/isEmpty/error.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/throw'; 3 | import 'rxjs/add/operator/isEmpty'; 4 | 5 | const source$ = Observable.throw(new Error('wrong')); 6 | const isEmpty$ = source$.isEmpty(); 7 | 8 | isEmpty$.subscribe( 9 | console.log, 10 | err => console.log(err), 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-06/conditional/src/isEmpty/negative.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/isEmpty'; 4 | 5 | const source$ = Observable.interval(1000); 6 | const isEmpty$ = source$.isEmpty(); 7 | 8 | isEmpty$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-06/conditional/src/isEmpty/never.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/never'; 3 | import 'rxjs/add/operator/isEmpty'; 4 | 5 | const source$ = Observable.never(); 6 | const isEmpty$ = source$.isEmpty(); 7 | 8 | isEmpty$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | // make this program never exist 15 | setInterval(f => f, 1000); 16 | 17 | 18 | -------------------------------------------------------------------------------- /chapter-06/math/src/count/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | import 'rxjs/add/operator/count'; 5 | 6 | const source$ = Observable.interval(100).take(10); 7 | const count$ = source$.count(); 8 | 9 | count$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-06/math/src/count/with_of.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/concat'; 4 | import 'rxjs/add/operator/count'; 5 | 6 | const source$= Observable.of(1, 2, 3).concat(Observable.of(4, 5, 6)); 7 | const count$ = source$.count(); 8 | 9 | count$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-06/math/src/count/with_timer.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/concat'; 4 | import 'rxjs/add/operator/count'; 5 | 6 | const source$= Observable.timer(1000).concat(Observable.timer(1000)); 7 | const count$ = source$.count(); 8 | 9 | count$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-06/math/src/max/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/max'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | const max$ = source$.max(); 7 | 8 | max$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-06/math/src/min/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/min'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | const min$ = source$.min(); 7 | 8 | min$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | -------------------------------------------------------------------------------- /chapter-06/math/src/min/object.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/min'; 4 | 5 | const intialRelease$ = Observable.of( 6 | {name: 'RxJS', year: 2011}, 7 | {name: 'React', year: 2013}, 8 | {name: 'Redux', year: 2015} 9 | ); 10 | const min$ = intialRelease$.min((a, b) => a.year- b.year); 11 | 12 | min$.subscribe( 13 | console.log, 14 | null, 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-06/math/src/reduce/average.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/reduce'; 4 | import 'rxjs/add/operator/map'; 5 | 6 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 7 | 8 | Observable.prototype.average = function () { 9 | return this.reduce( 10 | (acc, current) => ({sum: acc.sum + current, count: acc.count + 1 }), 11 | {sum: 0, count: 0} 12 | ).map(acc => acc.sum / acc.count); 13 | } 14 | const average$ = source$.average(); 15 | 16 | average$.subscribe( 17 | console.log, 18 | null, 19 | () => console.log('complete') 20 | ); 21 | 22 | 23 | 24 | 25 | -------------------------------------------------------------------------------- /chapter-06/math/src/reduce/max.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/reduce'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | 7 | const maxReducer = comparer => { 8 | return (typeof comparer === 'function') 9 | ? function (x, y) { return comparer(x, y) > 0 ? x : y; } 10 | : function (x, y) { return x > y ? x : y; }; 11 | }; 12 | Observable.prototype.max = function (comparer) { 13 | return this.reduce(maxReducer(comparer)); 14 | } 15 | const max$ = source$.max(); 16 | max$.subscribe( 17 | console.log, 18 | null, 19 | () => console.log('complete') 20 | ); 21 | 22 | 23 | -------------------------------------------------------------------------------- /chapter-06/math/src/reduce/sum.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import 'rxjs/add/operator/reduce'; 4 | 5 | const source$ = Observable.range(1, 100) 6 | const reduced$ = source$.reduce( 7 | (acc, current) => acc + current, 8 | 0 9 | ); 10 | 11 | reduced$.subscribe( 12 | console.log, 13 | null, 14 | () => console.log('complete') 15 | ); 16 | 17 | -------------------------------------------------------------------------------- /chapter-07/filter/src/audit/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/audit'; 5 | 6 | const source$ = Observable.interval(500); 7 | const durationSelector = value => { 8 | return Observable.timer(800); 9 | }; 10 | const result$ = source$.audit(durationSelector); 11 | 12 | result$.subscribe( 13 | console.log, 14 | null, 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-07/filter/src/audit/random.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/take'; 5 | import 'rxjs/add/operator/concat'; 6 | import 'rxjs/add/operator/mapTo'; 7 | import 'rxjs/add/operator/audit'; 8 | 9 | const source$ = Observable.interval(500).take(2).mapTo('A') 10 | .concat(Observable.interval(1000).take(3).mapTo('B')) 11 | .concat(Observable.interval(500).take(3).mapTo('C')); 12 | const durationSelector = value => { 13 | return Observable.timer(800); 14 | }; 15 | const result$ = source$.audit(durationSelector); 16 | 17 | result$.subscribe( 18 | console.log, 19 | null, 20 | () => console.log('complete') 21 | ); 22 | 23 | 24 | -------------------------------------------------------------------------------- /chapter-07/filter/src/auditTime/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/auditTime'; 5 | 6 | const source$ = Observable.interval(1000); 7 | const result$ = source$.auditTime(2000); 8 | 9 | result$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-07/filter/src/debounce/control.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/debounce'; 5 | 6 | const source$ = Observable.interval(1000); 7 | const durationSelector = value => { 8 | return Observable.timer(value % 3 === 0 ? 2000 : 1000); 9 | }; 10 | const result$ = source$.debounce(durationSelector); 11 | 12 | result$.subscribe( 13 | console.log, 14 | null, 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-07/filter/src/debounce/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/debounce'; 5 | 6 | const source$ = Observable.interval(1000); 7 | const durationSelector = value => { 8 | return Observable.interval(2000); 9 | }; 10 | const result$ = source$.debounce(durationSelector); 11 | 12 | result$.subscribe( 13 | console.log, 14 | null, 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-07/filter/src/debounceTime/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/debounceTime'; 4 | 5 | const source$ = Observable.interval(1000); 6 | const result$ = source$.debounceTime(2000); 7 | 8 | result$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/debounceTime/random.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/filter'; 4 | import 'rxjs/add/operator/take'; 5 | import 'rxjs/add/operator/concat'; 6 | import 'rxjs/add/operator/debounceTime'; 7 | 8 | const source$ = Observable.interval(500).take(2).mapTo('A') 9 | .concat(Observable.interval(1000).take(3).mapTo('B')) 10 | .concat(Observable.interval(500).take(3).mapTo('C')); 11 | const result$ = source$.debounceTime(800); 12 | 13 | result$.subscribe( 14 | console.log, 15 | null, 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-07/filter/src/debounceTime/with_filter.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/filter'; 4 | import 'rxjs/add/operator/debounceTime'; 5 | 6 | const source$ = Observable.interval(500); 7 | const filter$ = source$.filter(x => x % 3 === 0); 8 | const result$ = filter$.debounceTime(1000); 9 | 10 | result$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-07/filter/src/distinct/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/distinct'; 4 | 5 | const source$ = Observable.of(0, 1, 1, 2, 0, 0, 1, 3, 3); 6 | const distinct$ = source$.distinct(); 7 | 8 | distinct$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/distinct/with_flush.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/map'; 4 | import 'rxjs/add/operator/distinct'; 5 | 6 | const source$ = Observable.interval(100).map(x => x % 1000); 7 | const distinct$ = source$.distinct(null, Observable.interval(500)); 8 | 9 | distinct$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-07/filter/src/distinct/with_selector.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/distinct'; 4 | 5 | const source$ = Observable.of( 6 | {name: 'RxJS', version: 'v4'}, 7 | {name: 'React', version: 'v15'}, 8 | {name: 'React', version: 'v16'}, 9 | {name: 'RxJS', version: 'v5'} 10 | ); 11 | const distinct$ = source$.distinct(x => x.name); 12 | 13 | distinct$.subscribe( 14 | console.log, 15 | null, 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-07/filter/src/distinctKey/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/mapTo'; 4 | import 'rxjs/add/operator/distinctKey'; 5 | 6 | 7 | // distinctKey is removed since v5.0.0 8 | const source$ = Observable.interval(100).mapTo(2); 9 | const distinct$ = source$.distinctKey(); 10 | 11 | distinct$.subscribe( 12 | console.log, 13 | null, 14 | () => console.log('complete') 15 | ); 16 | 17 | 18 | -------------------------------------------------------------------------------- /chapter-07/filter/src/distinctUntilChanged/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/mapTo'; 4 | import 'rxjs/add/operator/distinctUntilChanged'; 5 | 6 | const source$ = Observable.of(0, 1, 1, 2, 0, 0, 1, 3, 3); 7 | const distinct$ = source$.distinctUntilChanged(); 8 | 9 | distinct$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-07/filter/src/distinctUntilChanged/with_compare.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/distinctUntilChanged'; 4 | 5 | const source$ = Observable.of( 6 | {name: 'RxJS', version: 'v4'}, 7 | {name: 'React', version: 'v15'}, 8 | {name: 'React', version: 'v16'}, 9 | {name: 'RxJS', version: 'v5'} 10 | ); 11 | const compare = (a, b) => a.name === b.name; 12 | const distinct$ = source$.distinctUntilChanged(compare); 13 | 14 | distinct$.subscribe( 15 | console.log, 16 | null, 17 | () => console.log('complete') 18 | ); 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-07/filter/src/distinctUntilKeyChanged/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/mapTo'; 4 | import 'rxjs/add/operator/distinctUntilKeyChanged'; 5 | 6 | const source$ = Observable.of( 7 | {name: 'RxJS', version: 'v4'}, 8 | {name: 'React', version: 'v15'}, 9 | {name: 'React', version: 'v16'}, 10 | {name: 'RxJS', version: 'v5'} 11 | ); 12 | const distinct$ = source$.distinctUntilKeyChanged('name'); 13 | const distinct$ = source$.distinctUntilKeyChanged('name'); 14 | 15 | distinct$.subscribe( 16 | console.log, 17 | null, 18 | () => console.log('complete') 19 | ); 20 | 21 | 22 | -------------------------------------------------------------------------------- /chapter-07/filter/src/elementAt/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/elementAt'; 4 | 5 | const source$ = Observable.of(3, 1, 2); 6 | const result$ = source$.elementAt(3, null); 7 | 8 | result$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/filter/even.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import 'rxjs/add/operator/filter'; 4 | 5 | const source$ = Observable.range(1, 5); 6 | const even$ = source$.filter(x => x % 2 === 0); 7 | 8 | even$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/filter/with_interval.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/filter'; 4 | 5 | const source$ = Observable.interval(1000); 6 | const even$ = source$.filter(x => x % 2 === 0); 7 | 8 | even$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/first/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/first'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | const first$ = source$.first(x => x % 2 === 0); 7 | 8 | first$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/first/notFound.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/first'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | const first$ = source$.first(x => x < 0); 7 | 8 | first$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/first/withDefault.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/first'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | const first$ = source$.first( 7 | x => x < 0, 8 | f => f, 9 | -1 10 | ); 11 | 12 | first$.subscribe( 13 | console.log, 14 | null, 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-07/filter/src/first/withIndex.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/first'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | const first$ = source$.first( 7 | x => x % 2 === 0, 8 | (value, index) => [value, index] 9 | ); 10 | 11 | first$.subscribe( 12 | console.log, 13 | null, 14 | () => console.log('complete') 15 | ); 16 | 17 | 18 | -------------------------------------------------------------------------------- /chapter-07/filter/src/ignoreElements/in_filter.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | import 'rxjs/add/operator/filter'; 5 | 6 | Observable.prototype.ignoreElements = function() { 7 | return this.filter(x => false); 8 | }; 9 | 10 | const source$ = Observable.interval(1000).take(5); 11 | const result$ = source$.ignoreElements(); 12 | 13 | result$.subscribe( 14 | console.log, 15 | null, 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-07/filter/src/ignoreElements/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/ignoreElements'; 4 | import 'rxjs/add/operator/take'; 5 | 6 | const source$ = Observable.interval(1000).take(5); 7 | const result$ = source$.ignoreElements(); 8 | 9 | result$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-07/filter/src/last/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/last'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9, 2, 6); 6 | const last$ = source$.last(x => x % 2 === 0); 7 | 8 | last$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/last/notFound.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/last'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | const last$ = source$.last(x => x < 0); 7 | 8 | last$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/last/withDefault.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/last'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | const last$ = source$.last( 7 | x => x < 0, 8 | f => f, 9 | -1 10 | ); 11 | 12 | last$.subscribe( 13 | console.log, 14 | null, 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-07/filter/src/last/withIndex.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/last'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9, 2, 6); 6 | const last$ = source$.last( 7 | x => x % 2 === 0, 8 | (value, index) => [value, index] 9 | ); 10 | 11 | last$.subscribe( 12 | console.log, 13 | null, 14 | () => console.log('complete') 15 | ); 16 | 17 | 18 | -------------------------------------------------------------------------------- /chapter-07/filter/src/last/with_interval.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | import 'rxjs/add/operator/last'; 5 | 6 | const source$ = Observable.interval(1000).take(4); 7 | const last$ = source$.last(x => x % 2 === 0); 8 | 9 | last$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-07/filter/src/sample/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/sample'; 5 | 6 | const source$ = Observable.interval(500); 7 | const notifer$ = Observable.interval(1500); 8 | const result$ = source$.sample(notifer$); 9 | 10 | result$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-07/filter/src/sample/random.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | import 'rxjs/add/operator/concat'; 5 | import 'rxjs/add/operator/mapTo'; 6 | import 'rxjs/add/operator/sample'; 7 | 8 | const source$ = Observable.interval(500).take(2).mapTo('A') 9 | .concat(Observable.interval(1000).take(3).mapTo('B')) 10 | .concat(Observable.interval(500).take(3).mapTo('C')); 11 | const notifer$ = Observable.interval(1500); 12 | const result$ = source$.sample(notifer$); 13 | 14 | result$.subscribe( 15 | console.log, 16 | null, 17 | () => console.log('complete') 18 | ); 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-07/filter/src/sample/sample.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |
5 | 6 |
0
7 |
8 | 9 | 17 | 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-07/filter/src/sampleTime/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/sampleTime'; 5 | 6 | const source$ = Observable.interval(1000); 7 | const result$ = source$.sampleTime(2000); 8 | 9 | result$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-07/filter/src/sampleTime/random.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/concat'; 4 | import 'rxjs/add/operator/mapTo'; 5 | import 'rxjs/add/operator/take'; 6 | import 'rxjs/add/operator/sampleTime'; 7 | 8 | const source$ = Observable.interval(500).take(2).mapTo('A') 9 | .concat(Observable.interval(1000).take(3).mapTo('B')) 10 | .concat(Observable.interval(500).take(3).mapTo('C')); 11 | const result$ = source$.sampleTime(2000); 12 | 13 | result$.subscribe( 14 | console.log, 15 | null, 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-07/filter/src/single/error.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/single'; 4 | import 'rxjs/add/operator/take'; 5 | 6 | const source$ = Observable.interval(1000); 7 | const result$ = source$.single(x => x % 2 === 0); 8 | 9 | result$.subscribe( 10 | console.log, 11 | err => console.log('Error: ', err), 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-07/filter/src/single/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/single'; 4 | import 'rxjs/add/operator/take'; 5 | 6 | const source$ = Observable.interval(1000).take(2); 7 | const result$ = source$.single(x => x % 2 === 0); 8 | 9 | result$.subscribe( 10 | console.log, 11 | err => console.log('Error: ', err), 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-07/filter/src/skip/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/skip'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | const skip$ = source$.skip(3); 7 | 8 | skip$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/skip/skipError.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/throw'; 3 | import 'rxjs/add/operator/skip'; 4 | 5 | const source$ = Observable.throw('error'); 6 | const skip$ = source$.skip(1); 7 | 8 | skip$.subscribe( 9 | console.log, 10 | err => console.log('error: ', err), 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/skip/skipInterval.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/skip'; 4 | 5 | const source$ = Observable.interval(1000); 6 | const skip$ = source$.skip(3); 7 | 8 | skip$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/skipWhile/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/skipWhile'; 4 | 5 | const source$ = Observable.interval(1000); 6 | const skipWhile$ = source$.skipWhile(value => value % 2 === 0); 7 | 8 | skipWhile$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/take/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | 5 | const source$ = Observable.interval(1000); 6 | const first3$ = source$.take(3); 7 | 8 | first3$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/take/takeCountWhile.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | import 'rxjs/add/operator/filter'; 5 | 6 | const source$ = Observable.interval(1000); 7 | Observable.prototype.takeCountWhile = function (count, predicate) { 8 | return this.filter(predicate).take(count); 9 | } 10 | 11 | const even$ = source$.takeCountWhile( 12 | 3, 13 | value => value % 2 === 0 14 | ); 15 | 16 | even$.subscribe( 17 | console.log, 18 | null, 19 | () => console.log('complete') 20 | ); 21 | 22 | 23 | -------------------------------------------------------------------------------- /chapter-07/filter/src/takeLast/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/takeLast'; 4 | 5 | const source$ = Observable.of(3, 1, 4, 1, 5, 9); 6 | const last3$ = source$.takeLast(3); 7 | 8 | last3$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/takeLast/nevenEnd.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/takeLast'; 4 | 5 | const source$ = Observable.interval(1000); 6 | const last3$ = source$.takeLast(3); 7 | 8 | last3$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/takeLast/with_take.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | import 'rxjs/add/operator/takeLast'; 5 | 6 | const source$ = Observable.interval(1000); 7 | const take$ = source$.take(5); 8 | const last3$ = take$.takeLast(3); 9 | 10 | last3$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-07/filter/src/takeUntil/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/takeUntil'; 5 | 6 | const source$ = Observable.interval(1000); 7 | const notifier$ = Observable.timer(3000); 8 | const takeUntil$ = source$.takeUntil(notifier$); 9 | 10 | takeUntil$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-07/filter/src/takeUntil/onError.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/observable/throw'; 5 | import 'rxjs/add/operator/takeUntil'; 6 | 7 | const source$ = Observable.interval(1000); 8 | const notifier$ = Observable.throw('custom error').delay(500); 9 | const takeUntil$ = source$.takeUntil(notifier$); 10 | 11 | takeUntil$.subscribe( 12 | console.log, 13 | error => console.log('on error: ', error), 14 | () => console.log('complete') 15 | ); 16 | 17 | 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-07/filter/src/takeWhile/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import 'rxjs/add/operator/takeWhile'; 4 | 5 | const source$ = Observable.range(1, 100); 6 | const takeWhile$ = source$.takeWhile( 7 | value => value % 2 === 0 8 | ); 9 | 10 | takeWhile$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-07/filter/src/takeWhile/take.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import 'rxjs/add/operator/takeWhile'; 4 | 5 | const source$ = Observable.range(1, 100); 6 | Observable.prototype.take = function (count) { 7 | return this.takeWhile((value, index) => index < count); 8 | }; 9 | const take$ = source$.take(3); 10 | 11 | take$.subscribe( 12 | console.log, 13 | null, 14 | () => console.log('complete') 15 | ); 16 | 17 | 18 | -------------------------------------------------------------------------------- /chapter-07/filter/src/throttle/control.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/throttle'; 5 | 6 | const source$ = Observable.interval(1000); 7 | const durationSelector = value => { 8 | return Observable.timer(value % 3 === 0 ? 2000 : 1000); 9 | }; 10 | const result$ = source$.throttle(durationSelector); 11 | 12 | result$.subscribe( 13 | console.log, 14 | null, 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-07/filter/src/throttle/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/throttle'; 5 | 6 | const source$ = Observable.interval(1000); 7 | const durationSelector = value => { 8 | console.log(`# call durationSelector with ${value}`); 9 | return Observable.timer(2000); 10 | }; 11 | const result$ = source$.throttle(durationSelector); 12 | 13 | result$.subscribe( 14 | console.log, 15 | null, 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-07/filter/src/throttleTime/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/throttleTime'; 4 | 5 | const source$ = Observable.interval(1000); 6 | const result$ = source$.throttleTime(2000); 7 | 8 | result$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-07/filter/src/throttleTime/random.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/filter'; 4 | import 'rxjs/add/operator/take'; 5 | import 'rxjs/add/operator/concat'; 6 | import 'rxjs/add/operator/mapTo'; 7 | import 'rxjs/add/operator/throttleTime'; 8 | 9 | const source$ = Observable.interval(500).take(2).mapTo('A') 10 | .concat(Observable.interval(1000).take(3).mapTo('B')) 11 | .concat(Observable.interval(500).take(3).mapTo('C')); 12 | const result$ = source$.throttleTime(800); 13 | 14 | result$.subscribe( 15 | console.log, 16 | null, 17 | () => console.log('complete') 18 | ); 19 | 20 | 21 | 22 | -------------------------------------------------------------------------------- /chapter-07/filter/src/throttleTime/with_filter.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/filter'; 4 | import 'rxjs/add/operator/throttleTime'; 5 | 6 | const source$ = Observable.interval(1000); 7 | const filter$ = source$.filter(x => x % 3 === 0); 8 | const result$ = filter$.throttleTime(2000); 9 | 10 | result$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-08/transform/src/buffer/endless.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/buffer'; 4 | import 'rxjs/add/operator/map'; 5 | 6 | const source$ = Observable.timer(0, 100); 7 | const notifer$ = Observable.timer(400, 400); 8 | const result$ = source$.buffer(notifer$); 9 | 10 | result$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-08/transform/src/buffer/withComplete.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/buffer'; 4 | import 'rxjs/add/operator/map'; 5 | 6 | const source$ = Observable.timer(0, 100); 7 | const notifer$ = Observable.timer(400); 8 | const result$ = source$.buffer(notifer$); 9 | 10 | result$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-08/transform/src/bufferCount/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/bufferCount'; 4 | import 'rxjs/add/operator/map'; 5 | 6 | const source$ = Observable.timer(0, 100); 7 | const result$ = source$.bufferCount(4, 2); 8 | 9 | result$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-08/transform/src/bufferCount/withStartBufferEvery.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/bufferCount'; 4 | import 'rxjs/add/operator/map'; 5 | 6 | const source$ = Observable.timer(0, 100); 7 | const result$ = source$.bufferCount(4, 2); 8 | 9 | result$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-08/transform/src/bufferTime/index.js: -------------------------------------------------------------------------------- 1 | //run this file after babel. Otherwise the timing might not be correct. 2 | import {Observable} from 'rxjs/Observable'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/bufferTime'; 5 | 6 | const source$ = Observable.timer(0, 100); 7 | const result$ = source$.bufferTime(400); 8 | 9 | result$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-08/transform/src/bufferTime/with2Args.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/bufferTime'; 4 | 5 | const source$ = Observable.interval(100); 6 | const result$ = source$.bufferTime(400, 200); 7 | 8 | result$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-08/transform/src/bufferToggle/index.js: -------------------------------------------------------------------------------- 1 | //run this file after babel. Otherwise the timing might not be correct. 2 | import {Observable} from 'rxjs/Observable'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/observable/empty'; 5 | import 'rxjs/add/operator/bufferToggle'; 6 | 7 | const source$ = Observable.timer(0, 100); 8 | const openings$ = Observable.timer(0, 400); 9 | const closingSelector = value => { 10 | console.log('#enter closingSelector'); 11 | return value % 2 === 0 ? Observable.timer(200) : Observable.timer(100); 12 | }; 13 | const result$ = source$.bufferToggle(openings$, closingSelector); 14 | 15 | result$.subscribe( 16 | console.log, 17 | null, 18 | () => console.log('complete') 19 | ); 20 | 21 | 22 | -------------------------------------------------------------------------------- /chapter-08/transform/src/bufferToggle/overlap.js: -------------------------------------------------------------------------------- 1 | //run this file after babel. Otherwise the timing might not be correct. 2 | import {Observable} from 'rxjs/Observable'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/observable/empty'; 5 | import 'rxjs/add/operator/bufferToggle'; 6 | 7 | const source$ = Observable.timer(0, 100); 8 | const openings$ = Observable.timer(0, 400); 9 | const closingSelector = value => { 10 | console.log('#enter closingSelector'); 11 | return value % 2 === 0 ? Observable.timer(500) : Observable.timer(100); 12 | }; 13 | const result$ = source$.bufferToggle(openings$, closingSelector); 14 | 15 | result$.subscribe( 16 | console.log, 17 | null, 18 | () => console.log('complete') 19 | ); 20 | 21 | 22 | -------------------------------------------------------------------------------- /chapter-08/transform/src/bufferWhen/index.js: -------------------------------------------------------------------------------- 1 | //run this file after babel. Otherwise the timing might not be correct. 2 | import {Observable} from 'rxjs/Observable'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/bufferWhen'; 5 | 6 | const source$ = Observable.timer(0, 100); 7 | const closingSelector = () => { 8 | return Observable.timer(400); 9 | }; 10 | const result$ = source$.bufferWhen(closingSelector); 11 | 12 | result$.subscribe( 13 | console.log, 14 | null, 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-08/transform/src/concatMap/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | import 'rxjs/add/operator/concatMap'; 5 | 6 | const source$ = Observable.interval(100); 7 | const result$ = source$.concatMap( 8 | (value, index) => { 9 | console.log('#enter func'); 10 | return Observable.interval(100).take(5); 11 | } 12 | ); 13 | 14 | result$.subscribe( 15 | console.log, 16 | null, 17 | () => console.log('complete') 18 | ); 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-08/transform/src/concatMapTo/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/observable/of'; 4 | import 'rxjs/add/operator/take'; 5 | import 'rxjs/add/operator/concatMapTo'; 6 | 7 | const intervalStream$ = Observable.interval(100); 8 | const innerStream$ = Observable.interval(1000).take(3); 9 | //const innerStream$ = Observable.of(1, 2, 3); 10 | const downStream$ = intervalStream$.concatMapTo( 11 | innerStream$ 12 | ); 13 | 14 | downStream$.subscribe( 15 | console.log, 16 | null, 17 | () => console.log('complete') 18 | ); 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-08/transform/src/exhaustMap/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | import 'rxjs/add/operator/exhaustMap'; 5 | 6 | const source$ = Observable.interval(100); 7 | const result$ = source$.exhaustMap( 8 | (value, index) => { 9 | console.log('#enter func'); 10 | return Observable.interval(100).take(5); 11 | } 12 | ); 13 | 14 | result$.subscribe( 15 | console.log, 16 | null, 17 | () => console.log('complete') 18 | ); 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-08/transform/src/exhaustMapTo/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | import 'rxjs/add/operator/exhaustMap'; 5 | 6 | Observable.prototype.exhaustMapTo = function (inner$) { 7 | return this.exhaustMap(() => inner$); 8 | }; 9 | 10 | const source$ = Observable.interval(100); 11 | const result$ = source$.exhaustMapTo(Observable.interval(100).take(5)); 12 | 13 | result$.subscribe( 14 | console.log, 15 | null, 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-08/transform/src/expand/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/observable/of'; 4 | import 'rxjs/add/operator/delay'; 5 | import 'rxjs/add/operator/expand'; 6 | 7 | const source$ = Observable.of(1); 8 | const result$ = source$.expand( 9 | (value, index) => Observable.of(value * 2).delay(100) 10 | ); 11 | 12 | result$.subscribe( 13 | console.log, 14 | null, 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-08/transform/src/groupBy/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/groupBy'; 4 | 5 | const source$ = Observable.interval(1000); 6 | const groupBy$ = source$.groupBy( 7 | x => x % 2 8 | ); 9 | 10 | groupBy$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-08/transform/src/groupBy/with_mergeAll.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/groupBy'; 4 | import 'rxjs/add/operator/mergeAll'; 5 | 6 | const source$ = Observable.interval(1000); 7 | const groupBy$ = source$.groupBy( 8 | x => x % 2 9 | ).mergeAll(); 10 | 11 | groupBy$.subscribe( 12 | console.log, 13 | null, 14 | () => console.log('complete') 15 | ); 16 | 17 | 18 | -------------------------------------------------------------------------------- /chapter-08/transform/src/map/better.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/map'; 4 | 5 | const source$ = Observable.of(3, 1, 4); 6 | const context = {separator: ':'}; 7 | const mapFunc = (function (separator) { 8 | return function(value, index) { 9 | return `${value} ${separator} ${index}`; 10 | }; 11 | })(context.separator) 12 | const result$ = source$.map(mapFunc); 13 | result$.subscribe( 14 | console.log, 15 | null, 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-08/transform/src/map/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/map'; 4 | 5 | const source$ = Observable.of(3, 1, 4); 6 | const mapFunc = function(value, index) { // this should not be big arrow function 7 | return `${value} ${this.separator} ${index}`; 8 | }; 9 | const context = {separator: ':'}; 10 | const result$ = source$.map(mapFunc, context); 11 | result$.subscribe( 12 | console.log, 13 | null, 14 | () => console.log('complete') 15 | ); 16 | 17 | 18 | -------------------------------------------------------------------------------- /chapter-08/transform/src/mapTo/in_map.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/map'; 4 | 5 | Observable.prototype.mapTo = function (value) { 6 | return this.map(x => value); 7 | }; 8 | 9 | const source$ = Observable.of(3, 1, 4); 10 | const result$ = source$.mapTo('A'); 11 | result$.subscribe( 12 | console.log, 13 | null, 14 | () => console.log('complete') 15 | ); 16 | 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-08/transform/src/mapTo/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/mapTo'; 4 | 5 | const source$ = Observable.of(3, 1, 4); 6 | const result$ = source$.mapTo('A'); 7 | result$.subscribe( 8 | console.log, 9 | null, 10 | () => console.log('complete') 11 | ); 12 | 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-08/transform/src/mergeMap/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | import 'rxjs/add/operator/mergeMap'; 5 | 6 | const source$ = Observable.interval(200).take(2); 7 | const result$ = source$.mergeMap( 8 | (value, index) => { 9 | console.log('#enter func'); 10 | return Observable.interval(100).take(5); 11 | } 12 | ); 13 | 14 | result$.subscribe( 15 | console.log, 16 | null, 17 | () => console.log('complete') 18 | ); 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-08/transform/src/mergeScan/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/mergeScan'; 5 | 6 | const source$ = Observable.interval(100); 7 | const result$ = source$.mergeScan((accumulation, value) => { 8 | return Observable.of(accumulation + value); 9 | }, 10 | 0); // must have seed argument 11 | 12 | result$.subscribe( 13 | console.log, 14 | null, 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-08/transform/src/pairwise/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/pairwise'; 4 | 5 | const source$ = Observable.timer(0, 100); 6 | const result$ = source$.pairwise(); 7 | 8 | result$.subscribe( 9 | console.log, 10 | null, 11 | () => console.log('complete') 12 | ); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-08/transform/src/partition/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/partition'; 4 | 5 | const source$ = Observable.timer(0, 100); 6 | const [even$, odd$] = source$.partition(x => x % 2 === 0); 7 | 8 | even$.subscribe(value => console.log('even:', value)); 9 | odd$.subscribe(value => console.log('odd:', value)); 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-08/transform/src/pluck/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/of'; 3 | import 'rxjs/add/operator/pluck'; 4 | 5 | const source$ = Observable.of( 6 | {name: 'RxJS', version: 'v4'}, 7 | {name: 'React', version: 'v15'}, 8 | {name: 'React', version: 'v16'}, 9 | {name: 'RxJS', version: 'v5'} 10 | ); 11 | const result$ = source$.pluck('name', 'what', 'else'); 12 | result$.subscribe( 13 | console.log, 14 | null, 15 | () => console.log('complete') 16 | ); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-08/transform/src/scan/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/scan'; 4 | 5 | const source$ = Observable.interval(100); 6 | const result$ = source$.scan((accumulation, value) => { 7 | return accumulation + value; 8 | }); 9 | 10 | result$.subscribe( 11 | console.log, 12 | null, 13 | () => console.log('complete') 14 | ); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-08/transform/src/switchMap/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | import 'rxjs/add/operator/switchMap'; 5 | 6 | const source$ = Observable.interval(100).take(2); 7 | const result$ = source$.switchMap( 8 | (value, index) => { 9 | console.log('#enter func'); 10 | return Observable.interval(100).take(5); 11 | } 12 | ); 13 | 14 | result$.subscribe( 15 | console.log, 16 | null, 17 | () => console.log('complete') 18 | ); 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-08/transform/src/window/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/timer'; 3 | import 'rxjs/add/operator/window'; 4 | 5 | const source$ = Observable.timer(0, 100); 6 | const notifer$ = Observable.timer(400, 400); 7 | const result$ = source$.window(notifer$); 8 | 9 | result$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-08/transform/src/windowCount/index.js: -------------------------------------------------------------------------------- 1 | //run this file after babel. Otherwise the timing might not be correct. 2 | import {Observable} from 'rxjs/Observable'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/windowCount'; 5 | 6 | const source$ = Observable.timer(0, 100); 7 | const result$ = source$.windowCount(4); 8 | 9 | result$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-08/transform/src/windowTime/index.js: -------------------------------------------------------------------------------- 1 | //run this file after babel. Otherwise the timing might not be correct. 2 | import {Observable} from 'rxjs/Observable'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/windowTime'; 5 | 6 | const source$ = Observable.timer(0, 100); 7 | const result$ = source$.windowTime(400); 8 | 9 | result$.subscribe( 10 | console.log, 11 | null, 12 | () => console.log('complete') 13 | ); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-08/transform/src/windowToggle/index.js: -------------------------------------------------------------------------------- 1 | //run this file after babel. Otherwise the timing might not be correct. 2 | import {Observable} from 'rxjs/Observable'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/operator/windowToggle'; 5 | 6 | const source$ = Observable.timer(0, 100); 7 | const openings$ = Observable.timer(0, 400); 8 | const closingSelector = value => { 9 | console.log('#enter closingSelector', value); 10 | return value % 2 === 0 ? Observable.timer(200) : Observable.timer(100); 11 | }; 12 | const result$ = source$.windowToggle(openings$, closingSelector); 13 | 14 | result$.subscribe( 15 | console.log, 16 | null, 17 | () => console.log('complete') 18 | ); 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-08/transform/src/windowToggle/overlap.js: -------------------------------------------------------------------------------- 1 | //run this file after babel. Otherwise the timing might not be correct. 2 | import {Observable} from 'rxjs/Observable'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/observable/empty'; 5 | import 'rxjs/add/operator/windowToggle'; 6 | 7 | const source$ = Observable.timer(0, 100); 8 | const openings$ = Observable.timer(0, 400); 9 | const closingSelector = value => { 10 | console.log('#enter closingSelector'); 11 | return value % 2 === 0 ? Observable.timer(500) : Observable.timer(100); 12 | }; 13 | const result$ = source$.windowToggle(openings$, closingSelector); 14 | 15 | result$.subscribe( 16 | console.log, 17 | null, 18 | () => console.log('complete') 19 | ); 20 | 21 | 22 | -------------------------------------------------------------------------------- /chapter-08/transform/src/windowWhen/index.js: -------------------------------------------------------------------------------- 1 | //run this file after babel. Otherwise the timing might not be correct. 2 | import {Observable} from 'rxjs/Observable'; 3 | import 'rxjs/add/observable/timer'; 4 | import 'rxjs/add/observable/empty'; 5 | import 'rxjs/add/operator/windowWhen'; 6 | 7 | const source$ = Observable.timer(0, 100); 8 | const closingSelector = () => { 9 | return Observable.timer(400); 10 | }; 11 | const result$ = source$.windowWhen(closingSelector); 12 | 13 | result$.subscribe( 14 | console.log, 15 | null, 16 | () => console.log('complete') 17 | ); 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-09/error-handling/src/async_error.js: -------------------------------------------------------------------------------- 1 | const invalidJsonString = 'Not Found'; 2 | 3 | const delayParse = (jsonString, callback) => { 4 | setTimeout(() => { 5 | try { 6 | const result = JSON.parse(jsonString); 7 | callback(null, result); 8 | } catch (error) { 9 | callback(error); 10 | } 11 | }, 1000); 12 | }; 13 | 14 | delayParse(invalidJsonString, (error, result) => { 15 | if (error) { 16 | console.log('catch error: ', error); 17 | return; 18 | } 19 | 20 | console.log(result); 21 | }); 22 | 23 | 24 | -------------------------------------------------------------------------------- /chapter-09/error-handling/src/error/catch/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import 'rxjs/add/observable/of'; 4 | import 'rxjs/add/operator/map'; 5 | import 'rxjs/add/operator/catch'; 6 | 7 | const throwOnUnluckyNumber = value => { 8 | if (value === 4) { 9 | throw new Error('unlucky number 4'); 10 | } 11 | 12 | return value; 13 | }; 14 | 15 | const source$ = Observable.range(1, 5); 16 | const error$ = source$.map(throwOnUnluckyNumber) 17 | const catch$ = error$.catch((err, caught$) => Observable.of(8)); 18 | 19 | catch$.subscribe( 20 | value => console.log('value: ', value), 21 | err => console.log('error: ', err), 22 | () => console.log('complete') 23 | ); 24 | 25 | 26 | 27 | -------------------------------------------------------------------------------- /chapter-09/error-handling/src/error/catch/nocatch.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/observable/of'; 4 | import 'rxjs/add/observable/throw'; 5 | import 'rxjs/add/operator/map'; 6 | import 'rxjs/add/operator/catch'; 7 | 8 | const throwOnUnluckyNumber = value => { 9 | if (value === 4) { 10 | throw new Error('unlucky number 4'); 11 | } 12 | 13 | return value; 14 | }; 15 | 16 | const source$ = Observable.interval(500); 17 | const nocatch$ = source$.map(throwOnUnluckyNumber); 18 | 19 | nocatch$.subscribe( 20 | value => console.log('value: ', value), 21 | ); 22 | 23 | 24 | 25 | -------------------------------------------------------------------------------- /chapter-09/error-handling/src/promise/chain.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |
5 |
6 | 7 | 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /chapter-09/error-handling/src/promise/error_handling.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |
5 |
6 | 7 | 16 | 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-09/error-handling/src/promise/stargazer.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |
5 |
6 | 7 | 23 | 24 | 25 | 26 | -------------------------------------------------------------------------------- /chapter-09/error-handling/src/try_catch_async.js: -------------------------------------------------------------------------------- 1 | const invalidJsonString = 'Not Found'; 2 | 3 | try { 4 | setTimeout(() => { 5 | JSON.parse(invalidJsonString); 6 | }, 1000); 7 | } catch (error) { 8 | console.log('catch error'); 9 | } 10 | -------------------------------------------------------------------------------- /chapter-09/error-handling/src/try_catch_finally.js: -------------------------------------------------------------------------------- 1 | //const jsonString = 'Not Found'; 2 | const jsonString = '{"foo": "bar"}'; 3 | 4 | let result; 5 | try { 6 | result = JSON.parse(jsonString); 7 | } catch (error) { 8 | result = {}; 9 | } finally { 10 | console.log(result); 11 | } 12 | -------------------------------------------------------------------------------- /chapter-09/error-handling/src/xmlhttp.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 13 | 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-09/error-handling/src/xmlhttp_with_trycatch.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 17 | 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/multicast/connect.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/multicast'; 5 | import 'rxjs/add/operator/take'; 6 | 7 | const coldSource$ = Observable.interval(1000).take(3); 8 | const tick$ = coldSource$.multicast(new Subject()); 9 | 10 | tick$.subscribe(value => console.log('observer 1: ' + value)); 11 | setTimeout(() => { 12 | tick$.subscribe(value => console.log('observer 2: ' + value)); 13 | }, 1500); 14 | 15 | tick$.connect(); 16 | 17 | 18 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/multicast/no_connect.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/multicast'; 5 | import 'rxjs/add/operator/take'; 6 | 7 | const coldSource$ = Observable.interval(1000).take(3); 8 | const tick$ = coldSource$.multicast(new Subject()); 9 | 10 | tick$.subscribe(value => console.log('observer 1: ' + value)); 11 | setTimeout(() => { 12 | tick$.subscribe(value => console.log('observer 2: ' + value)); 13 | }, 1500); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/multicast/no_selector_diamond.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | import 'rxjs/add/operator/do'; 5 | import 'rxjs/add/operator/delay'; 6 | import 'rxjs/add/operator/merge'; 7 | 8 | const coldSource$ = Observable.interval(1000).take(2).do(x => console.log('source ', x)); 9 | const tick$ = coldSource$; 10 | const delayedTicks$ = tick$.delay(500); 11 | const mergedTick$ = delayedTicks$.merge(tick$); 12 | 13 | mergedTick$.subscribe(value => console.log('observer : ' + value)); 14 | 15 | 16 | 17 | 18 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/multicast/refCount.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/multicast'; 5 | import 'rxjs/add/operator/take'; 6 | 7 | const coldSource$ = Observable.interval(1000).take(3); 8 | const tick$ = coldSource$.multicast(new Subject()).refCount(); 9 | 10 | setTimeout(() => { 11 | tick$.subscribe(value => console.log('observer 1: ' + value)); 12 | }, 500); 13 | setTimeout(() => { 14 | tick$.subscribe(value => console.log('observer 2: ' + value)); 15 | }, 2000); 16 | 17 | 18 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/multicast/refCount_with_factory.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/multicast'; 5 | import 'rxjs/add/operator/take'; 6 | 7 | const subjectFactory = () => { 8 | console.log('enter subjectFactory'); 9 | return new Subject(); 10 | } 11 | 12 | const coldSource$ = Observable.interval(1000).take(3); 13 | const tick$ = coldSource$.multicast(subjectFactory).refCount(); 14 | 15 | tick$.subscribe(value => console.log('observer 1: ' + value)); 16 | setTimeout(() => { 17 | tick$.subscribe(value => console.log('observer 2: ' + value)); 18 | }, 5000); 19 | 20 | 21 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/multicast/refCount_with_factory_2.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/multicast'; 5 | import 'rxjs/add/operator/take'; 6 | 7 | const subjectFactory = () => new Subject(); 8 | 9 | const coldSource$ = Observable.interval(1000).take(3); 10 | const tick$ = coldSource$.multicast(subjectFactory).refCount(); 11 | 12 | tick$.subscribe(value => console.log('observer 1: ' + value)); 13 | setTimeout(() => { 14 | tick$.subscribe(value => console.log('observer 2: ' + value)); 15 | }, 1500); 16 | setTimeout(() => { 17 | tick$.subscribe(value => console.log('observer 3: ' + value)); 18 | }, 5000); 19 | 20 | 21 | 22 | 23 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/multicast/refCount_without_factory.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/multicast'; 5 | import 'rxjs/add/operator/take'; 6 | 7 | const coldSource$ = Observable.interval(1000).take(3); 8 | const tick$ = coldSource$.multicast(new Subject()).refCount(); 9 | 10 | tick$.subscribe(value => console.log('observer 1: ' + value)); 11 | 12 | setTimeout(() => { 13 | tick$.subscribe(value => console.log('observer 2: ' + value)); 14 | }, 5000); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/multicast/with_selector.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/observable/of'; 5 | import 'rxjs/add/operator/multicast'; 6 | import 'rxjs/add/operator/concat'; 7 | import 'rxjs/add/operator/take'; 8 | 9 | const coldSource$ = Observable.interval(1000).take(3); 10 | const selector = shared => { 11 | return shared.concat(Observable.of('done')); 12 | } 13 | const tick$ = coldSource$.multicast(new Subject(), selector); 14 | 15 | tick$.subscribe(value => console.log('observer 1: ' + value)); 16 | 17 | setTimeout(() => { 18 | tick$.subscribe(value => console.log('observer 2: ' + value)); 19 | }, 5000); 20 | 21 | 22 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/publish/implementation.js: -------------------------------------------------------------------------------- 1 | function publish(selector) { 2 | if (selector) { 3 | return this.multicast(() => new Subject(), selector); 4 | } else { 5 | return this.multicast(new Subject()); 6 | } 7 | } 8 | 9 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/publish/lateSub.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/publish'; 4 | import 'rxjs/add/operator/take'; 5 | 6 | const tick$ = Observable.interval(1000).take(3); 7 | const sharedTick$ = tick$.publish().refCount(); 8 | 9 | sharedTick$.subscribe(value => console.log('observer 1: ' + value)); 10 | setTimeout(() => { 11 | sharedTick$.subscribe(value => console.log('observer 2: ' + value)); 12 | }, 5000); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/publishBehavior/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/publishBehavior'; 4 | import 'rxjs/add/operator/take'; 5 | 6 | const tick$ = Observable.interval(1000).take(3); 7 | const sharedTick$ = tick$.publishBehavior(-1).refCount(); 8 | 9 | sharedTick$.subscribe(value => console.log('observer 1: ' + value)); 10 | setTimeout(() => { 11 | sharedTick$.subscribe(value => console.log('observer 2: ' + value)); 12 | }, 2500); 13 | setTimeout(() => { 14 | sharedTick$.subscribe(value => console.log('observer 3: ' + value)); 15 | }, 5000); 16 | 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/publishLast/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/publishLast'; 4 | import 'rxjs/add/operator/take'; 5 | 6 | const tick$ = Observable.interval(1000).take(3); 7 | const sharedTick$ = tick$.publishLast().refCount(); 8 | 9 | sharedTick$.subscribe(value => console.log('observer 1: ' + value)); 10 | setTimeout(() => { 11 | sharedTick$.subscribe(value => console.log('observer 2: ' + value)); 12 | }, 4500); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/publishReplay/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/publishReplay'; 4 | import 'rxjs/add/operator/take'; 5 | import 'rxjs/add/operator/do'; 6 | 7 | const tick$ = Observable.interval(1000).take(3) 8 | .do(x => console.log('source ', x)); 9 | const sharedTick$ = tick$.publishReplay().refCount(); 10 | 11 | sharedTick$.subscribe(value => console.log('observer 1: ' + value)); 12 | setTimeout(() => { 13 | sharedTick$.subscribe(value => console.log('observer 2: ' + value)); 14 | }, 5000); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/publishReplay/withBothArgument.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/publishReplay'; 4 | import 'rxjs/add/operator/take'; 5 | 6 | const tick$ = Observable.interval(1000).take(3); 7 | const sharedTick$ = tick$.publishReplay(2, 1500).refCount(); 8 | 9 | sharedTick$.subscribe(value => console.log('observer 1: ' + value)); 10 | setTimeout(() => { 11 | sharedTick$.subscribe(value => console.log('observer 2: ' + value)); 12 | }, 5000); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/publishReplay/withBufferSize.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/publishReplay'; 4 | import 'rxjs/add/operator/take'; 5 | import 'rxjs/add/operator/do'; 6 | 7 | const tick$ = Observable.interval(1000).take(3) 8 | .do(x => console.log('source ', x)); 9 | const sharedTick$ = tick$.publishReplay(2).refCount(); 10 | 11 | sharedTick$.subscribe(value => console.log('observer 1: ' + value)); 12 | setTimeout(() => { 13 | sharedTick$.subscribe(value => console.log('observer 2: ' + value)); 14 | }, 5000); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/publishReplay/withWindowTime.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/publishReplay'; 4 | import 'rxjs/add/operator/take'; 5 | 6 | const tick$ = Observable.interval(1000).take(3); 7 | const sharedTick$ = tick$.publishReplay(Number.POSITIVE_INFINITY, 3500).refCount(); 8 | 9 | sharedTick$.subscribe(value => console.log('observer 1: ' + value)); 10 | setTimeout(() => { 11 | sharedTick$.subscribe(value => console.log('observer 2: ' + value)); 12 | }, 5000); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/share/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/share'; 4 | import 'rxjs/add/operator/take'; 5 | 6 | const tick$ = Observable.interval(1000).take(3); 7 | const sharedTick$ = tick$.share(); 8 | 9 | sharedTick$.subscribe(value => console.log('observer 1: ' + value)); 10 | setTimeout(() => { 11 | sharedTick$.subscribe(value => console.log('observer 2: ' + value)); 12 | }, 1500); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/share/lateSub.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/share'; 4 | import 'rxjs/add/operator/take'; 5 | 6 | const tick$ = Observable.interval(1000).take(3); 7 | const sharedTick$ = tick$.share(); 8 | 9 | sharedTick$.subscribe(value => console.log('observer 1: ' + value)); 10 | setTimeout(() => { 11 | sharedTick$.subscribe(value => console.log('observer 2: ' + value)); 12 | }, 4500); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/subject/broadcast.js: -------------------------------------------------------------------------------- 1 | import EventEmitter from 'events'; 2 | 3 | const eventHub = new EventEmitter(); 4 | 5 | eventHub.on('data', (info) => console.log(info)); 6 | 7 | eventHub.emit('data', 'some data'); 8 | eventHub.emit('data', 'some other data'); 9 | 10 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/subject/error.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/take'; 5 | import 'rxjs/add/operator/map'; 6 | 7 | const throwOnUnluckyNumber = value => { 8 | if (value === 4) { 9 | throw new Error('unlucky number 4'); 10 | } 11 | 12 | return value; 13 | }; 14 | 15 | const tick$ = Observable.interval(1000).take(10); 16 | const subject = new Subject(); 17 | 18 | tick$.subscribe(subject); 19 | 20 | subject.map(throwOnUnluckyNumber).subscribe( 21 | value => console.log('observer 1: ' + value) 22 | ); 23 | 24 | subject.subscribe( 25 | value => console.log('observer 2: ' + value) 26 | ); 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/subject/makeHot.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/observable/range'; 5 | import 'rxjs/add/operator/take'; 6 | 7 | Observable.prototype.makeHot = function () { 8 | const cold$ = this; 9 | const subject = new Subject(); 10 | cold$.subscribe(subject); 11 | //return subject; 12 | return Observable.create((observer) => subject.subscribe(observer)); 13 | } 14 | 15 | const hotTick$ = Observable.interval(1000).take(3).makeHot(); 16 | 17 | hotTick$.subscribe(value => console.log('observer 1: ' + value)); 18 | setTimeout(() => { 19 | hotTick$.subscribe(value => console.log('observer 2: ' + value)); 20 | }, 1500); 21 | 22 | 23 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/subject/merge_multi_upstream.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/take'; 5 | import 'rxjs/add/operator/mapTo'; 6 | import 'rxjs/add/observable/merge'; 7 | 8 | const tick1$ = Observable.interval(1000).mapTo('a').take(2); 9 | const tick2$ = Observable.interval(1000).mapTo('b').take(2); 10 | 11 | const merged$ = Observable.merge(tick1$, tick2$); 12 | 13 | merged$.subscribe(value => console.log('observer 1: ' + value)); 14 | merged$.subscribe(value => console.log('observer 2: ' + value)); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/subject/multi_upstream.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/take'; 5 | import 'rxjs/add/operator/mapTo'; 6 | 7 | const tick1$ = Observable.interval(1000).mapTo('a').take(2); 8 | const tick2$ = Observable.interval(1000).mapTo('b').take(2); 9 | const subject = new Subject(); 10 | 11 | tick1$.subscribe(subject); 12 | tick2$.subscribe(subject); 13 | 14 | subject.subscribe(value => console.log('observer 1: ' + value)); 15 | subject.subscribe(value => console.log('observer 2: ' + value)); 16 | 17 | 18 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/subject/multicast.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/take'; 5 | 6 | const tick$ = Observable.interval(1000).take(3); 7 | const subject = new Subject(); 8 | tick$.subscribe(subject); 9 | 10 | subject.subscribe(value => console.log('observer 1: ' + value)); 11 | setTimeout(() => { 12 | subject.subscribe(value => console.log('observer 2: ' + value)); 13 | }, 1500); 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/subject/no_subject.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | 5 | const tick$ = Observable.interval(1000).take(3); 6 | 7 | tick$.subscribe(value => console.log('observer 1: ' + value)); 8 | setTimeout(() => { 9 | tick$.subscribe(value => console.log('observer 2: ' + value)); 10 | }, 1500); 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/subject/observer_observable.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/map'; 5 | 6 | const subject = new Subject(); 7 | 8 | subject.map(x => x * 2).subscribe( 9 | value => console.log('on data: ' + value), 10 | err => console.log('on error: ' + err.message), 11 | () => console.log('on complete') 12 | ); 13 | 14 | subject.next(1); 15 | subject.next(2); 16 | subject.next(3); 17 | subject.complete(); 18 | 19 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/subject/un_reusable.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | 4 | const subject = new Subject(); 5 | 6 | subject.subscribe( 7 | value => console.log('on observer 1 data: ' + value), 8 | err => console.log('on observer 1 error: ' + err.message), 9 | () => console.log('on observer 1 complete') 10 | ); 11 | 12 | subject.next(1); 13 | subject.next(2); 14 | subject.complete(); 15 | 16 | subject.subscribe( 17 | value => console.log('on observer 2 data: ' + value), 18 | err => console.log('on observer 2 error: ' + err.message), 19 | () => console.log('on observer 2 complete') 20 | ); 21 | 22 | subject.next(3); 23 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/subject/un_reusable_error.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | 4 | const subject = new Subject(); 5 | 6 | subject.subscribe( 7 | value => console.log('on observer 1 data: ' + value), 8 | err => console.log('on observer 1 error: ' + err.message), 9 | () => console.log('on observer 1 complete') 10 | ); 11 | 12 | subject.next(1); 13 | subject.next(2); 14 | subject.error(new Error('something wrong')); 15 | 16 | subject.subscribe( 17 | value => console.log('on observer 2 data: ' + value), 18 | err => console.log('on observer 2 error: ' + err.message), 19 | () => console.log('on observer 2 complete') 20 | ); 21 | 22 | subject.next(3); 23 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/subject/unicast.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | 5 | const tick$ = Observable.interval(1000).take(5); 6 | 7 | subject.subscribe(value => console.log('observer 1: ' + value)); 8 | setTimeout(() => { 9 | subject.subscribe(value => console.log('observer 2: ' + value)); 10 | }, 2000); 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-10/multicast/src/subject/unsubscribe.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import {Subject} from 'rxjs/Subject'; 3 | import 'rxjs/add/observable/interval'; 4 | import 'rxjs/add/operator/take'; 5 | 6 | const tick$ = Observable.interval(1000); 7 | const subject = new Subject(); 8 | 9 | tick$.subscribe(subject); 10 | 11 | subject.subscribe(value => console.log('observer: ' + value)); 12 | setTimeout(() => { 13 | subject.unsubscribe(); 14 | }, 1500); 15 | 16 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/callstack/Promise_vs_setTimeout.js: -------------------------------------------------------------------------------- 1 | 2 | setTimeout(() => console.log('setTimeout'), 0); 3 | Promise.resolve(1).then(() => console.log('Promise.resolve')); 4 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/callstack/nextTick_vs_setTimeout.js: -------------------------------------------------------------------------------- 1 | 2 | setTimeout(() => console.log('setTimeout'), 0); 3 | process.nextTick(() => console.log('nextTick')); 4 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/callstack/range.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | 3 | Observable.range = function(start, count) { 4 | return Observable.create((observer) => { 5 | let index = start; 6 | let end = start + count; 7 | do { 8 | if (index >= end) { 9 | observer.complete(); 10 | break; 11 | } 12 | observer.next(index++); 13 | } while (true); 14 | }); 15 | }; 16 | 17 | Observable.range(1, 1).subscribe(console.log); 18 | 19 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/customScheduler/range.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import {asap} from 'rxjs/scheduler/asap'; 4 | import {Scheduler} from 'rxjs/Scheduler'; 5 | import {Action} from 'rxjs/scheduler/Action'; 6 | 7 | const timeStart = new Date(); 8 | const source$ = Observable.range(1, 100000, new Scheduler(Action)); 9 | 10 | console.log('before subscribe'); 11 | source$.subscribe({ 12 | complete: () => { 13 | console.log('Time elapsed: ' + (Date.now() - timeStart) + 'ms'); 14 | } 15 | }); 16 | console.log('after subscribe'); 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/eventloop/index.js: -------------------------------------------------------------------------------- 1 | import {asap} from 'rxjs/scheduler/asap'; 2 | import {async} from 'rxjs/scheduler/async'; 3 | import {queue} from 'rxjs/scheduler/queue'; 4 | 5 | console.log('before schedule'); 6 | async.schedule(() => console.log('async')); 7 | asap.schedule(() => console.log('asap')); 8 | queue.schedule(() => console.log('queue')); 9 | console.log('after schedule'); 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/eventloop/interval_asap.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | 4 | console.log('before schedule'); 5 | 6 | const source$ = Observable.interval(1000, asap); 7 | source$.subscribe(console.log); 8 | 9 | console.log('after schedule'); 10 | 11 | 12 | 13 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/eventloop/recursive_queue.js: -------------------------------------------------------------------------------- 1 | import {queue} from 'rxjs/scheduler/queue'; 2 | 3 | queue.schedule(() => { 4 | console.log('enter first action'); 5 | queue.schedule(() => { 6 | console.log('enter second action'); 7 | }); 8 | console.log('leave first action'); 9 | }); 10 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/observeOn/index.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import 'rxjs/add/operator/observeOn'; 4 | import {asap} from 'rxjs/scheduler/asap'; 5 | 6 | const source$ = Observable.range(1, 3); 7 | const asapSource$ = source$.observeOn(asap); 8 | 9 | console.log('before subscribe'); 10 | asapSource$.subscribe( 11 | value => console.log('data: ', value), 12 | error => console.log('error: ', error), 13 | () => console.log('complete') 14 | ); 15 | console.log('after subscribe'); 16 | 17 | 18 | 19 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/observeOn/time.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import 'rxjs/add/operator/observeOn'; 4 | import {asap} from 'rxjs/scheduler/asap'; 5 | 6 | const timeStart = new Date(); 7 | const source$ = Observable.range(1, 100000); 8 | 9 | console.log('before subscribe'); 10 | source$.observeOn(asap).subscribe({ 11 | error: err => { 12 | console.log('Error', err); 13 | }, 14 | complete: () => { 15 | console.log('Time elapsed: ' + (Date.now() - timeStart) + 'ms'); 16 | } 17 | }); 18 | console.log('after subscribe'); 19 | 20 | 21 | 22 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/operators/merge_range.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import 'rxjs/add/observable/merge'; 4 | import {asap} from 'rxjs/scheduler/asap'; 5 | 6 | const source1$ = Observable.range(1, 3); 7 | const source2$ = Observable.range(10, 3); 8 | const source$ = Observable.merge(source1$, source2$, 2, asap); 9 | 10 | console.log('before subscribe'); 11 | source$.subscribe( 12 | value => console.log('data: ', value), 13 | error => console.log('error: ', error), 14 | () => console.log('complete') 15 | ); 16 | console.log('after subscribe'); 17 | 18 | 19 | 20 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/operators/merge_range_2.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import 'rxjs/add/observable/merge'; 4 | import 'rxjs/add/operator/do'; 5 | import {asap} from 'rxjs/scheduler/asap'; 6 | 7 | const source1$ = Observable.range(1, 3) 8 | .do(x => console.log('source 1', x)); 9 | const source2$ = Observable.range(10, 3) 10 | .do(x => console.log('source 2', x)); 11 | const source$ = Observable.merge(source1$, source2$, 2, asap); 12 | 13 | console.log('before subscribe'); 14 | source$.subscribe( 15 | value => console.log('data: ', value), 16 | error => console.log('error: ', error), 17 | () => console.log('complete') 18 | ); 19 | console.log('after subscribe'); 20 | 21 | 22 | 23 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/performance/range.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | 4 | const timeStart = new Date(); 5 | const source$ = Observable.range(1, 100000); 6 | 7 | console.log('before subscribe'); 8 | source$.subscribe({ 9 | complete: () => { 10 | console.log('Time elapsed: ' + (Date.now() - timeStart) + 'ms'); 11 | } 12 | }); 13 | console.log('after subscribe'); 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/performance/range_asap.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import {asap} from 'rxjs/scheduler/asap'; 4 | 5 | const timeStart = new Date(); 6 | const source$ = Observable.range(1, 100000, asap); 7 | 8 | console.log('before subscribe'); 9 | source$.subscribe({ 10 | complete: () => { 11 | console.log('Time elapsed: ' + (Date.now() - timeStart) + 'ms'); 12 | } 13 | }); 14 | console.log('after subscribe'); 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/scheduler/interval_asap.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/interval'; 3 | import 'rxjs/add/operator/take'; 4 | import {asap} from 'rxjs/scheduler/asap'; 5 | 6 | const source$ = Observable.interval(1000, asap).take(3); 7 | 8 | console.log('before subscribe'); 9 | source$.subscribe( 10 | value => console.log('data: ', value), 11 | error => console.log('error: ', error), 12 | () => console.log('complete') 13 | ); 14 | console.log('after subscribe'); 15 | 16 | 17 | 18 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/scheduler/queue_vs_async.js: -------------------------------------------------------------------------------- 1 | import {async} from 'rxjs/scheduler/async'; 2 | import {queue} from 'rxjs/scheduler/queue'; 3 | 4 | async.schedule(() => console.log('async 1')); 5 | queue.schedule(() => console.log('queue 1')); 6 | 7 | async.schedule(() => console.log('async 2'), 1); 8 | queue.schedule(() => console.log('queue 2'), 1); 9 | 10 | const Rx = require('rxjs'); 11 | 12 | /* 13 | Rx.Scheduler.async.schedule(() => console.log('async 3')); 14 | Rx.Scheduler.queue.schedule(() => console.log('queue3')); 15 | 16 | Rx.Scheduler.async.schedule(() => console.log('async 4'), 1); 17 | Rx.Scheduler.queue.schedule(() => console.log('queue 4'), 1); 18 | */ 19 | 20 | 21 | 22 | 23 | 24 | 25 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/scheduler/range.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | 4 | const source$ = Observable.range(1, 3); 5 | 6 | console.log('before subscribe'); 7 | source$.subscribe( 8 | value => console.log('data: ', value), 9 | error => console.log('error: ', error), 10 | () => console.log('complete') 11 | ); 12 | console.log('after subscribe'); 13 | 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/scheduler/range_asap.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import {asap} from 'rxjs/scheduler/asap'; 4 | 5 | const source$ = Observable.range(1, 3, asap); 6 | 7 | console.log('before subscribe'); 8 | source$.subscribe( 9 | value => console.log('data: ', value), 10 | error => console.log('error: ', error), 11 | () => console.log('complete') 12 | ); 13 | console.log('after subscribe'); 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/scheduler/range_async.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import {async} from 'rxjs/scheduler/async'; 4 | 5 | const source$ = Observable.range(1, 3, async); 6 | 7 | console.log('before subscribe'); 8 | source$.subscribe( 9 | value => console.log('data: ', value), 10 | error => console.log('error: ', error), 11 | () => console.log('complete') 12 | ); 13 | console.log('after subscribe'); 14 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/scheduler/range_queue.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import {queue} from 'rxjs/scheduler/queue'; 4 | 5 | const source$ = Observable.range(1, 3, queue); 6 | 7 | console.log('before subscribe'); 8 | source$.subscribe( 9 | value => console.log('data: ', value), 10 | error => console.log('error: ', error), 11 | () => console.log('complete') 12 | ); 13 | console.log('after subscribe'); 14 | -------------------------------------------------------------------------------- /chapter-11/scheduler/src/subscribeOn/no_subscribeOn.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import 'rxjs/add/operator/subscribeOn'; 4 | 5 | const source$ = Observable.create(observer => { 6 | console.log('on subscribe'); 7 | observer.next(1); 8 | observer.next(2); 9 | observer.next(3); 10 | 11 | return () => { 12 | console.log('on unsubscribe'); 13 | } 14 | }); 15 | 16 | console.log('before subscribe'); 17 | source$.subscribe( 18 | value => console.log('data: ', value), 19 | error => console.log('error: ', error), 20 | () => console.log('complete') 21 | ); 22 | console.log('after subscribe'); 23 | 24 | 25 | 26 | -------------------------------------------------------------------------------- /chapter-12/counter/counter.js: -------------------------------------------------------------------------------- 1 | const plus$ = Rx.Observable.fromEvent(document.querySelector('#plus'), 'click'); 2 | const minus$ = Rx.Observable.fromEvent(document.querySelector('#minus'), 'click'); 3 | 4 | Rx.Observable.merge(plus$.mapTo(1), minus$.mapTo(-1)) 5 | .scan((count, delta) => count + delta, 0) 6 | .subscribe( 7 | currentCount => { 8 | document.querySelector('#count').innerHTML = currentCount; 9 | } 10 | ); 11 | -------------------------------------------------------------------------------- /chapter-12/counter/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |
5 |

6 | Count: 0 7 |

8 | 9 | 10 |
11 | 12 | 13 | 14 | 15 | 16 | -------------------------------------------------------------------------------- /chapter-12/debugging/.babelrc: -------------------------------------------------------------------------------- 1 | { 2 | "presets": [ 3 | "es2015", 4 | "stage-0" 5 | ], 6 | "plugins": [ 7 | "transform-runtime" 8 | ] 9 | } 10 | -------------------------------------------------------------------------------- /chapter-12/debugging/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "chapter-02", 3 | "version": "1.0.0", 4 | "description": "", 5 | "main": "run.js", 6 | "dependencies": { 7 | "babel-plugin-transform-runtime": "^6.23.0", 8 | "node-fetch": "^2.0.0-alpha.3", 9 | "rxjs": "~5.5.2", 10 | "symbol-observable": "^1.0.4" 11 | }, 12 | "devDependencies": { 13 | "babel-cli": "^6.24.1", 14 | "babel-preset-es2015": "^6.24.1", 15 | "babel-preset-stage-0": "^6.24.1" 16 | }, 17 | "scripts": { 18 | "build": "babel src/ -d build/" 19 | }, 20 | "author": "", 21 | "license": "ISC" 22 | } 23 | -------------------------------------------------------------------------------- /chapter-12/debugging/src/debug.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import 'rxjs/add/operator/filter'; 4 | import 'rxjs/add/operator/map'; 5 | import 'rxjs/add/operator/do'; 6 | 7 | global.debug = true; 8 | 9 | Observable.prototype.debug = function(fn) { 10 | if (global.debug) { 11 | return this.do(fn); 12 | } else { 13 | return this; 14 | } 15 | }; 16 | 17 | const source$ = Observable.range(1, 10) 18 | .filter(x => x % 2 === 0) 19 | .debug(x => console.log('source$ after filter data = ', x)) 20 | .map(x => x*x); 21 | 22 | const observer = { 23 | next: value => console.log('on data ', value) 24 | }; 25 | 26 | source$.subscribe(observer); 27 | -------------------------------------------------------------------------------- /chapter-12/debugging/src/do_in_pipe.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import 'rxjs/add/operator/filter'; 4 | import 'rxjs/add/operator/map'; 5 | import 'rxjs/add/operator/do'; 6 | 7 | const source$ = Observable.range(1, 10) 8 | .filter(x => x % 2 === 0) 9 | .do(x => console.log('source$ after filter data = ', x)) 10 | .map(x => x*x); 11 | 12 | const observer = { 13 | next: value => console.log('on data ', value) 14 | }; 15 | 16 | source$.do( 17 | value => console.log('source$ data = ', value) 18 | ).subscribe(observer); 19 | -------------------------------------------------------------------------------- /chapter-12/debugging/src/use_do.js: -------------------------------------------------------------------------------- 1 | import {Observable} from 'rxjs/Observable'; 2 | import 'rxjs/add/observable/range'; 3 | import 'rxjs/add/operator/do'; 4 | 5 | const source$ = Observable.range(1, 10); 6 | 7 | const observer = { 8 | next: value => console.log('on data ', value) 9 | }; 10 | 11 | source$.do( 12 | value => console.log('source$ data = ', value) 13 | ).subscribe(observer); 14 | -------------------------------------------------------------------------------- /chapter-12/search/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |
5 | 6 | 7 | 9 |
10 | 11 | 12 | 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-12/unit_testing/.babelrc: -------------------------------------------------------------------------------- 1 | { 2 | "presets": [ 3 | "es2015", 4 | "stage-0" 5 | ] 6 | } 7 | -------------------------------------------------------------------------------- /chapter-12/unit_testing/.gitignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | 3 | *.log 4 | -------------------------------------------------------------------------------- /chapter-12/unit_testing/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "rxjs_unit_testing", 3 | "version": "1.0.0", 4 | "description": "RxJS Unit Testing", 5 | "main": "index.js", 6 | "scripts": { 7 | "test": "mocha --compilers js:babel-core/register" 8 | }, 9 | "keywords": [ 10 | "rxjs", 11 | "unit", 12 | "testing" 13 | ], 14 | "author": "Morgan Cheng", 15 | "license": "MIT", 16 | "dependencies": { 17 | "isomorphic-fetch": "^2.2.1", 18 | "lodash": "^4.17.4", 19 | "rxjs": "^5.5.2" 20 | }, 21 | "devDependencies": { 22 | "babel-core": "^6.26.0", 23 | "babel-preset-es2015": "^6.24.1", 24 | "babel-preset-stage-0": "^6.24.1", 25 | "chai": "^4.1.0", 26 | "mocha": "^3.4.2" 27 | } 28 | } 29 | -------------------------------------------------------------------------------- /chapter-12/unit_testing/src/counter.js: -------------------------------------------------------------------------------- 1 | import Rx from 'rxjs'; 2 | 3 | export const counterPipe = (plus$, minus$) => { 4 | return Rx.Observable.merge(plus$.mapTo(1), minus$.mapTo(-1)) 5 | .scan((count, delta) => count + delta, 0) 6 | }; 7 | -------------------------------------------------------------------------------- /chapter-12/unit_testing/src/sum.js: -------------------------------------------------------------------------------- 1 | import {reduce} from 'rxjs/operators/reduce'; 2 | import {map} from 'rxjs/operators/map'; 3 | 4 | const sum = (source$) => { 5 | return source$.pipe( 6 | map(x => parseInt(x, 10)), 7 | reduce((a, b) => a + b, 0) 8 | ); 9 | }; 10 | 11 | export {sum}; 12 | -------------------------------------------------------------------------------- /chapter-12/unit_testing/src/sum.simple.js: -------------------------------------------------------------------------------- 1 | import 'rxjs/add/operator/reduce'; 2 | 3 | const sum = (source$) => { 4 | return source$.reduce((a, b) => a + b, 0); 5 | }; 6 | 7 | export {sum}; 8 | -------------------------------------------------------------------------------- /chapter-12/unit_testing/test/counter.test.js: -------------------------------------------------------------------------------- 1 | require('./helpers/test-helper'); 2 | 3 | import {counterPipe} from '../src/counter'; 4 | 5 | describe('Counter', () => { 6 | test('should add & subtract count on source', () => { 7 | const plus = '^-a------|'; 8 | const minus = '^---c--d--|'; 9 | const expected = '--x-y--z--|'; 10 | 11 | const result$ = counterPipe(hot(plus), hot(minus)); 12 | 13 | expectObservable(result$).toBe(expected, { 14 | x: 1, 15 | y: 0, 16 | z: -1, 17 | }); 18 | }); 19 | }); 20 | -------------------------------------------------------------------------------- /chapter-12/unit_testing/test/sample.test.js: -------------------------------------------------------------------------------- 1 | describe('sample suite', () => { 2 | it('should work', () => { 3 | }); 4 | 5 | it('should work as well', () => { 6 | }); 7 | 8 | context('another suite', () => { 9 | it('should do something', () => { 10 | }); 11 | }); 12 | }); 13 | 14 | 15 | -------------------------------------------------------------------------------- /chapter-12/unit_testing/test/sum.test.js: -------------------------------------------------------------------------------- 1 | const Rx = require('rxjs'); 2 | const chai = require('chai'); 3 | const assert = chai.assert; 4 | 5 | import {sum} from '../src/sum.js'; 6 | 7 | describe('operator sum', () => { 8 | it('should sum up range of value', () => { 9 | const source$ = Rx.Observable.range(1, 5); 10 | 11 | const result$ = source$.pipe(sum); 12 | 13 | result$.subscribe( 14 | value => assert.equal(15, value) 15 | ); 16 | }); 17 | 18 | it('should sum up string value', () => { 19 | const source$ = Rx.Observable.of('1', '2', '3'); 20 | 21 | const result$ = source$.pipe(sum); 22 | 23 | result$.subscribe( 24 | value => assert.equal(6, value) 25 | ); 26 | }); 27 | 28 | }); 29 | 30 | 31 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/react-container/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/ignore-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | 6 | # testing 7 | /coverage 8 | 9 | # production 10 | /build 11 | 12 | # misc 13 | .DS_Store 14 | .env.local 15 | .env.development.local 16 | .env.test.local 17 | .env.production.local 18 | 19 | npm-debug.log* 20 | yarn-debug.log* 21 | yarn-error.log* 22 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/react-container/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "react-rxjs", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "react": "^16.1.1", 7 | "react-dom": "^16.1.1", 8 | "react-scripts": "1.0.17" 9 | }, 10 | "scripts": { 11 | "start": "react-scripts start", 12 | "build": "react-scripts build", 13 | "test": "react-scripts test --env=jsdom", 14 | "eject": "react-scripts eject" 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/react-container/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mocheng/dissecting-rxjs/b0e875355517bd57367f379712abb8f5f0931809/chapter-13/react-rxjs/react-container/public/favicon.ico -------------------------------------------------------------------------------- /chapter-13/react-rxjs/react-container/public/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "short_name": "React App", 3 | "name": "Create React App Sample", 4 | "icons": [ 5 | { 6 | "src": "favicon.ico", 7 | "sizes": "64x64 32x32 24x24 16x16", 8 | "type": "image/x-icon" 9 | } 10 | ], 11 | "start_url": "./index.html", 12 | "display": "standalone", 13 | "theme_color": "#000000", 14 | "background_color": "#ffffff" 15 | } 16 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/react-container/src/App.css: -------------------------------------------------------------------------------- 1 | .App { 2 | margin: 0 auto; 3 | max-width: 600px; 4 | } 5 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/react-container/src/App.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import Counter from './Counter'; 3 | 4 | import './App.css'; 5 | 6 | class App extends Component { 7 | render() { 8 | return ( 9 |
10 | 11 |
12 | ); 13 | } 14 | } 15 | 16 | export default App; 17 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/react-container/src/index.css: -------------------------------------------------------------------------------- 1 | body { 2 | margin: 0px; 3 | padding: 0px; 4 | font-family: sans-serif; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/react-container/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import './index.css'; 4 | import App from './App'; 5 | 6 | ReactDOM.render(, document.getElementById('root')); 7 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-async/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "react-rxjs", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "react": "^16.1.1", 7 | "react-dom": "^16.1.1", 8 | "react-scripts": "1.0.17", 9 | "rxjs": "^5.5.2" 10 | }, 11 | "scripts": { 12 | "start": "react-scripts start", 13 | "build": "react-scripts build", 14 | "test": "react-scripts test --env=jsdom", 15 | "eject": "react-scripts eject" 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-async/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mocheng/dissecting-rxjs/b0e875355517bd57367f379712abb8f5f0931809/chapter-13/react-rxjs/rxjs-async/public/favicon.ico -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-async/public/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "short_name": "React App", 3 | "name": "Create React App Sample", 4 | "icons": [ 5 | { 6 | "src": "favicon.ico", 7 | "sizes": "64x64 32x32 24x24 16x16", 8 | "type": "image/x-icon" 9 | } 10 | ], 11 | "start_url": "./index.html", 12 | "display": "standalone", 13 | "theme_color": "#000000", 14 | "background_color": "#ffffff" 15 | } 16 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-async/src/App.css: -------------------------------------------------------------------------------- 1 | .App { 2 | margin: 0 auto; 3 | max-width: 600px; 4 | } 5 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-async/src/App.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import Counter from './Counter'; 3 | 4 | import './App.css'; 5 | 6 | class App extends Component { 7 | render() { 8 | return ( 9 |
10 | 11 |
12 | ); 13 | } 14 | } 15 | 16 | export default App; 17 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-async/src/index.css: -------------------------------------------------------------------------------- 1 | body { 2 | margin: 0px; 3 | padding: 0px; 4 | font-family: sans-serif; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-async/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import './index.css'; 4 | import App from './App'; 5 | 6 | ReactDOM.render(, document.getElementById('root')); 7 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-container/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/ignore-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | 6 | # testing 7 | /coverage 8 | 9 | # production 10 | /build 11 | 12 | # misc 13 | .DS_Store 14 | .env.local 15 | .env.development.local 16 | .env.test.local 17 | .env.production.local 18 | 19 | npm-debug.log* 20 | yarn-debug.log* 21 | yarn-error.log* 22 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-container/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "react-rxjs", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "react": "^16.1.1", 7 | "react-dom": "^16.1.1", 8 | "react-scripts": "1.0.17" 9 | }, 10 | "scripts": { 11 | "start": "react-scripts start", 12 | "build": "react-scripts build", 13 | "test": "react-scripts test --env=jsdom", 14 | "eject": "react-scripts eject" 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-container/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mocheng/dissecting-rxjs/b0e875355517bd57367f379712abb8f5f0931809/chapter-13/react-rxjs/rxjs-container/public/favicon.ico -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-container/public/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "short_name": "React App", 3 | "name": "Create React App Sample", 4 | "icons": [ 5 | { 6 | "src": "favicon.ico", 7 | "sizes": "64x64 32x32 24x24 16x16", 8 | "type": "image/x-icon" 9 | } 10 | ], 11 | "start_url": "./index.html", 12 | "display": "standalone", 13 | "theme_color": "#000000", 14 | "background_color": "#ffffff" 15 | } 16 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-container/src/App.css: -------------------------------------------------------------------------------- 1 | .App { 2 | margin: 0 auto; 3 | max-width: 600px; 4 | } 5 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-container/src/App.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import Counter from './Counter'; 3 | 4 | import './App.css'; 5 | 6 | class App extends Component { 7 | render() { 8 | return ( 9 |
10 | 11 |
12 | ); 13 | } 14 | } 15 | 16 | export default App; 17 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-container/src/index.css: -------------------------------------------------------------------------------- 1 | body { 2 | margin: 0px; 3 | padding: 0px; 4 | font-family: sans-serif; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-container/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import './index.css'; 4 | import App from './App'; 5 | 6 | ReactDOM.render(, document.getElementById('root')); 7 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-hoc/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/ignore-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | 6 | # testing 7 | /coverage 8 | 9 | # production 10 | /build 11 | 12 | # misc 13 | .DS_Store 14 | .env.local 15 | .env.development.local 16 | .env.test.local 17 | .env.production.local 18 | 19 | npm-debug.log* 20 | yarn-debug.log* 21 | yarn-error.log* 22 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-hoc/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "react-rxjs", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "lodash": "^4.17.4", 7 | "react": "^16.1.1", 8 | "react-dom": "^16.1.1", 9 | "react-scripts": "1.0.17" 10 | }, 11 | "scripts": { 12 | "start": "react-scripts start", 13 | "build": "react-scripts build", 14 | "test": "react-scripts test --env=jsdom", 15 | "eject": "react-scripts eject" 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-hoc/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mocheng/dissecting-rxjs/b0e875355517bd57367f379712abb8f5f0931809/chapter-13/react-rxjs/rxjs-hoc/public/favicon.ico -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-hoc/public/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "short_name": "React App", 3 | "name": "Create React App Sample", 4 | "icons": [ 5 | { 6 | "src": "favicon.ico", 7 | "sizes": "64x64 32x32 24x24 16x16", 8 | "type": "image/x-icon" 9 | } 10 | ], 11 | "start_url": "./index.html", 12 | "display": "standalone", 13 | "theme_color": "#000000", 14 | "background_color": "#ffffff" 15 | } 16 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-hoc/src/App.css: -------------------------------------------------------------------------------- 1 | .App { 2 | margin: 0 auto; 3 | max-width: 600px; 4 | } 5 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-hoc/src/App.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import Counter from './Counter'; 3 | import StopWatch from './StopWatch'; 4 | 5 | import './App.css'; 6 | 7 | class App extends Component { 8 | render() { 9 | return ( 10 |
11 | 12 | 13 |
14 | ); 15 | } 16 | } 17 | 18 | export default App; 19 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-hoc/src/index.css: -------------------------------------------------------------------------------- 1 | body { 2 | margin: 0px; 3 | padding: 0px; 4 | font-family: sans-serif; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-hoc/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import './index.css'; 4 | import App from './App'; 5 | 6 | ReactDOM.render(, document.getElementById('root')); 7 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-hoc/src/observe.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | 3 | const observe = (WrappedComponent, observableFactory, defaultState) => { 4 | return class extends React.Component { 5 | constructor() { 6 | super(...arguments); 7 | this.state = defaultState; 8 | this.props$ = observableFactory(this.props, this.state); 9 | } 10 | 11 | render() { 12 | return 13 | } 14 | 15 | componentWillUnmount() { 16 | this.subscription.unsubscribe(); 17 | } 18 | 19 | componentDidMount() { 20 | this.subscription = this.props$.subscribe(value => this.setState(value)); 21 | } 22 | }; 23 | }; 24 | 25 | export default observe; 26 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-subject/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "react-rxjs", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "react": "^16.1.1", 7 | "react-dom": "^16.1.1", 8 | "react-scripts": "1.0.17", 9 | "rxjs": "^5.5.2" 10 | }, 11 | "scripts": { 12 | "start": "react-scripts start", 13 | "build": "react-scripts build", 14 | "test": "react-scripts test --env=jsdom", 15 | "eject": "react-scripts eject" 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-subject/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mocheng/dissecting-rxjs/b0e875355517bd57367f379712abb8f5f0931809/chapter-13/react-rxjs/rxjs-subject/public/favicon.ico -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-subject/public/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "short_name": "React App", 3 | "name": "Create React App Sample", 4 | "icons": [ 5 | { 6 | "src": "favicon.ico", 7 | "sizes": "64x64 32x32 24x24 16x16", 8 | "type": "image/x-icon" 9 | } 10 | ], 11 | "start_url": "./index.html", 12 | "display": "standalone", 13 | "theme_color": "#000000", 14 | "background_color": "#ffffff" 15 | } 16 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-subject/src/App.css: -------------------------------------------------------------------------------- 1 | .App { 2 | margin: 0 auto; 3 | max-width: 600px; 4 | } 5 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-subject/src/App.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import Counter from './Counter'; 3 | 4 | import './App.css'; 5 | 6 | class App extends Component { 7 | render() { 8 | return ( 9 |
10 | 11 |
12 | ); 13 | } 14 | } 15 | 16 | export default App; 17 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-subject/src/index.css: -------------------------------------------------------------------------------- 1 | body { 2 | margin: 0px; 3 | padding: 0px; 4 | font-family: sans-serif; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/rxjs-subject/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import './index.css'; 4 | import App from './App'; 5 | 6 | ReactDOM.render(, document.getElementById('root')); 7 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/simple/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/ignore-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | 6 | # testing 7 | /coverage 8 | 9 | # production 10 | /build 11 | 12 | # misc 13 | .DS_Store 14 | .env.local 15 | .env.development.local 16 | .env.test.local 17 | .env.production.local 18 | 19 | npm-debug.log* 20 | yarn-debug.log* 21 | yarn-error.log* 22 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/simple/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "react-rxjs", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "react": "^16.1.1", 7 | "react-dom": "^16.1.1", 8 | "react-scripts": "1.0.17" 9 | }, 10 | "scripts": { 11 | "start": "react-scripts start", 12 | "build": "react-scripts build", 13 | "test": "react-scripts test --env=jsdom", 14 | "eject": "react-scripts eject" 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/simple/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mocheng/dissecting-rxjs/b0e875355517bd57367f379712abb8f5f0931809/chapter-13/react-rxjs/simple/public/favicon.ico -------------------------------------------------------------------------------- /chapter-13/react-rxjs/simple/public/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "short_name": "React App", 3 | "name": "Create React App Sample", 4 | "icons": [ 5 | { 6 | "src": "favicon.ico", 7 | "sizes": "64x64 32x32 24x24 16x16", 8 | "type": "image/x-icon" 9 | } 10 | ], 11 | "start_url": "./index.html", 12 | "display": "standalone", 13 | "theme_color": "#000000", 14 | "background_color": "#ffffff" 15 | } 16 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/simple/src/App.css: -------------------------------------------------------------------------------- 1 | .App { 2 | margin: 0 auto; 3 | max-width: 600px; 4 | } 5 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/simple/src/App.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import Counter from './Counter'; 3 | //import CountButton from './CountButton'; 4 | 5 | import './App.css'; 6 | 7 | class App extends Component { 8 | render() { 9 | return ( 10 |
11 | 12 | {/* 13 |
14 |
15 | 16 | */} 17 |
18 | ); 19 | } 20 | } 21 | 22 | export default App; 23 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/simple/src/CountButton.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | 3 | class CountButton extends React.Component { 4 | state = {count: 0} 5 | 6 | onClick() { 7 | this.setState({count: this.state.count + 1}); 8 | } 9 | 10 | render() { 11 | return ( 12 | 15 | ); 16 | } 17 | } 18 | 19 | export default CountButton; 20 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/simple/src/Counter.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | 3 | export default class Counter extends React.Component { 4 | state = {count: 0} 5 | 6 | onIncrement() { 7 | this.setState({count: this.state.count + 1}); 8 | } 9 | 10 | onDecrement() { 11 | this.setState({count: this.state.count - 1}); 12 | } 13 | 14 | render() { 15 | return ( 16 |
17 |

Count: {this.state.count}

18 | 19 | 20 |
21 | ); 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/simple/src/index.css: -------------------------------------------------------------------------------- 1 | body { 2 | margin: 0px; 3 | padding: 0px; 4 | font-family: sans-serif; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /chapter-13/react-rxjs/simple/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import './index.css'; 4 | import App from './App'; 5 | 6 | ReactDOM.render(, document.getElementById('root')); 7 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/observable/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/ignore-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | 6 | # testing 7 | /coverage 8 | 9 | # production 10 | /build 11 | 12 | # misc 13 | .DS_Store 14 | .env.local 15 | .env.development.local 16 | .env.test.local 17 | .env.production.local 18 | 19 | npm-debug.log* 20 | yarn-debug.log* 21 | yarn-error.log* 22 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/observable/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "react-rxjs", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "react": "^16.1.1", 7 | "react-dom": "^16.1.1", 8 | "react-redux": "^5.0.6", 9 | "react-scripts": "1.0.17", 10 | "redux": "^3.7.2", 11 | "redux-observable": "^0.17.0", 12 | "rxjs": "^5.5.2" 13 | }, 14 | "scripts": { 15 | "start": "react-scripts start", 16 | "build": "react-scripts build", 17 | "test": "react-scripts test --env=jsdom", 18 | "eject": "react-scripts eject" 19 | } 20 | } 21 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/observable/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mocheng/dissecting-rxjs/b0e875355517bd57367f379712abb8f5f0931809/chapter-14/redux-rxjs/observable/public/favicon.ico -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/observable/public/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "short_name": "React App", 3 | "name": "Create React App Sample", 4 | "icons": [ 5 | { 6 | "src": "favicon.ico", 7 | "sizes": "64x64 32x32 24x24 16x16", 8 | "type": "image/x-icon" 9 | } 10 | ], 11 | "start_url": "./index.html", 12 | "display": "standalone", 13 | "theme_color": "#000000", 14 | "background_color": "#ffffff" 15 | } 16 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/observable/src/ActionTypes.js: -------------------------------------------------------------------------------- 1 | export const INCREMENT = 'increment'; 2 | 3 | export const DECREMENT = 'decrement'; 4 | 5 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/observable/src/Actions.js: -------------------------------------------------------------------------------- 1 | import * as ActionTypes from './ActionTypes.js'; 2 | 3 | export const increment = () => ({ 4 | type: ActionTypes.INCREMENT 5 | }); 6 | 7 | export const decrement = () => ({ 8 | type: ActionTypes.DECREMENT 9 | }); 10 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/observable/src/App.css: -------------------------------------------------------------------------------- 1 | .App { 2 | margin: 0 auto; 3 | max-width: 600px; 4 | } 5 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/observable/src/App.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import Counter from './Counter'; 3 | 4 | import './App.css'; 5 | 6 | class App extends Component { 7 | render() { 8 | return ( 9 |
10 | 11 |
12 | ); 13 | } 14 | } 15 | 16 | export default App; 17 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/observable/src/Reducer.js: -------------------------------------------------------------------------------- 1 | import * as ActionTypes from './ActionTypes.js'; 2 | 3 | const reducer = (state, action) => { 4 | switch (action.type) { 5 | case ActionTypes.INCREMENT: 6 | return {...state, count: state.count + 1}; 7 | case ActionTypes.DECREMENT: 8 | return {...state, count: state.count - 1}; 9 | default: 10 | return state 11 | } 12 | }; 13 | 14 | export default reducer; 15 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/observable/src/Store.js: -------------------------------------------------------------------------------- 1 | import {createStore, applyMiddleware} from 'redux'; 2 | import {createEpicMiddleware} from 'redux-observable'; 3 | import reducer from './Reducer'; 4 | import epic from './Epic'; 5 | 6 | const epicMiddleware = createEpicMiddleware(epic); 7 | 8 | const initValues = { 9 | count: 0 10 | }; 11 | const store = createStore( 12 | reducer, 13 | initValues, 14 | applyMiddleware(epicMiddleware) 15 | ); 16 | 17 | export default store; 18 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/observable/src/index.css: -------------------------------------------------------------------------------- 1 | body { 2 | margin: 0px; 3 | padding: 0px; 4 | font-family: sans-serif; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/observable/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import './index.css'; 4 | import App from './App'; 5 | import {Provider} from 'react-redux'; 6 | import store from './Store.js'; 7 | 8 | ReactDOM.render( 9 | 10 | 11 | , 12 | document.getElementById('root') 13 | ); 14 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/reactive-store/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/ignore-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | 6 | # testing 7 | /coverage 8 | 9 | # production 10 | /build 11 | 12 | # misc 13 | .DS_Store 14 | .env.local 15 | .env.development.local 16 | .env.test.local 17 | .env.production.local 18 | 19 | npm-debug.log* 20 | yarn-debug.log* 21 | yarn-error.log* 22 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/reactive-store/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "react-rxjs", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "react": "^16.1.1", 7 | "react-dom": "^16.1.1", 8 | "react-redux": "^5.0.6", 9 | "react-scripts": "1.0.17", 10 | "redux": "^3.7.2", 11 | "rxjs": "^5.5.2" 12 | }, 13 | "scripts": { 14 | "start": "react-scripts start", 15 | "build": "react-scripts build", 16 | "test": "react-scripts test --env=jsdom", 17 | "eject": "react-scripts eject" 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/reactive-store/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mocheng/dissecting-rxjs/b0e875355517bd57367f379712abb8f5f0931809/chapter-14/redux-rxjs/reactive-store/public/favicon.ico -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/reactive-store/public/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "short_name": "React App", 3 | "name": "Create React App Sample", 4 | "icons": [ 5 | { 6 | "src": "favicon.ico", 7 | "sizes": "64x64 32x32 24x24 16x16", 8 | "type": "image/x-icon" 9 | } 10 | ], 11 | "start_url": "./index.html", 12 | "display": "standalone", 13 | "theme_color": "#000000", 14 | "background_color": "#ffffff" 15 | } 16 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/reactive-store/src/ActionTypes.js: -------------------------------------------------------------------------------- 1 | export const INCREMENT = 'increment'; 2 | 3 | export const DECREMENT = 'decrement'; 4 | 5 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/reactive-store/src/Actions.js: -------------------------------------------------------------------------------- 1 | import * as ActionTypes from './ActionTypes.js'; 2 | 3 | export const increment = () => ({ 4 | type: ActionTypes.INCREMENT 5 | }); 6 | 7 | export const decrement = () => ({ 8 | type: ActionTypes.DECREMENT 9 | }); 10 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/reactive-store/src/App.css: -------------------------------------------------------------------------------- 1 | .App { 2 | margin: 0 auto; 3 | max-width: 600px; 4 | } 5 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/reactive-store/src/App.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import Counter from './Counter'; 3 | 4 | import './App.css'; 5 | 6 | class App extends Component { 7 | render() { 8 | return ( 9 |
10 | 11 |
12 | ); 13 | } 14 | } 15 | 16 | export default App; 17 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/reactive-store/src/Reducer.js: -------------------------------------------------------------------------------- 1 | import * as ActionTypes from './ActionTypes.js'; 2 | 3 | const reducer = (state, action) => { 4 | switch (action.type) { 5 | case ActionTypes.INCREMENT: 6 | return {...state, count: state.count + 1}; 7 | case ActionTypes.DECREMENT: 8 | return {...state, count: state.count - 1}; 9 | default: 10 | return state 11 | } 12 | }; 13 | 14 | export default reducer; 15 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/reactive-store/src/Store.js: -------------------------------------------------------------------------------- 1 | import createReactiveStore from './createReactiveStore'; 2 | import reducer from './Reducer.js'; 3 | 4 | const initValues = { 5 | count: 0 6 | }; 7 | 8 | const store = createReactiveStore(reducer, initValues); 9 | 10 | export default store; 11 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/reactive-store/src/createReactiveStore.js: -------------------------------------------------------------------------------- 1 | import {Subject} from 'rxjs/Subject'; 2 | import 'rxjs/add/operator/scan'; 3 | import 'rxjs/add/operator/startWith'; 4 | import 'rxjs/add/operator/do'; 5 | 6 | const createReactiveStore = (reducer, initialState) => { 7 | const action$ = new Subject(); 8 | let currentState = initialState; 9 | 10 | const store$ = action$.startWith(initialState).scan(reducer).do(state => { 11 | currentState = state 12 | }); 13 | 14 | return { 15 | dispatch: (action) => { 16 | return action$.next(action) 17 | }, 18 | getState: () => currentState, 19 | subscribe: (func) => { 20 | store$.subscribe(func); 21 | } 22 | } 23 | } 24 | 25 | export default createReactiveStore; 26 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/reactive-store/src/index.css: -------------------------------------------------------------------------------- 1 | body { 2 | margin: 0px; 3 | padding: 0px; 4 | font-family: sans-serif; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/reactive-store/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import './index.css'; 4 | import App from './App'; 5 | import {Provider} from 'react-redux'; 6 | import store from './Store.js'; 7 | 8 | ReactDOM.render( 9 | 10 | 11 | , 12 | document.getElementById('root') 13 | ); 14 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/simple/.gitignore: -------------------------------------------------------------------------------- 1 | # See https://help.github.com/ignore-files/ for more about ignoring files. 2 | 3 | # dependencies 4 | /node_modules 5 | 6 | # testing 7 | /coverage 8 | 9 | # production 10 | /build 11 | 12 | # misc 13 | .DS_Store 14 | .env.local 15 | .env.development.local 16 | .env.test.local 17 | .env.production.local 18 | 19 | npm-debug.log* 20 | yarn-debug.log* 21 | yarn-error.log* 22 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/simple/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "react-rxjs", 3 | "version": "0.1.0", 4 | "private": true, 5 | "dependencies": { 6 | "react": "^16.1.1", 7 | "react-dom": "^16.1.1", 8 | "react-redux": "^5.0.6", 9 | "react-scripts": "1.0.17", 10 | "redux": "^3.7.2", 11 | "rxjs": "^5.5.2" 12 | }, 13 | "scripts": { 14 | "start": "react-scripts start", 15 | "build": "react-scripts build", 16 | "test": "react-scripts test --env=jsdom", 17 | "eject": "react-scripts eject" 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/simple/public/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mocheng/dissecting-rxjs/b0e875355517bd57367f379712abb8f5f0931809/chapter-14/redux-rxjs/simple/public/favicon.ico -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/simple/public/manifest.json: -------------------------------------------------------------------------------- 1 | { 2 | "short_name": "React App", 3 | "name": "Create React App Sample", 4 | "icons": [ 5 | { 6 | "src": "favicon.ico", 7 | "sizes": "64x64 32x32 24x24 16x16", 8 | "type": "image/x-icon" 9 | } 10 | ], 11 | "start_url": "./index.html", 12 | "display": "standalone", 13 | "theme_color": "#000000", 14 | "background_color": "#ffffff" 15 | } 16 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/simple/src/ActionTypes.js: -------------------------------------------------------------------------------- 1 | export const INCREMENT = 'increment'; 2 | 3 | export const DECREMENT = 'decrement'; 4 | 5 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/simple/src/Actions.js: -------------------------------------------------------------------------------- 1 | import * as ActionTypes from './ActionTypes.js'; 2 | 3 | export const increment = () => ({ 4 | type: ActionTypes.INCREMENT 5 | }); 6 | 7 | export const decrement = () => ({ 8 | type: ActionTypes.DECREMENT 9 | }); 10 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/simple/src/App.css: -------------------------------------------------------------------------------- 1 | .App { 2 | margin: 0 auto; 3 | max-width: 600px; 4 | } 5 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/simple/src/App.js: -------------------------------------------------------------------------------- 1 | import React, { Component } from 'react'; 2 | import Counter from './Counter'; 3 | 4 | import './App.css'; 5 | 6 | class App extends Component { 7 | render() { 8 | return ( 9 |
10 | 11 |
12 | ); 13 | } 14 | } 15 | 16 | export default App; 17 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/simple/src/Reducer.js: -------------------------------------------------------------------------------- 1 | import * as ActionTypes from './ActionTypes.js'; 2 | 3 | const reducer = (state, action) => { 4 | switch (action.type) { 5 | case ActionTypes.INCREMENT: 6 | return {...state, count: state.count + 1}; 7 | case ActionTypes.DECREMENT: 8 | return {...state, count: state.count - 1}; 9 | default: 10 | return state 11 | } 12 | }; 13 | 14 | export default reducer; 15 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/simple/src/Store.js: -------------------------------------------------------------------------------- 1 | import {createStore} from 'redux'; 2 | import reducer from './Reducer.js'; 3 | 4 | const initValues = { 5 | count: 0 6 | }; 7 | const store = createStore(reducer, initValues); 8 | 9 | export default store; 10 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/simple/src/index.css: -------------------------------------------------------------------------------- 1 | body { 2 | margin: 0px; 3 | padding: 0px; 4 | font-family: sans-serif; 5 | } 6 | 7 | -------------------------------------------------------------------------------- /chapter-14/redux-rxjs/simple/src/index.js: -------------------------------------------------------------------------------- 1 | import React from 'react'; 2 | import ReactDOM from 'react-dom'; 3 | import './index.css'; 4 | import App from './App'; 5 | import {Provider} from 'react-redux'; 6 | import store from './Store.js'; 7 | 8 | ReactDOM.render( 9 | 10 | 11 | , 12 | document.getElementById('root') 13 | ); 14 | -------------------------------------------------------------------------------- /chapter-15/breakout/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | -------------------------------------------------------------------------------- /chapter-15/breakout/style.css: -------------------------------------------------------------------------------- 1 | #stage { 2 | background: salmon; 3 | } 4 | 5 | html, 6 | body { 7 | height: 100%; 8 | } 9 | 10 | body { 11 | display: flex; 12 | align-items: center; 13 | justify-content: center; 14 | } 15 | -------------------------------------------------------------------------------- /dissect_rxjs.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mocheng/dissecting-rxjs/b0e875355517bd57367f379712abb8f5f0931809/dissect_rxjs.jpg -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "chapter-02", 3 | "version": "1.0.0", 4 | "description": "", 5 | "main": "run.js", 6 | "dependencies": { 7 | "babel-plugin-transform-runtime": "^6.23.0", 8 | "node-fetch": "^2.0.0-alpha.3", 9 | "rxjs": "~5.5.2", 10 | "symbol-observable": "^1.0.4" 11 | }, 12 | "devDependencies": { 13 | "babel-cli": "^6.24.1", 14 | "babel-preset-env": "^1.7.0", 15 | "babel-preset-es2015": "^6.24.1", 16 | "babel-preset-stage-0": "^6.24.1" 17 | }, 18 | "author": "", 19 | "license": "ISC" 20 | } 21 | --------------------------------------------------------------------------------