https://github.com/seracio/plugnplay
A tiny module to use a dictionary of Observables as a store for React
https://github.com/seracio/plugnplay
react rxjs store
Last synced: 2 months ago
JSON representation
A tiny module to use a dictionary of Observables as a store for React
- Host: GitHub
- URL: https://github.com/seracio/plugnplay
- Owner: seracio
- License: mit
- Created: 2017-03-08T14:43:04.000Z (about 8 years ago)
- Default Branch: master
- Last Pushed: 2025-03-27T16:00:29.000Z (2 months ago)
- Last Synced: 2025-03-31T09:13:40.867Z (2 months ago)
- Topics: react, rxjs, store
- Language: TypeScript
- Homepage:
- Size: 796 KB
- Stars: 1
- Watchers: 1
- Forks: 0
- Open Issues: 1
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
# plugnplay

> A tiny module to use a dictionary of Observables as a Store for React
## Disclaimer
The purpose here is not to provide an async middleware to a redux store with Observables, as [redux-cycle-middleware](https://github.com/cyclejs-community/redux-cycle-middleware) and [redux-observable](https://github.com/redux-observable/redux-observable) do but to replace redux and its different slices (async middlewares, reducers and derived data) with Behavior Subjects. As this, we can express each variable of the store as a function of other variables, in a clean and async way.
This library only exposes a component `Playground` (a store Provider) and a render props component `Plug`.
## Install
```bash
npm i [email protected] [email protected] rxjs@6 @seracio/plugnplay
```## Basic usage
```javascript
import { Plug, Playground } from '@seracio/plugnplay';
import React from 'react';
import { of, interval } from 'rxjs';
import { shareReplay, delay } from 'rxjs/operators';// expose a dictionary of Observables (Behavior Subjects)
const store = {
hello$: of('hello').pipe(delay(250), shareReplay(1)),
count$: interval(1000).pipe(shareReplay(1))
};render(
My app
store.hello$}>
{(val) => (!!val ?{val}:waiting...)}
Here is a counter:
store.count$}>
{(val) => (!!val ?{val}:waiting...)}
);
```## API
### Playground
The `Playground` component is the equivalent of a redux `Provider`.
```typescript
type PlaygroundProps = {
store: { [key: string]: Observable };
children: JSX.Elements;
};
```### Plug
```typescript
type PlugProps = {
combinator: (store) => Observable;
defaultValue?: any;
};
```The `combinator` props is a function that takes the dictionary store as param and returns the unique Observable we want to listen to.
This Observable can be:- an Observable defined in the store
- a combination of multiple Obserables from the store (thanks to RX operators)
- a brand new Observble, unlinked to the storeThe value of this Observable will be emitted through a render props function. Typically, you want them to be formated like props, but nothing mandatory here:
```javascript
combineLatest(store.count$, store.val$).pipe(
map(([count, val]) => ({ count, val }))
)
}
>
{(props) => (!!props ? : )}```
As Observables are asynchronous by nature, you must provide a defaultValue if you want a synchronous rendering:
```javascript
store.props$} defaultValue={{ count: 0, val: '' }}>
{(props) => }```
Or you can use a Waiting component, as defaultValue is defined as null by default:
```javascript
store.props$}>
{(props) => (!!props ? : )}```
## Development
```
yarn test --watch
```## Publish
Due to the namespace
```
npm publish --access=public
```