The value of a philanthropic laboratory

While George Washington is credited as the first to say it, many have embraced the idea of the United States as “The Great Experiment.” In a letter dated in 1790, Washington expresses that the…

Smartphone

独家优惠奖金 100% 高达 1 BTC + 180 免费旋转




Marble testing Observable Introduction

The way we tend to learn and communicate about observables and streams in general, is done with marble diagrams. It is a visual representation, like a schema describing what’s happening with our observable.

When we need to test Observables, we have two main patterns that we can use. Either the subscribe and assert pattern, or the marble testing pattern using diagrams. This article is an introduction to marble testing.

Marble diagram is a domain specific language for RxJS to help you to model the interactions and the values of one or more observable in your test.

Because observable is a stream of events through time and some operators are directly affecting this time relation (delay, throttle…), it is a better and easier way to represent them visually with diagrams. You can see the observable values, the operator and the result through time.

This new syntax will provide you the power to create and manipulate the stream of your observable. For example:

of(1, 2, 3).pipe(map(x => x*2))

This code will create an observable that will emit a value. Then, the value will be multiplied by 2. We can represent this with a marble diagram like this:

To write a test with marble diagrams you will need to stick to a convention of characters that will help visualize the observable stream:

These strings are a powerful syntax that will permit you to simulate the passage of time, emit a value, a completion, an error etc.. all that, without creating the observable yourself.

You also have some methods to parse and create observables from your diagrams:

cold(marbles: string, values?: object, error?: any) Subscription starts when test begins:

cold(--a--b--|, { a: 'Hello', b: 'World' }) → Emit ‘Hello’ at 30ms and ‘World’ at 60ms, complete at 90ms.

hot(marbles: string, values?: object, error?: any) Behaves like subscription starts at point of caret:

hot(--^--a--b--|, { a: 'Hello', b: 'World' }) → Subscription begins at point of caret, then emit ‘Hello’ at 30ms and ‘World’ at 60ms, complete at 90ms.

Now if we want to create the marble test of the previous example, we can do as follow:

Marble testing is really useful as this technique allows you to actually see the value emitted by your observable though time in a nice and simple manner.

Notice the source and expected variables declarations, in marble testing you will use this pattern a lot. With this pattern, you are able to see when the emitted values (a, b, c), when the subscription ends (|) for the source and can directly compare with what is expected.

You can see more example on StackBlitz below:

Marble diagrams are parsed, creating an observable that emits test message objects. The parsing step is done through the helper functions cold() and hot() .

When parsed, the resulting object message has some specific properties:

Test message object includes the values emitted, the frame at which thew were emitted, and the type of notification, including next, error, and complete. These objects will be tested by the expect clause in you tests.

To show the basics of Marble testing, lets see some examples with different RxJS operators.

Map operator
SwitchMap operator
MergeMap operator
ConcatMap operator

More examples on StackBlitz below:

When time comes into play, the test needs to have a time reference or context. We don’t want to have to deal with milliseconds, so we are changing the time reference to use a virtual clock, that will count in frames. This is the role of the TestScheduler.

All RxJS operators & utilities that handle the concept of time (delay, interval, debounce…) have a second argument where you can inject your Scheduler (the time reference). It will determine what “thing” you will use for the passage of time (milliseconds, frames).

Let see some examples with Interval and Delay:

Testing an interval with the TestScheduler

Examples available on StackBlitz below:

In this article we have looked at what is Marbles Testing with Observables. We used some basic examples to show how it works. We then saw how to test Observable that has relation to time with some examples.

Add a comment

Related posts:

As mulheres fora do horizonte

Quando pensamos no movimento modernista brasileiro, costumamos ter poucas referências femininas na ponta da língua. Geralmente, conhecemos apenas Tarsila do Amaral e Anita Malfatti — que, embora…

Ditch the Gym!

My fitness journey started from going to a nearby gym near my house. The gym was tiny but enough to help me kickstart my passion for fitness. I would come to the gym and workout daily to a point…