{"id":13781199,"url":"https://github.com/aromalanil/react-rhino","last_synced_at":"2025-08-17T10:40:00.582Z","repository":{"id":47628376,"uuid":"343173153","full_name":"aromalanil/react-rhino","owner":"aromalanil","description":"A lightweight global state management library for React.js","archived":false,"fork":false,"pushed_at":"2021-12-08T17:27:32.000Z","size":239,"stargazers_count":26,"open_issues_count":0,"forks_count":2,"subscribers_count":1,"default_branch":"master","last_synced_at":"2025-06-11T09:08:41.348Z","etag":null,"topics":["hacktoberfest","lightweight","npm-package","react","react-hooks","react-js","react-state-management","reactjs","state","state-management"],"latest_commit_sha":null,"homepage":"https://npmjs.com/package/react-rhino","language":"TypeScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/aromalanil.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":"CONTRIBUTING.md","funding":".github/FUNDING.yml","license":"LICENSE","code_of_conduct":"CODE_OF_CONDUCT.md","threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null},"funding":{"github":null,"patreon":null,"open_collective":null,"ko_fi":"aromalanil","tidelift":null,"community_bridge":null,"liberapay":null,"issuehunt":null,"otechie":null,"custom":["https://paypal.me/aromalanil","https://www.buymeacoffee.com/aromalanil"]}},"created_at":"2021-02-28T17:51:40.000Z","updated_at":"2024-05-26T13:10:56.000Z","dependencies_parsed_at":"2022-09-06T11:11:25.714Z","dependency_job_id":null,"html_url":"https://github.com/aromalanil/react-rhino","commit_stats":null,"previous_names":[],"tags_count":5,"template":false,"template_full_name":null,"purl":"pkg:github/aromalanil/react-rhino","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/aromalanil%2Freact-rhino","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/aromalanil%2Freact-rhino/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/aromalanil%2Freact-rhino/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/aromalanil%2Freact-rhino/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/aromalanil","download_url":"https://codeload.github.com/aromalanil/react-rhino/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/aromalanil%2Freact-rhino/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":270220353,"owners_count":24547520,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-08-13T02:00:09.904Z","response_time":66,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["hacktoberfest","lightweight","npm-package","react","react-hooks","react-js","react-state-management","reactjs","state","state-management"],"created_at":"2024-08-03T18:01:23.822Z","updated_at":"2025-08-17T10:40:00.559Z","avatar_url":"https://github.com/aromalanil.png","language":"TypeScript","funding_links":["https://ko-fi.com/aromalanil","https://paypal.me/aromalanil","https://www.buymeacoffee.com/aromalanil"],"categories":["List"],"sub_categories":[],"readme":"# 🦏 React Rhino \n\n[![NPM Version](https://img.shields.io/npm/v/react-rhino)](https://www.npmjs.com/package/react-rhino)\n![ESLint Check](https://github.com/aromalanil/react-rhino/workflows/ESLint-Check/badge.svg)\n[![GitHub license](https://img.shields.io/badge/license-MIT-blue.svg)](https://github.com/aromalanil/react-rhino/blob/master/LICENSE)\n[![npm bundle size](https://img.shields.io/bundlephobia/minzip/react-rhino)](https://www.npmjs.com/package/react-rhino)\n\n[![https://nodei.co/npm/react-rhino.png?downloads=true\u0026downloadRank=true\u0026stars=true](https://nodei.co/npm/react-rhino.png?downloads=true\u0026downloadRank=true\u0026stars=true)](https://www.npmjs.com/package/react-rhino)\n\nReact Rhino is a simple yet powerful state management library for [React](https://reactjs.org/)\n\n## Installation \n\n```bash\n# If you use npm:\nnpm install react-rhino\n\n# Or if you use Yarn:\nyarn add react-rhino\n```\n## Why choose Rhino?\n\n### 🏋️‍♂️ Lightweight\nOnly **~770** bytes when Minified \u0026 Gzipped.\n\n### 🚀 Syntax you already know\nOffers a straightforward syntax similar to the built-in hooks of React.\n\n### 👷‍♂️ Easy to Extend\nAdd a new global state with just a single line of code, it's that simple.\n\n### 📐 Easy to Use\nGet started with Rhino in a short amount of time.\n\n## Online Playground\nUse the button below to play with a small demo project to help familiarize with state management using React Rhino.\n\n[![View on Codesandbox](https://codesandbox.io/static/img/play-codesandbox.svg)](https://codesandbox.io/s/react-rhino-example-svv5b)\n\n## Usage\n\nSet up React Rhino in your project using these simple steps\n\n### Step 1\nWrap your app with `RhinoProvider` and pass the store object to it\n\n\u003e Note: `store` is an object in which each entries will  become a global state. In `store`, keys will be the identifiers for each state and their corresponding value will be the initial values of that particular state.\n\n```jsx\nimport { RhinoProvider } from 'react-rhino';\n\nconst store = {\n dark_mode: true\n}\n\nfunction App() {\n  return (\n    \u003cRhinoProvider store={store}\u003e\n      \u003cCounter /\u003e\n    \u003c/RhinoProvider\u003e\n  );\n}\n```\n\n### Step 2\nConsume global state in any of your components, by using the `useRhinoState` hook as in the below example\n\n```jsx\nimport { useRhinoState } from \"react-rhino\"\n\n const DarkModeButton = () =\u003e {\n\n /* \"dark_mode\" is the key given to this state in the store */\n const [isDarkMode, setDarkMode] = useRhinoState(\"dark_mode\"); \n\n const toggleDarkMode = () =\u003e {\n   setDarkMode(currentMode =\u003e !currentMode);\n }\n\n return(\n   \u003cp\u003e{ isDarkMode ? \"Switch to Light\" : \"Switch to dark\" }\u003c/p\u003e\n   \u003cbutton onClick={toggleDarkMode}\u003eToggle\u003c/button\u003e\n );\n}\n\nexport default DarkModeButton;\n```\n\n\u003e Note : `useRhinoState` is similar to the `useState` hook of React. `useRhinoState` will also returns an array containing the state and it's updater function.\u003cbr/\u003e\u003cbr/\u003e\nThe only difference is that unlike \n`useState` hook we pass the key of the global state to `useRhinoState` hook.\n\n\n## API / Documentation\n### RhinoProvider\nComponents that use Rhino state need `RhinoProvider` to appear somewhere in the parent tree. A good place to put this is in your root component.\n\n\u003e `RhinoProvider` takes only a single prop, `store`. Each entries in `store` will be converted to a global state. \u003cbr/\u003e \u003cbr/\u003eEach key in `store` represents a global state and the values corresponding to them becomes the initial values of those states respectively.\n\n```js\nimport { RhinoProvider } from \"react-rhino\";\n\nconst store={\n   name: \"John Doe\", // Will become a global state with initial value \"John Doe\"\n   isDarkMode : true, // Will become another global state with initial value true\n}\n\nfunction App() {\n  return (\n    \u003cRhinoProvider store={store}\u003e\n      \u003cSearchBar /\u003e\n    \u003c/RhinoProvider\u003e\n  );\n}\n```\n\n### useRhinoState\nTakes key representing the state as argument and returns an array with the state value and the function to update the state.\n\n\u003e This hook is pretty similar to `useState` hook in React.\n```jsx\nconst [darkMode, setDarkMode] = useRhinoState(\"isDarkMode\");\n/* Here \"isDakMode\" is the key representing the state */\n```\n\n### useRhinoValue\nTakes key representing the state as argument and returns only the the state value.\n\u003e You can use this if your component only needs to read the state but perform no updates.\n```jsx\nconst darkMode = useRhinoValue(\"isDarkMode\");\n/* Here \"isDakMode\" is the key representing the state */\n```\n\n### useSetRhinoState\nTakes key representing the state as argument and returns the function to update the state.\n\u003e You can use this if your component only needs the updater function and not the state itself.\nHaving an updater function in the component will not trigger a re-render on the state change.\n```jsx\nconst setDarkMode = useSetRhinoState(\"isDarkMode\");\n/* Here \"isDakMode\" is the key representing the state */\n```\n\n## Some Examples\n### A Component which only read the state and not the updater function\nFor Components that only read the state values,  declare a constant inside the component and assign the constant to  a call to `useRhinoValue(\"key_to_identify_state_value\")` passing in key as an argument like:\n\n`menu_bar.js`\n```jsx\nimport { useRhinoValue } from \"react-rhino\"\n\nconst Menu = () =\u003e {\n\n /* useRhinoValue only return state value */\n const isDarkMode = useRhinoValue(\"dark_mode\"); \n\n return(\n   \u003cnav\u003e\n    {/* Other nav contents */}\n    \u003cp\u003e{`Currently it is ${isDarkMode ? \"Dark\" : \"Light\"}`}\u003c/p\u003e\n   \u003c/nav\u003e\n );\n\n export default Menu;\n}\n```\n\n### A Component which only accesses the updater function\nFor a component that only updates the state, import `useSetRhinoState` in the component file that performs update to the global state.\n\nDeclare a constant inside the component and assign the constant to a call to `useSetRhinoState(\"key_to_identify_state_value\")` passing in a  key identifying a state value as an argument.\n\n`toggle.js`\n\u003e This component will not re-render if the state `isDarkMode` changes as it only uses the updater function and not the state itself.\n```jsx\nimport { useSetRhinoState } from \"react-rhino\"\n\nconst Toggle = () =\u003e {\n\n /* useSetRhinoState only return updater function */\n const setDarkMode = useSetRhinoState(\"dark_mode\");\n\n const toggleDarkMode = () =\u003e {\n   setDarkMode(currentMode =\u003e !currentMode);\n }\n\n return \u003cbutton onClick={toggleDarkMode}\u003eToggle DarkMode\u003c/button\u003e\n\n export default Toggle;\n}\n```\n### A Component accessing multiple global state values\nAccessing multiple state values is pretty straight forward, declare constants to hold different state values and access state values by calling `useRhinoValue(\"key\")` passing a key identifying with a state value as an argument.\n\n`details.js`\n\n```jsx\nimport { useRhinoValue } from \"react-rhino\"\n\nconst Details= () =\u003e {\n  /*  \n      Separate calls to useSetRhinoState return separate state values\n      based on keys that identify with state value.\n  */\n  const userName = useRhinoValue(\"name\")\n  const addressDetails = useRhinoValue(\"addressDetails\")\n  return(\u003cdiv\u003e\n      \u003cspan\u003e{userName}\u003c/span\u003e\n  \u003c/div\u003e\n  )\n\n}\n```\n\n## Author\n[Aromal Anil](https://aromalanil.in)\n\n## License\n```\nMIT License\n\nCopyright (c) 2021 Aromal Anil\n\nPermission is hereby granted, free of charge, to any person obtaining a copy\nof this software and associated documentation files (the \"Software\"), to deal\nin the Software without restriction, including without limitation the rights\nto use, copy, modify, merge, publish, distribute, sublicense, and/or sell\ncopies of the Software, and to permit persons to whom the Software is\nfurnished to do so, subject to the following conditions:\n\nThe above copyright notice and this permission notice shall be included in all\ncopies or substantial portions of the Software.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\nIMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\nFITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE\nAUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\nLIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\nOUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE\nSOFTWARE.\n```\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Faromalanil%2Freact-rhino","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Faromalanil%2Freact-rhino","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Faromalanil%2Freact-rhino/lists"}