1 of 22

Start to write Test (Side) Effect

JaMe Siwat Kaolueng

2 of 22

JaMe Siwat Kaolueng

  • Angular enthusiast passionating about front-end engineering
  • Golang beginner
  • Jasmine tea lover

https://medium.com/@perjerz3434

3 of 22

4 of 22

Fundamental

https://medium.com/stratajet-tech/a-beginners-guide-to-ngrx-store-bc2184d6d7f0

5 of 22

Redux

TommyLam - https://plugon.us/tommylam/ngrx-6111b

6 of 22

NgRx

TommyLam - https://plugon.us/tommylam/ngrx-6111b

7 of 22

RxJS

Reactive programming is programming with asynchronous data streams in JavaScript.

https://www.sitepoint.com/functional-reactive-programming-rxjs/

https://softwareengineeringdaily.com/2016/02/15/reactive-programming-with-matthew-podwysocki/

8 of 22

RxJS Example

https://gist.github.com/staltz/868e7e9bc2a7b8c1f754

9 of 22

Marble Diagram

https://medium.com/@jshvarts/read-marble-diagrams-like-a-pro-3d72934d3ef5

Stream completes successfully

Stream terminates with error

Stream does not terminate

Timeline (Left To Right)

10 of 22

Marble Diagram Example

http://rxmarbles.com

11 of 22

Marble Test

with jasmine-marbles

https://github.com/ReactiveX/rxjs/blob/5.4.2/doc/writing-marble-tests.md#basic-method

12 of 22

ASCII Marble Diagram - Basic Methods

  • hot(marbles: string, values?: object, error?: any) - creates a "hot" observable (a subject) that will behave as though it's already "running" when the test begins. An interesting difference is that hot marbles allow a ^ character to signal where the "zero frame" is. That is the point at which the subscription to observables being tested begins.
  • cold(marbles: string, values?: object, error?: any) - creates a "cold" observable whose subscription starts when the test begins.
  • expectObservable(actual: Observable<T>).toBe(marbles: string, values?: object, error?: any) - schedules an assertion for when the TestScheduler flushes. The TestScheduler will automatically flush at the end of your jasmine it block.
  • expectSubscriptions(actualSubscriptionLogs: SubscriptionLog[]).toBe(subscriptionMarbles: string) - like expectObservable schedules an assertion for when the testScheduler flushes. Both cold() and hot() return an observable with a property subscriptions of type SubscriptionLog[]. Give subscriptions as parameter to expectSubscriptions to assert whether it matches the subscriptionsMarbles marble diagram given in toBe(). Subscription marble diagrams are slightly different than Observable marble diagrams. Read more below.

https://github.com/ReactiveX/rxjs/blob/5.4.2/doc/writing-marble-tests.md#basic-method

13 of 22

Hot & Cold Observables

https://www.slideshare.net/mariofusco/reactive-programming-for-a-demanding-world-building-eventdriven-and-responsive-applications-with-rxjava

14 of 22

Hot & Cold Observables

https://www.slideshare.net/mariofusco/reactive-programming-for-a-demanding-world-building-eventdriven-and-responsive-applications-with-rxjava

15 of 22

Marble Syntax

Marble syntax is a string represents events happening over "time". The first character of any marble string always represents the "zero frame". A "frame" is somewhat analogous to a virtual millisecond.

  • "-" time: 10 "frames" of time passage.
  • "|" complete: The successful completion of an observable. This is the observable producer signaling complete()
  • "#" error: An error terminating the observable. This is the observable producer signaling error()
  • "a" any character: All other characters represent a value being emitted by the producure signaling next()
  • "()" sync groupings: When multiple events need to single in the same frame synchronously, parenthesis are used to group those events. You can group nexted values, a completion or an error in this manner. The position of the initial (determines the time at which its values are emitted.
  • "^" subscription point: (hot observables only) shows the point at which the tested observables will be subscribed to the hot observable. This is the "zero frame" for that observable, every frame before the ^ will be negative.

https://github.com/ReactiveX/rxjs/blob/5.4.2/doc/writing-marble-tests.md#basic-method

16 of 22

Marble Syntax Example

Examples

'-' or '------': Equivalent to Observable.never(), or an observable that never emits or completes

|: Equivalent to Observable.empty()

#: Equivalent to Observable.throw()

'--a--': An observable that waits 20 "frames", emits value a and then never completes.

'--a--b--|: On frame 20 emit a, on frame 50 emit b, and on frame 80, complete

'--a--b--#: On frame 20 emit a, on frame 50 emit b, and on frame 80, error

'-a-^-b--|: In a hot observable, on frame -20 emit a, then on frame 20 emit b, and on frame 50, complete.

'--(abc)-|': on frame 20, emit a, b, and c, then on frame 80 complete

'-----(a|)': on frame 50, emit a and complete.

https://github.com/ReactiveX/rxjs/blob/5.4.2/doc/writing-marble-tests.md#basic-method

17 of 22

Basic Test

var e1 = hot('----a--^--b-------c--|');�var e2 = hot( '---d-^--e---------f-----|');�var expected = '---(be)----c-f-----|';��expectObservable(e1.merge(e2)).toBe(expected);

https://github.com/ReactiveX/rxjs/blob/5.4.2/doc/writing-marble-tests.md#basic-method

18 of 22

Basic Test

var values = {� a: 1,� b: 2,� c: 3,� d: 4,� x: 1 + 3, // a + c� y: 2 + 4, // b + d�}�var e1 = hot('---a---b---|', values);�var e2 = hot('-----c---d---|', values);�var expected = '-----x---y---|';��expectObservable(e1.zip(e2, function(x, y) { return x + y; }))� .toBe(expected, values);

https://github.com/ReactiveX/rxjs/blob/5.4.2/doc/writing-marble-tests.md#basic-method

19 of 22

Testing

  • Isolated Test
  • Shallow Test
  • Integration Test

https://vsavkin.com/three-ways-to-test-angular-2-components-dcea8e90bd8d

20 of 22

E-Commerce App

  • Dispatch List Items Action
  • XHR Call
  • Response All Items
  • Update Store via Reducer

21 of 22

Demo

https://github.com/perjerz3434/NgRx-From-Store-To-View

22 of 22

Question?