DerivedState

@mvuijs/core / rx / DerivedState

DerivedState<T> #

A DerivedState object derives state from an existing DerivedState or State object using a pure function.

Example #

const state = new rx.State({a: 1, b: 4});
const derived = rx.derive(state, value => value.a + 1);
derived.subscribe(console.log); // => logs 2
state.next(3); // => logs 4

In the most simple case, this is similar to the map operator:

const state = new rx.State({a: 1, b: 4});
state.pipe(rx.map(v => v + 1)).subscribe(console.log); // => logs 2
state.next(3); // => logs 4

However, DerivedState can offer some additional features by being deliberately less powerful then operators:

  • They must always be free of side effects
  • They must always derive from some known state with an initial value
  • They cannot filter or delay emissions, they can only map values

As a general rule of thumb, always use DerivedState instead of operators when possible since they are more efficient and easy to use. There are of course many cases where operators are simply necessary.

The value of DerivedState can be accessed “imperatively” #

const derived = rx.derive(
  new rx.State({a: 1, b: 4}), value => value.a + 1
);
console.log(derived.value === 2) // => logs true

DerivedState is memoized #

When the arguments to DerivedState do not change, it does not have to run its defining function again and can instead return the previous value.

Type parameters #

  • T

Hierarchy #

Accessors #

value #

Get the current value of this DerivedState.

Be aware that if this DerivedState is not currently subscribed to anywhere, it must internally subscribe and unsubscribe and therefore execute the entire “chain” of its parent DerivedState objects. If there is an active subscription, the current value is returned immediatly without any computation.

Signature #

value(): T;

Returns #

T

Defined in: packages/core/src/rx/derived-state.ts:68

Defined in: packages/core/src/rx/derived-state.ts:68

Methods #

observable #

Signature #

observable: object;

Returns #

object

Member Type
subscribe (observer: ObserverDefinition <T>) => { unsubscribe: () => void; }

Inherited from: Stream . [observable]

Defined in: packages/core/src/rx/stream.ts:191

derive() #

Shorthand for rx. derive (this, definition)

Signature #

derive<ReturnT>(definition: Function, equality: Equality = 'scalar'): DerivedState<ReturnT>;

Type parameters #

  • ReturnT

Parameters #

Name Type Default value
definition (value: T) => ReturnT undefined
equality Equality 'scalar'

Returns #

DerivedState <ReturnT>

Defined in: packages/core/src/rx/derived-state.ts:126

filter() #

Shorthand for .pipe(rx.filter(...))

Signature #

filter(filter: Function): Stream<T>;

Parameters #

Name Type
filter (value: T) => boolean

Returns #

Stream <T>

Inherited from: Stream . filter

Defined in: packages/core/src/rx/stream.ts:187

if() #

Shorthand for .pipe(rx.if(...))

Signature #

if<TrueT>(this: Stream<boolean>, def: TrueT): Stream<undefined | TrueT>;

Type parameters #

  • TrueT

Parameters #

Name Type
this Stream <boolean>
def TrueT

Returns #

Stream <undefined | TrueT>

Inherited from: Stream . if

Defined in: packages/core/src/rx/stream.ts:182

ifelse() #

Shorthand for .pipe(rx.ifelse(...))

Signature #

ifelse<TrueT, FalseT>(this: Stream<boolean>, def: object): Stream<TrueT | FalseT>;

Type parameters #

  • TrueT
  • FalseT

Parameters #

Name Type
this Stream <boolean>
def object
def.else FalseT
def.if TrueT

Returns #

Stream <TrueT | FalseT>

Inherited from: Stream . ifelse

Defined in: packages/core/src/rx/stream.ts:174

map() #

Shorthand for .pipe(rx.map(...))

Signature #

map<ReturnT>(mapper: Function): Stream<ReturnT>;

Type parameters #

  • ReturnT

Parameters #

Name Type
mapper (value: T) => ReturnT

Returns #

Stream <ReturnT>

Inherited from: Stream . map

Defined in: packages/core/src/rx/stream.ts:169

pipe() #

Pipe this Stream through a series of operators. Operator functions can be looked up in the rx namespace.

Example #

rx.of([0, 1, 2, 3]).pipe(
  rx.map(n => n + 1),
  rx.filter(n => n !== 2),
).subscribe(console.log);
// prints 1, 3, 4

Signature #

pipe<A, B>(op1: OperatorFunction<T, A>, op2: OperatorFunction<A, B>): Stream<B>;

Type parameters #

  • A
  • B

Parameters #

Name Type
op1 OperatorFunction <T, A>
op2 OperatorFunction <A, B>

Returns #

Stream <B>

Inherited from: Stream . pipe

Defined in: packages/core/src/rx/stream.ts:109

subscribe() #

‘Subscribe’ to this Stream with a function. Whenever a new value is emitted (that is, the next function passed to the subscriber in the constructor is called), observer will be called with the new value. Returns a ‘unsubscribe’ function that you may want to store to later be able to unsubscribe. Note that if a Stream does not complete, not unsubscribing is a memory leak.

Signature #

subscribe(observer: ObserverDefinition<T>): Function;

Parameters #

Name Type
observer ObserverDefinition <T>

Returns #

Function

‘Subscribe’ to this Stream with a function. Whenever a new value is emitted (that is, the next function passed to the subscriber in the constructor is called), observer will be called with the new value. Returns a ‘unsubscribe’ function that you may want to store to later be able to unsubscribe. Note that if a Stream does not complete, not unsubscribing is a memory leak.

Signature #
(): void;
Returns #

void

Inherited from: Stream . subscribe

Defined in: packages/core/src/rx/stream.ts:49

then() #

You can await the last value of a Stream. This of course requires the Stream to complete. If no value was emitted, an EmptyError will be thrown.

This is useful for consuming a Stream based API in a Promise based environment. For example, mvui’s HTTP client can be used like this:

const response = await http.get<number>('/my-route');
// response will be of type number

Signature #

then(callback: Function): void;

Parameters #

Name Type
callback (value: T) => any

Returns #

void

Inherited from: Stream . then

Defined in: packages/core/src/rx/stream.ts:217