# react-context-store

> A two way binding solution that uses React context as a storage mechanism.

Latest version **1.1.1** (published 2022-10-13) · MIT license · 0 weekly downloads

## Install

```sh
npm install react-context-store
pnpm add react-context-store
yarn add react-context-store
bun add react-context-store
```

## Health

**Score 15/100 (F)** — status: abandoned.

Positive: no vulnerabilities.

Warnings: low downloads; no types; no esm support.

Negative: abandoned; low maintenance score.

## Facts

| | |
|---|---|
| Version | 1.1.1 |
| Published | 2022-10-13 |
| First published | 2017-03-02 |
| Weekly downloads | 0 |
| License | MIT |
| TypeScript types | none |
| Module format | CommonJS |
| Dependencies | 0 |
| Unpacked size | 102.2 KB |
| Known vulnerabilities | 0 |
| Install scripts | no |
| Author | Snowcoders |
| Maintainers | k2snowman69 |

## Links

- npm: https://www.npmjs.com/package/react-context-store
- Repository: https://github.com/snowcoders/react-context-store
- Homepage: https://github.com/snowcoders/react-context-store#readme
- Issues: https://github.com/snowcoders/react-context-store/issues
- npm.io page: https://npm.io/package/react-context-store

## Recent versions

- 1.1.1 (latest) — 2022-10-13
- 1.2.0-beta.1 (beta) — 2023-07-15
- 1.2.0-beta.0 — 2023-07-15
- 1.1.0 — 2021-05-24
- 1.1.0-beta.0 — 2021-05-23
- 1.0.0 — 2021-03-02
- 1.0.0-beta.6 — 2021-03-01
- 1.0.0-beta.5 — 2021-02-28
- 1.0.0-beta.4 — 2021-02-23
- 1.0.0-beta.3 — 2021-02-21
- 1.0.0-beta.2 — 2021-02-16
- 1.0.0-beta.0 — 2021-02-05
- 0.1.0 — 2017-10-23
- 0.0.5 — 2017-07-17
- 0.0.4 — 2017-06-16
- … 3 more at https://npm.io/package/react-context-store/versions

## README

# React context store

A two way binding mechanism that uses React context as a storage machanism.

For small to medium sized apps I found redux to be a bit heavy for what it achieved. In reality, most of the time I want to create a simple website that blocks the form submit as a network call is being processed.

## API

There are a few types of store hooks both of which return the current store contents and the available modifiers.

- useContextStore - For non-indexable stores like objects and primatives or when you don't need to edit individual elements
- useIndexableContextStore - For indexable stores like maps or arrays with a single loading state at the root
- useIndexableStatefulContextStore - For indexable stores but when you want to maintain separate load states per item than the list of items

All come with some basic modifiers:

- useUpdateFactory - Used to modify all the values in the store at once. Useful for getAll, deleteAll, modifyAll, etc.
- setContextData - Used to create custom modifiers if for some reason you don't like ours.

They also have the same states:

- unsent - No modifier has acted upon the data
- loading - The modifier has been invoked but the action hasn't completed yet
- success - The action was successful and the data has been updated
- error - The action failed

The `useIndexableContextStore` and `useIndexableStatefulContextStore` have additional update factories that allow for creating functions that manipulate individual items:

- useCreateOneFactory - Used to create a new entry - GET and POST calls.
- useDeleteOneFactory - Used to remove an entry - DELETE call
- useUpdateOneFactory - Used to update an existing entry - PUT/PATCH calls

## Example usage

The following documentation has been copied out of a test case. If you find that it's not working, please check the test case. This example is an array but you can also use maps, or store a non-indexable type.

First create the context store

```javascript
import React, { PropsWithChildren } from "react";

import {
  ContextStore,
  getNotImplementedPromise,
  useIndexableContextStore,
} from "react-context-store";

export type Item = {
  id: number,
  name: string,
};

type ContextStoreData = Array<Item>;

export type RefreshAllParams = void;
export interface ContextValue extends ContextStore<ContextStoreData> {
  refreshAll: (params: RefreshAllParams) => Promise<ContextStoreData>;
}

const defaultValue: ContextValue = {
  data: [],
  refreshAll: getNotImplementedPromise,
  state: "unsent",
};

export const Context = React.createContext(defaultValue);
export type ProviderProps = PropsWithChildren<{}>;

export function ApiProvider(props: ProviderProps) {
  const { children } = props;
  const [contextValue, { useUpdateFactory }] = useIndexableContextStore(
    defaultValue
  );

  const refreshAll = useUpdateFactory({
    action: (params: RefreshAllParams) => {
      return fetchResults(params);
    },
  });

  return (
    <Context.Provider
      value={{
        ...contextValue,
        refreshAll,
      }}
    >
      {children}
    </Context.Provider>
  );
}
```

Somewhere in your app, setup the shared provider

```javascript
import { ApiProvider, Context } from "../context";
import { List } from "./component";

export function App() {
  return (
    <ApiProvider>
      <List />
    </ApiProvider>
  );
}
```

And finally consume the context

```javascript
import { ApiProvider, Context } from "../context";

export function List() {
  const { data, refreshAll, state } = useContext(Context);

  useEffect(() => {
    refreshAll();
  });

  switch (state) {
    case "error":
      return <div>Oh no!</div>;
    case "success":
      return (
        <div>
          <ul>
            {data.map((item) => {
              const { id, name } = item;
              return <li key={id}>{name}</li>;
            })}
          </ul>
        </div>
      );
    default:
      return <div>Loading</div>;
  }
}
```

For more examples, take a look at our extensive testing suite.

---
_Source: https://npm.io/package/react-context-store · Machine-readable twin of the npm.io package page. Health data is recomputed on every publish._
