{"_id":"@alismael/remote-data","_rev":"3-4a9b0792970e021289a88cb7ec838693","name":"@alismael/remote-data","dist-tags":{"latest":"1.0.2"},"versions":{"1.0.0":{"name":"@alismael/remote-data","version":"1.0.0","description":"Handling Asynchronous fetching of data with React & Redux","author":{"name":"alismael"},"license":"MIT","repository":{"type":"git","url":"git+https://github.com/alismael/remote-data.git"},"main":"dist/index.js","module":"dist/index.modern.js","source":"src/index.ts","engines":{"node":">=10"},"scripts":{"build":"microbundle-crl --no-compress --format modern,cjs","start":"microbundle-crl watch --no-compress --format modern,cjs","prepare":"run-s build","test":"run-s test:unit test:lint test:build","test:build":"run-s build","test:lint":"eslint .","test:unit":"cross-env CI=1 react-scripts test --env=jsdom","test:watch":"react-scripts test --env=jsdom","predeploy":"cd example && npm install && npm run build","deploy":"gh-pages -d example/build"},"peerDependencies":{"react":"^16.0.0","redux":"^3.7.2 || ^4.0.0","axios":"^0.18.0 || ^0.19.0"},"devDependencies":{"@testing-library/jest-dom":"^4.2.4","@testing-library/react":"^9.5.0","@testing-library/user-event":"^7.2.1","@types/jest":"^25.1.4","@types/node":"^12.12.38","@types/react":"^16.9.27","@types/react-dom":"^16.9.7","@typescript-eslint/eslint-plugin":"^2.26.0","@typescript-eslint/parser":"^2.26.0","axios":"^0.19.2","babel-eslint":"^10.0.3","cross-env":"^7.0.2","eslint":"^6.8.0","eslint-config-prettier":"^6.7.0","eslint-config-standard":"^14.1.0","eslint-config-standard-react":"^9.2.0","eslint-plugin-import":"^2.18.2","eslint-plugin-node":"^11.0.0","eslint-plugin-prettier":"^3.1.1","eslint-plugin-promise":"^4.2.1","eslint-plugin-react":"^7.17.0","eslint-plugin-standard":"^4.0.1","gh-pages":"^2.2.0","microbundle-crl":"^0.13.10","node-sass":"^4.14.1","npm-run-all":"^4.1.5","prettier":"^2.0.4","react":"^16.13.1","react-dom":"^16.13.1","react-scripts":"^3.4.1","redux":"^4.0.5","typescript":"^3.7.5"},"keywords":["remote-data","remote-component","react","redux","component","components","react-remote-component","react-remote-data","api","asynchronous","async","fetching"],"dependencies":{},"gitHead":"030dfadc8a1ee5f0d9660d8187b46cc0fedee2a7","bugs":{"url":"https://github.com/alismael/remote-data/issues"},"homepage":"https://github.com/alismael/remote-data#readme","_id":"@alismael/remote-data@1.0.0","_nodeVersion":"12.14.1","_npmVersion":"6.13.4","dist":{"integrity":"sha512-9jHUKqGsB4b9nO+V7IxeYVso5Z+a0GRvmzGX7bLdk9ARKNUho4XXLQjsAWho3vUuKpPjd59bhjNQMv3qJwN5Rg==","shasum":"915d69a1adb5c95842287577acbaf9323f6647c4","tarball":"https://registry.npmjs.org/@alismael/remote-data/-/remote-data-1.0.0.tgz","fileCount":23,"unpackedSize":40454,"npm-signature":"-----BEGIN PGP SIGNATURE-----\r\nVersion: OpenPGP.js v3.0.4\r\nComment: https://openpgpjs.org\r\n\r\nwsFcBAEBCAAQBQJfCd3CCRA9TVsSAnZWagAAOQ0P/jWQ/tN5RqmQ9SlEe03J\nkBKDIcOgMUV6pACnfqrrWiZVlU34504gktScxLtSrD+x+46gHr2OH3wXnUTL\nAIouOpOxqUs3m3d5y5r5R0fthYuxl/9wV8TNVEhnZPbvKjiIMKnDey+4JWN6\n553G6Fch8LcBFyo+I9gegnertcNPf3vsrV+yFUsLOr9B6Y3NwXMyZVg2GsjA\n6X77mmWBqbLD277RzTqTu/qw16Fezr88EQngXI4999AO5fLEel3fxV53SU8d\nSQ1FBmQtOzGnGxXUB6V18E/nyqVXKRDT4P0zNZhD7/XRQ5K79Of0uP9F33oD\nFq4OCFINIJi8GIOKCmq3pMIrQU8rmoO1xFMomDeLLfeNe/cDdtTxn/PHcrE7\nkRS7v2lS3/MOtjo3eBsBLkqXIiackg1kVP6MOgc1hbYG6HyJofyvPxIq5lEd\nvcAVoYI7aHmq6WhK5xdm81Lr+SgK096rPDjY3OJNw+ZGCGLpq+fkeD2nJ4I7\npBLxua0ZBcAr42O4LIShm2fbZx47xYexfL7BvBrjEkIJ0cZ7t9BaJhT+4g1x\n9Erj50UwQGTsI8DZ4lYEaXGlT90RWEUEnzmVbn4z8LgbHXYnuGSnyJVxHbEK\ncScd7yd/u8tgiOqjuVDONRForlVdFVUIVuXb3QrHxnP+JhK0GgSmNxgZwZLQ\nr1o0\r\n=OMDM\r\n-----END PGP SIGNATURE-----\r\n","signatures":[{"keyid":"SHA256:jl3bwswu80PjjokCgh0o2w5c2U4LhQAE57gj9cz1kzA","sig":"MEUCIE2sqy8uABl3LdrtEMB9zhaaFagjQQBwJ/iosvs50qwtAiEA2GilnM+9ZKfuMWOLdyk2l2t+3uisBfZiuOVNZeuNNGA="}]},"maintainers":[{"name":"alismael","email":"aliismaelabdelwahab@gmail.com"}],"_npmUser":{"name":"alismael","email":"aliismaelabdelwahab@gmail.com"},"directories":{},"_npmOperationalInternal":{"host":"s3://npm-registry-packages","tmp":"tmp/remote-data_1.0.0_1594482114099_0.15239674149510596"},"_hasShrinkwrap":false},"1.0.1":{"name":"@alismael/remote-data","version":"1.0.1","description":"Handle modeling, fetching, and displaying remote data in React/Redux apps","author":{"name":"alismael"},"license":"MIT","repository":{"type":"git","url":"git+https://github.com/alismael/remote-data.git"},"main":"dist/index.js","module":"dist/index.modern.js","source":"src/index.ts","engines":{"node":">=10"},"scripts":{"build":"microbundle-crl --no-compress --format modern,cjs","start":"microbundle-crl watch --no-compress --format modern,cjs","prepare":"run-s build","test":"run-s test:unit test:lint test:build","test:build":"run-s build","test:lint":"eslint .","test:unit":"cross-env CI=1 react-scripts test --env=jsdom","test:watch":"react-scripts test --env=jsdom","predeploy":"cd example && npm install && npm run build","deploy":"gh-pages -d example/build"},"peerDependencies":{"react":"^16.0.0","redux":"^3.7.2 || ^4.0.0","axios":"^0.18.0 || ^0.19.0"},"devDependencies":{"@testing-library/jest-dom":"^4.2.4","@testing-library/react":"^9.5.0","@testing-library/user-event":"^7.2.1","@types/jest":"^25.1.4","@types/node":"^12.12.38","@types/react":"^16.9.27","@types/react-dom":"^16.9.7","@typescript-eslint/eslint-plugin":"^2.26.0","@typescript-eslint/parser":"^2.26.0","axios":"^0.19.2","babel-eslint":"^10.0.3","cross-env":"^7.0.2","eslint":"^6.8.0","eslint-config-prettier":"^6.7.0","eslint-config-standard":"^14.1.0","eslint-config-standard-react":"^9.2.0","eslint-plugin-import":"^2.18.2","eslint-plugin-node":"^11.0.0","eslint-plugin-prettier":"^3.1.1","eslint-plugin-promise":"^4.2.1","eslint-plugin-react":"^7.17.0","eslint-plugin-standard":"^4.0.1","gh-pages":"^2.2.0","microbundle-crl":"^0.13.10","node-sass":"^4.14.1","npm-run-all":"^4.1.5","prettier":"^2.0.4","react":"^16.13.1","react-dom":"^16.13.1","react-scripts":"^3.4.1","redux":"^4.0.5","typescript":"^3.7.5"},"keywords":["react","redux","remote-data","remote-component","component","components","api","asynchronous","fetching","fetching-data","typescript","typescript-library"],"dependencies":{},"gitHead":"d3eb72de455faacfb335edf174d91e50f6252594","bugs":{"url":"https://github.com/alismael/remote-data/issues"},"homepage":"https://github.com/alismael/remote-data#readme","_id":"@alismael/remote-data@1.0.1","_nodeVersion":"12.16.0","_npmVersion":"6.13.4","dist":{"integrity":"sha512-91KufVR4pVhrF93nYRfnopLmCkAv7KrDFSn5RzOFXR/znQBZkkE5wK1wQY9ivxFB4exTI6xYoRIaDpgKNQ7hCA==","shasum":"5ce7460bc08fdfccd80a51dd49e0f33d2377801e","tarball":"https://registry.npmjs.org/@alismael/remote-data/-/remote-data-1.0.1.tgz","fileCount":18,"unpackedSize":39699,"npm-signature":"-----BEGIN PGP SIGNATURE-----\r\nVersion: OpenPGP.js v3.0.13\r\nComment: https://openpgpjs.org\r\n\r\nwsFcBAEBCAAQBQJfhVvUCRA9TVsSAnZWagAAoIIP/2alItzMLUcpYGX5lNWG\n2Y9t3AVlQCErRoJQmJIvnCB6WAqpie046GIMuNj4m/8tHyollqHk6O11V4zP\nf7XFNHHc6dG0sG9ZkNh7QgSQ8RLpX2CFQDac2jUMz9kEgbAglZfdXlV4nrx+\nhL1aA8dcUTcebutc/89AUk9GVfYgwX+QbSdUqAwE6M3zGh+jheEr+b8uTHZB\niOziNcWz2kYWgR+2EA//zJq1PSpC8uU5vwP/3OXM451o6+bjh2QXiIIVInHj\nUHUwghvMZXD/IRNTI0CZKiLwgVRT9NY6rwuPpEZd8nFTYlUIU6GTw3BY1L9c\nIYQETtb523wDr3/b1glKv73jHls/oYhzjiozURv9ZYBAgfeFNr3t+xRe84/X\nlDyVDWUX6NwC2qZnY4/a5XnXhknI4+F6DnBKu5uotfWmNM5ByZTQzCwdub6j\ny9JBO/6GVsq4leoVzYP7t5wXStTbhOhmFpX0CbYx5qQxbaUZJuqVD3eBJR7C\nx54pZQMAfdy5Poupbj4fCn3wtvsXM5V/mANv12LpMuCdLJA4+kDD/F0IXFre\n8KgvaEBcN6W5BsxFSoiMHklRCTxwkmTxeEa1hIsv4uWiPJJVPjU19B8yKMtB\n1Qy8rxoNhRB+Xi212pG/ri/2kunKSWVq7pwiKuYQKkHErmMk6f8c8dtsIbFR\nbjPW\r\n=aZFf\r\n-----END PGP SIGNATURE-----\r\n","signatures":[{"keyid":"SHA256:jl3bwswu80PjjokCgh0o2w5c2U4LhQAE57gj9cz1kzA","sig":"MEQCIDX4AOcuPN3FyNJHtAT10F8jnCrjeZtF2GQmVVNYBSn3AiAVSo107brZO/YQRnTvfLfKknXy3YQgYz0X1jHESL64HQ=="}]},"maintainers":[{"name":"alismael","email":"aliismaelabdelwahab@gmail.com"}],"_npmUser":{"name":"alismael","email":"aliismaelabdelwahab@gmail.com"},"directories":{},"_npmOperationalInternal":{"host":"s3://npm-registry-packages","tmp":"tmp/remote-data_1.0.1_1602575315649_0.7648297395438259"},"_hasShrinkwrap":false},"1.0.2":{"name":"@alismael/remote-data","version":"1.0.2","description":"Handle modeling, fetching, and displaying remote data in React/Redux apps","author":{"name":"alismael"},"license":"MIT","repository":{"type":"git","url":"git+https://github.com/alismael/remote-data.git"},"main":"dist/index.js","module":"dist/index.modern.js","source":"src/index.ts","engines":{"node":">=10"},"scripts":{"build":"microbundle-crl --no-compress --format modern,cjs","start":"microbundle-crl watch --no-compress --format modern,cjs","prepare":"run-s build","test":"run-s test:unit test:lint test:build","test:build":"run-s build","test:lint":"eslint .","test:unit":"cross-env CI=1 react-scripts test --env=jsdom","test:watch":"react-scripts test --env=jsdom","predeploy":"cd example && npm install && npm run build","deploy":"gh-pages -d example/build"},"peerDependencies":{"react":"^16.0.0","redux":"^3.7.2 || ^4.0.0","axios":"^0.18.0 || ^0.19.0"},"devDependencies":{"@testing-library/jest-dom":"^4.2.4","@testing-library/react":"^9.5.0","@testing-library/user-event":"^7.2.1","@types/jest":"^25.1.4","@types/node":"^12.12.38","@types/react":"^16.9.27","@types/react-dom":"^16.9.7","@typescript-eslint/eslint-plugin":"^2.26.0","@typescript-eslint/parser":"^2.26.0","axios":"^0.21.1","babel-eslint":"^10.0.3","cross-env":"^7.0.2","eslint":"^6.8.0","eslint-config-prettier":"^6.7.0","eslint-config-standard":"^14.1.0","eslint-config-standard-react":"^9.2.0","eslint-plugin-import":"^2.18.2","eslint-plugin-node":"^11.0.0","eslint-plugin-prettier":"^3.1.1","eslint-plugin-promise":"^4.2.1","eslint-plugin-react":"^7.17.0","eslint-plugin-standard":"^4.0.1","gh-pages":"^2.2.0","microbundle-crl":"^0.13.10","node-sass":"^4.14.1","npm-run-all":"^4.1.5","prettier":"^2.0.4","react":"^16.13.1","react-dom":"^16.13.1","react-scripts":"^3.4.1","redux":"^4.0.5","typescript":"^3.7.5"},"keywords":["react","redux","remote-data","remote-component","component","components","api","asynchronous","fetching","fetching-data","typescript","typescript-library"],"dependencies":{},"gitHead":"c1b7514e5332eafd5551e2c47751583f0ca52b3a","bugs":{"url":"https://github.com/alismael/remote-data/issues"},"homepage":"https://github.com/alismael/remote-data#readme","_id":"@alismael/remote-data@1.0.2","_npmVersion":"5.6.0","_nodeVersion":"9.5.0","_npmUser":{"name":"alismael","email":"aliismaelabdelwahab@gmail.com"},"dist":{"integrity":"sha512-ZguNxpexomVWdBLDsDnfSMQkn3+CaPWILGkdIIvBcyTOkh+GblDFkiw6khIRBGZHgfH6LzgWkW98AC1LBqBpNw==","shasum":"efd5a4064006f05ae7bfaa990ca4b2f77933526e","tarball":"https://registry.npmjs.org/@alismael/remote-data/-/remote-data-1.0.2.tgz","fileCount":24,"unpackedSize":41154,"npm-signature":"-----BEGIN PGP SIGNATURE-----\r\nVersion: OpenPGP.js v3.0.13\r\nComment: https://openpgpjs.org\r\n\r\nwsFcBAEBCAAQBQJg10ZeCRA9TVsSAnZWagAAMxsP+wf+LBO52kTQugynte8F\ny5yQl573nIg5PGwZdGjCELg6PgOK+HdSK23dg42w9LCepGF95i0rBJeH8N9C\nzQASLQf6WSMrGvv2KpUgrXnapybI84L5Nez8FH7zuw8RsqeQDO5LzmWrMaSR\nv6Wj1SJbic2SpIkdv4k0Q+d19TMEnP6T4/emhOq+KKSBws8eTpnsbxVqNTE9\nwpMhQ78m6PkTKzG/Q7cXFncVyY9DMdfDSxmlwx2M2VazkIDAT4k+DwVzg+li\nxlBxNauRQTgsgj14myO5AC6Ujo0SlI1Zbrr7/FEJxt+mciRVxYopIlh0HEWp\ntjnnSGnPmJ9kNlfXEBxm2Da8CbOSZI4/8wwNFrcXkH8CNSO7+TWvrsPhaG7B\nL9LME385SYfwpeNgEaTCnEtHoGVdOBJmBM4tCMYtwyYG8+6gf3lvv6zY/IOE\n/cdsOIbd1JQUzkqUi/d0Lfj90cyVRPPoIH8VBTEvGb13jgrFYaJW+RDjtbvQ\nj2C0yh62xU/krRYIXCwutIhRjibbSx7glrNNKcR4EqTYObqkDLq4gAurRfWc\nIByK1lXyjsvgnEVCFh3Nywzb2imNpbBtU+U/qgCUgaXjTMqvYw0dQhvrndgI\n9xC1As2sKXkvNBH6f0vDcLBX6D8JgBVXiMic6U8BFMNI7zRK9n1c4DiQanet\nbOKf\r\n=rruD\r\n-----END PGP SIGNATURE-----\r\n","signatures":[{"keyid":"SHA256:jl3bwswu80PjjokCgh0o2w5c2U4LhQAE57gj9cz1kzA","sig":"MEUCIDQMuedvJJ+3FbXrJM0mpN9lzqSMvRZE3Qb0lDkBUt70AiEArOXzNUH5oAe+m+uEvqMLvSphFoWb6XnhHS4i2K1Yzvw="}]},"directories":{},"maintainers":[{"name":"alismael","email":"aliismaelabdelwahab@gmail.com"}],"_npmOperationalInternal":{"host":"s3://npm-registry-packages","tmp":"tmp/remote-data_1.0.2_1624720989361_0.48416324872977223"},"_hasShrinkwrap":false}},"time":{"created":"2020-07-11T15:41:54.054Z","1.0.0":"2020-07-11T15:41:54.288Z","modified":"2022-04-04T13:27:46.026Z","1.0.1":"2020-10-13T07:48:35.765Z","1.0.2":"2021-06-26T15:23:09.478Z"},"maintainers":[{"name":"alismael","email":"aliismaelabdelwahab@gmail.com"}],"description":"Handle modeling, fetching, and displaying remote data in React/Redux apps","homepage":"https://github.com/alismael/remote-data#readme","keywords":["react","redux","remote-data","remote-component","component","components","api","asynchronous","fetching","fetching-data","typescript","typescript-library"],"repository":{"type":"git","url":"git+https://github.com/alismael/remote-data.git"},"author":{"name":"alismael"},"bugs":{"url":"https://github.com/alismael/remote-data/issues"},"license":"MIT","readme":"# remote-data\n\n[![npm version](https://img.shields.io/npm/v/@alismael/remote-data.svg?style=flat-square)](https://www.npmjs.org/package/@alismael/remote-data)\n\n> Handle modeling, fetching, and displaying remote data in React/Redux apps\n\n## Idea\n\nA React library aimed at modeling, fetching, and displaying remote data and the states it can be in.\n\nThis library provides:\n\n* [api](#apit-e) request wrapper based on <a href=\"https://github.com/axios/axios\">Axios</a> to make the HTTP requests\n* [fetchingReducer](#fetchingreducer) to update the store\n* [RemoteComponent](#remotecomponent) to handle displaying remote data\n\n## Dependencies\n\n### Required Peer Dependencies\n\nThese libraries are not bundled with remote-data but required at runtime:\n\n* [**React**](https://www.npmjs.com/package/react)\n* [**Redux**](https://www.npmjs.com/package/redux)\n* [**Axios**](https://www.npmjs.com/package/axios)\n\n#### Install\n\n```sh\nnpm i @alismael/remote-data\n```\n\n#### Usage\n\nPerforming a `GET` request to fetch the data\n\nactions.ts\n\n```ts\nimport { api } from 'remote-data';\nimport { Post, ErrorResponse } from '../models';\nimport { FETCH_POSTS } from './constants';\n\nconst fetchPosts = () =>\n  api<Post[], ErrorResponse>({\n    method: 'GET',\n    url: 'posts',\n    baseURL: 'https://jsonplaceholder.typicode.com/',\n    action: FETCH_POSTS,\n  });\n```\n\nAdding a reducer to update the store\n\nreducer.ts\n\n```ts\nimport { Reducer } from 'react';\nimport { combineReducers } from 'redux';\nimport { fetchingReducer, RemoteData } from 'remote-data';\nimport { Post, ErrorResponse } from '../../models';\nimport { FETCH_POSTS } from './constants';\n\nexport type PostsStore = {\n  posts: RemoteData<Post[], ErrorResponse>;\n};\n\nconst postsReducer: Reducer<PostsStore, any> = combineReducers({\n  posts: fetchingReducer<Post[], ErrorResponse>(FETCH_POSTS),\n});\n\nexport default postsReducer;\n```\n\nDisplaying your remote data\n\nPostsComponent.tsx\n\n```tsx\nconst PostsLoading = () => <>Loading posts...</>;\nconst PostsError = ({ err }: { err: ErrorResponse }) => <>{err}</>;\nconst ListPosts = ({ data }: { data: Post[] }) => <>Here you can use the fetched data</>\n\ntype PostsContainerProps = {\n  fetchPosts: () => Promise<Post[]>;\n  posts: RemoteData<Post[], ErrorResponse>;\n};\n\nconst PostsContainer = ({ fetchPosts, posts }: PostsContainerProps) => {\n  React.useEffect(() => {\n    fetchPosts();\n  }, [fetchPosts]);\n\n  return (\n    <RemoteComponent\n      remote={{ posts }}\n      loading={PostsLoading}\n      reject={({ posts }) => <PostsError error={posts.error} />}\n      success={({ posts }) => <ListPosts posts={posts.data} />}\n    />\n  );\n};\n\nconst mapStateToProps = ({ posts }: StoreState) => ({\n  posts: posts.posts,\n});\nconst mapDispatchToProps = (\n  dispatch,\n) => ({\n  fetchPosts: () => dispatch(fetchPostsAction()),\n});\nconnect(mapStateToProps, mapDispatchToProps)(PostsContainer);\n```\n\nYou can check the `example` folder for more details\n\n## api<T, E>\n\napi<T, E>(config) where T, E are the types of data and the expected error respectively\n\n```ts\nimport { api } from 'remote-data';\n\napi<Post[], ErrorResponse>({\n  method: 'GET',\n  url: 'posts',\n  baseURL: 'https://jsonplaceholder.typicode.com/',\n  action: FETCH_POSTS,\n});\n```\n\nRequest Config\n\nIn addition to axios <a href=\"https://github.com/axios/axios#request-config\">request config</a> there are **three more options**:\n\n* `action`: is the action type that will be dispatched when request state changed. If not provided no action will be dispatched.\n* `onSuccess`, `onError`: are the callbacks to be triggered for the relevant request state.\n\n## fetchingReducer\n\nfetchingReducer<T, E>(actionType) a reducer for managing the state of the remote data\n\n```ts\nimport { fetchingReducer } from 'remote-data';\n\ncombineReducers({\n  posts: fetchingReducer<Post[], ErrorResponse>(FETCH_POSTS),\n});\n```\n\n* `actionType`: it should be the same as the action passed to the [`api`](#apit-e) request wrapper\n\n## RemoteComponent\n\nHandle displaying of your remote data.\n\n```tsx\nimport { RemoteComponent } from 'remote-data';\n\n<RemoteComponent\n  remote={{ posts }}\n  loading={PostsLoading}\n  reject={({ posts }) => <PostsError error={posts.error} />}\n  success={({ posts }) => <ListPosts posts={posts.data} />}\n/>\n```\n\nOnly `remote` and `success` are required\n\n* `remote` passing your remote data here, it should be of type [RemoteData<T, E>](#remotedatat-e)\n* `loading`, `success`, and `reject` will be rendered for the relevant state\n\nYou can handle displaying multiple remote data at once with one component. [here](#handle-displaying-multiple-remote-data-with-remotecomponent-component)\n\n## RemoteData<T, E>\n\nRemoteData<T, E> where `T` is the data type and `E` is the error type respectively\n\n```ts\nenum RemoteKind {\n  NotAsked = 'NOT_ASKED',\n  Loading = 'LOADING',\n  Success = 'SUCCESS',\n  Reject = 'REJECT',\n}\n\ntype NotAsked = {\n  kind: RemoteKind.NotAsked;\n};\n\ntype Loading = {\n  kind: RemoteKind.Loading;\n};\n\ntype Success<T> = {\n  kind: RemoteKind.Success;\n  data: T;\n};\n\ntype Reject<E> = {\n  kind: RemoteKind.Reject;\n  error: E;\n};\n\ntype RemoteData<T, E> = NotAsked | Loading | Success<T> | Reject<E>;\n```\n\n## Action<T, E>\n\nAction<T, E> where `T` is the data type and `E` is the error type respectively\n\n```ts\ntype ActionType = string;\n\ntype NotAskedAction = {\n  type: ActionType;\n  kind: RemoteKind.NotAsked;\n};\n\ntype LoadingAction = {\n  type: ActionType;\n  kind: RemoteKind.Loading;\n};\n\ntype SuccessAction<T> = {\n  type: ActionType;\n  kind: RemoteKind.Success;\n  data: T;\n  headers: any;\n};\n\ntype RejectAction<E> = {\n  type: ActionType;\n  kind: RemoteKind.Reject;\n  error: E;\n  headers: any;\n};\n\ntype Action<T, E> =\n  | NotAskedAction\n  | LoadingAction\n  | SuccessAction<T>\n  | RejectAction<E>;\n```\n\n## Handle displaying multiple remote data with `RemoteComponent` component\n\n```tsx\n<RemoteComponent\n  remote={{ posts, users }}\n  loading={() => (\n    <>\n      <PostsLoading />\n      <UsersLoading />\n    </>\n  )}\n  reject={({ posts, users }) => (\n    <>\n      {users.error && <UsersError error={users.error} />}\n      {posts.error && <PostsError error={posts.error} />}\n    </>\n  )}\n  success={({ posts, users }) => (\n    <>\n      <h1 className=\"page-title\">Users</h1>\n      <ListUsers users={users.data} />\n      <h1 className=\"page-title\">Posts</h1>\n      <ListPosts posts={posts.data} />\n    </>\n  )}\n/>\n```\n\n## Create a custom reducer to manually update the store\n\nYou can create your custom reducer, here's an example:\n\n```ts\nimport { RemoteData, RemoteKind, Action } from 'remote-data';\nimport { Post, ErrorResponse } from '../../models';\nimport { FETCH_POSTS } from './constants';\n\nexport type PostsStore = {\n  posts: RemoteData<Post[], ErrorResponse>;\n};\n\nconst initialState: PostsStore = {\n  posts: {\n    kind: RemoteKind.NotAsked,\n  },\n};\n\nexport default (\n  state: PostsStore = initialState,\n  action: Action<Post[], ErrorResponse>,\n): PostsStore => {\n  if (action.type === FETCH_POSTS) {\n    switch (action.kind) {\n      case RemoteKind.Loading:\n        return {\n          ...state,\n          posts: {\n            kind: RemoteKind.Loading,\n          },\n        };\n\n      case RemoteKind.Success:\n        return {\n          ...state,\n          posts: {\n            kind: RemoteKind.Success,\n            data: action.data,\n          },\n        };\n\n      case RemoteKind.Reject:\n        return {\n          ...state,\n          posts: {\n            kind: RemoteKind.Reject,\n            error: action.error,\n          },\n        };\n\n      default:\n        return state;\n    }\n  }\n\n  return state;\n};\n```\n\n* Initialize your state\n* Verify the action type and kind\n* Update your state\n\n`action` is of type [Action<T, E>](#actiont-e)\n\n## Development\n\nTo setup and run locally\n\n1. Clone this repo with `git clone https://github.com/alismael/remote-data`\n2. Run `npm install` in the root folder\n3. Run `npm install` in the example folder\n4. run `npm start` in the root and example folders\n\n## License\n\nMIT © [alismael](https://github.com/alismael)","readmeFilename":"README.md"}