RxJs, Redux Observable, Redux Toolkit. Part 1 - setup
2 min
In this article, we will put together a simple React, ping pong application to show the idea of reactivity.
Note that this article is part of RxJs series about the RxJs, Redux Observable, Redux Toolkit:
So let's start:
Bootstrap
First, we will initialize CRA application with TypeScript
yarn create react-app react-redux-toolkit-rxjs-setup --template typescript
Then we will add libraries
yarn add @reduxjs/toolkit react-redux rxjs redux-observable@2.0.0-rc.2
Building block
Create a redux Toolkit slice
// app.slice.ts import { createSlice } from '@reduxjs/toolkit'; export interface AppState {} const initialState: AppState = {}; export const appSlice = createSlice({ name: 'app', initialState, reducers: { ping: () => {}, pong: () => {}, endGame: () => {}, }, });
Then we will create an Epic
// app.epic.ts import { Action } from '@reduxjs/toolkit'; import { combineEpics, Epic } from 'redux-observable'; import { filter, map, tap } from 'rxjs/operators'; import { appSlice } from './app.slice'; export type RootEpic = Epic<Action, Action>; const ping$: RootEpic = (action$) => action$.pipe( filter(appSlice.actions.ping.match), tap(() => console.log('ping')), map(() => appSlice.actions.pong()) ); const pong$: RootEpic = (action$) => action$.pipe( filter(appSlice.actions.pong.match), tap(() => console.log('pong')), map(() => appSlice.actions.endGame()) ); export const appEpic$ = combineEpics(ping$, pong$);
Put it together
Create a store
// app.store.ts import { Action } from '@reduxjs/toolkit'; import { createEpicMiddleware } from 'redux-observable'; import { configureStore } from '@reduxjs/toolkit'; import { appSlice } from './app.slice'; import { appEpic$ } from './app.epic'; const epicMiddleware = createEpicMiddleware<Action, Action>(); export const store = configureStore({ reducer: { app: appSlice.reducer, }, middleware: [epicMiddleware], }); epicMiddleware.run(appEpic$);
Provide a store
// index.tsx import React from 'react'; import ReactDOM from 'react-dom'; import { Provider } from 'react-redux'; import { App } from './app/app'; import { store } from './app/app.store'; ReactDOM.render( <React.StrictMode> <Provider store={store}> <App /> </Provider> </React.StrictMode>, document.getElementById('root') );
Fire action
Finally, let's dispatch a ping action
// app.tsx import { useEffect } from 'react'; import { useDispatch } from 'react-redux'; import { appSlice } from './app.slice'; export const App = () => { const dispatch = useDispatch(); useEffect(() => { dispatch(appSlice.actions.ping()); }, [dispatch]); return <div>Ping pong setup</div>; };
In the console log you should see:
ping pong
See complete code here
Thanks for reading.