# @helpers4/observable

> Tree-shakable TypeScript utility functions for the `observable` domain.
> Package: `@helpers4/observable` — Version: 3.0.1
> License: LGPL-3.0-or-later

## Installation

```sh
npm install @helpers4/observable
# or
pnpm add @helpers4/observable
```

## Usage

```typescript
import { combine, combineLatest, isObservable } from '@helpers4/observable';
```

## Functions

| Function | Description |
|---|---|
| `combine` | Combine two observables with a map function and an optional pre-treatment.  Note: you can use the pr |
| `combineLatest` | Combines multiple Observables to create an Observable whose values are calculated from the latest va |
| `isObservable` | Checks if a value is an RxJS Observable or any compatible observable.  Uses duck-typing: returns `tr |

---

## API Reference

### `combine`

Combine two observables with a map function and an optional pre-treatment.

Note: you can use the pre-treatment to add a filter, a distinctUntilChanged,
any other operator that can be used in a pipe, or even an `UntilDestroy`
operator.

```typescript
import { combine } from '@helpers4/observable';

combine<T, U, R>(source1: Observable<T>, source2: Observable<U>, map: function, options?: combineOptions<T, U>): Observable<R>
```

**Parameters:**

- `source1: Observable<T>` — first source of data
- `source2: Observable<U>` — second source of data
- `map: function` — way to combine data
- `options?: combineOptions<T, U>` — options for the combineLatest operator

**Returns:** `Observable<R>` — an observable that emits the result of the map function

**Examples:**

*Combine two observables with a map*

Combines the latest values of two observables using a mapping function.

```typescript
combine(of(1), of(2), ([a, b]) => a + b)
// emits 3
```

---

### `combineLatest`

Combines multiple Observables to create an Observable whose values are
calculated from the latest values of each of its input Observables.

This method relies on combineLatestOperator of rxjs.

The main difference with combineLatestOperator is in case of empty parameters.
If the parameter is empty (empty array or empty object), the result will be
also empty.

ATTENTION: this version doesn't support `scheduler` nor `mapper` as last
argument like in combineLatestOperator.

```typescript
import { combineLatest } from '@helpers4/observable';

combineLatest<A extends readonly unknown[]>(sources: readonly [ObservableInputTuple<A>]): Observable<A>
```

**Parameters:**

- `sources: readonly [ObservableInputTuple<A>]`

```typescript
import { combineLatest } from '@helpers4/observable';

combineLatest<T extends Record<string, ObservableInput<unknown>>>(sourcesObject: T): Observable<mapped>
```

**Parameters:**

- `sourcesObject: T`

**Examples:**

*Combine array of observables*

Combines an array of observables into one that emits arrays of their latest values.

```typescript
combineLatest([of(1), of(2), of(3)])
// emits [1, 2, 3]
```

*Handle empty array*

Returns an observable that emits an empty array when given no sources.

```typescript
combineLatest([])
// emits []
```

---

### `isObservable`

Checks if a value is an RxJS Observable or any compatible observable.

Uses duck-typing: returns `true` for any object with both `.subscribe()` and
`.pipe()` methods, covering `Observable`, `Subject`, `BehaviorSubject`,
`ReplaySubject`, and any RxJS-compatible observable implementation.

```typescript
import { isObservable } from '@helpers4/observable';

isObservable(value: unknown): value is Observable<unknown>
```

**Parameters:**

- `value: unknown` — The value to check

**Returns:** `value is Observable<unknown>` — `true` if value is observable-like

**Examples:**

*Detect an RxJS Observable or Subject*

Returns true for Observable, Subject, BehaviorSubject, and any duck-typed observable.

```typescript
import { Observable, Subject } from 'rxjs';
isObservable(new Observable())  // => true
isObservable(new Subject())     // => true
isObservable(Promise.resolve()) // => false
isObservable({})                // => false
```

*Accept either an Observable or a plain value*

Use as a guard to normalize inputs that may be Observables or raw values.

```typescript
import { Observable, of } from 'rxjs';
function toObservable<T>(value: T | Observable<T>): Observable<T> {
  return isObservable(value) ? value : of(value);
}
```

---
