A tiny state container for JavaScript apps
- Tiny footprint (
@stash/core
+@stash/react
= way less than 1kb) - Familiar names and ideas from Redux
- Thunks support with no additional packages
- TypeScript first class support (stash is written in TS ❤️)
- DevTools support (soon)
import { createStore } from "@stash/core";
// create store and set initial state
const store = createStore({ todos: [], loading: false });
import { createAction, createThunk } from "@stash/core";
// An action is just a reducer
const AddTodo = createAction("Add todo", (state, todo) => {
return { ...state, todos: [...state.todos, todo] };
});
// The first param (e.g. "Set loading") is used for logging
const SetLoading = createAction("Set loading", (state, loading) => {
return { ...state, loading };
});
// A thunk may dispatch actions asynchronously
const LoadTodos = createThunk("Load todos", (state, payload, dispatch) => {
dispatch(SetLoading, true);
setTimeout(() => {
dispatch(AddTodo, "3. Third todo");
dispatch(SetLoading, false);
}, 3000);
});
NOTE: You need to use React v16.8.0 (or later) to run this code since
useStore
is a custom hook.
import React from 'react';
import { useStore } from "@stash/react";
import { AddTodo, LoadTodos } from './actions';
function Todos() {
// useStore also accepts a selector e.g.
// const [loading, dispatch] = useStore(state => state.loading)
const [state, dispatch] = useStore();
React.useEffect(() => {
// Load some todos
dispatch(AddTodo, "1. First todo");
dispatch(AddTodo, "2. Second todo");
// Load more async
dispatch(LoadTodos, {});
}, []);
return (
<div>
<h1>Todos</h1>
<ul>
{state.todos.map((todo, index) => (
<li key={index}>{todo}</li>
))}
</ul>
{state.loading && "Loading ..."}
</div>
);
}
To be able to use useStore
we must wrap our <Todos>
inside the <Provider>
component provided by @stash/react
package. For example:
import { Provider } from "@stash/react";
import store from './store';
ReactDOM.render(
<Provider store={store}>
<Todos />
</Provider>,
document.getElementById("root")
);
Install @stash/logger
package:
$ npm add -D @stash/logger
Then:
const store = createStore(/* initial state */);
// Add logging
createLogger()(store);
Name | Version | Size |
---|---|---|
@stash/core |
||
@stash/react |
||
@stash/logger |
See examples.
MIT © Ahmed T. Ali