{"id":28965800,"url":"https://github.com/umarsiddique010/use-http-request-hook","last_synced_at":"2026-01-20T16:58:47.097Z","repository":{"id":300044265,"uuid":"1005059753","full_name":"umarSiddique010/use-http-request-hook","owner":"umarSiddique010","description":null,"archived":false,"fork":false,"pushed_at":"2025-06-19T16:18:03.000Z","size":0,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"main","last_synced_at":"2025-06-19T16:19:59.326Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/umarSiddique010.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null}},"created_at":"2025-06-19T15:46:41.000Z","updated_at":"2025-06-19T16:18:06.000Z","dependencies_parsed_at":"2025-06-19T16:20:03.676Z","dependency_job_id":"59e10c71-2bb6-46c6-8997-ba58e69a52b5","html_url":"https://github.com/umarSiddique010/use-http-request-hook","commit_stats":null,"previous_names":["umarsiddique010/use-http-request-hook"],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/umarSiddique010/use-http-request-hook","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/umarSiddique010%2Fuse-http-request-hook","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/umarSiddique010%2Fuse-http-request-hook/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/umarSiddique010%2Fuse-http-request-hook/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/umarSiddique010%2Fuse-http-request-hook/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/umarSiddique010","download_url":"https://codeload.github.com/umarSiddique010/use-http-request-hook/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/umarSiddique010%2Fuse-http-request-hook/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":261624971,"owners_count":23186121,"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","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":[],"created_at":"2025-06-24T07:09:37.541Z","updated_at":"2026-01-20T16:58:47.090Z","avatar_url":"https://github.com/umarSiddique010.png","language":"JavaScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# useHttpRequest\n\nA lightweight, production-ready React hook for making HTTP requests — with:\n\n- ✅ Built-in **GET request caching**\n- ✅ **Waterfall protection** for shared concurrent requests\n- ✅ Native **AbortController** handling\n- ✅ Optional **debounce** delay\n- ✅ Easy **refetch** and **manual cache invalidation**\n- ✅ Zero dependencies — just `fetch` and idiomatic React\n\n---\n\n## Why Use This Hook?\n\n\u003e No more boilerplate, stale fetches, or duplicate network calls.\n\n`useHttpRequest` is for React developers who want:\n- Clean async logic without `useEffect` gymnastics\n- Reliable loading/error/data state without manual tracking\n- Built-in **caching** and **request deduplication** (waterfall protection)\n- Auto-abort behavior to prevent memory leaks\n- Full support for `GET`, `POST`, `PUT`, `DELETE`, and custom configs\n\n**Perfect for:**\n- Fetching data on mount\n- Debounced APIs (e.g., search/autocomplete)\n- Avoiding redundant GET calls in multiple components\n- Keeping UI state clean, responsive, and React-idiomatic\n\n---\n\n## What Is This?\n\n`useHttpRequest()` is a custom React hook that simplifies `fetch()` logic inside functional components.\n\nIt handles:\n- What to fetch (`url`)\n- How to fetch (method, headers, body)\n- When to fetch (with debounce and cleanup)\n- What to do with the result (`data`, `error`, `isLoading`)\n\nYou use it like this:\n\n```js\nconst { data, error, isLoading, refetch } = useHttpRequest(url, options);\n```\n\n---\n\n## Installation\n\n```bash\nnpm install @mdus/use-http-request-hook\n# or\nyarn add @mdus/use-http-request-hook\n```\n\n---\n\n## API Reference\n\n### What It Expects\n\n| Argument  | Type     | Required | Description                                 |\n| --------- | -------- | -------- | ------------------------------------------- |\n| `url`     | `string` | ✅ Yes    | The URL or endpoint to fetch data from      |\n| `options` | `object` | ❌ No     | An optional object to configure the request |\n\n### What Goes Inside `options`\n\n| Option     | Type     | Default | Description                                               |\n| ---------- | -------- | ------- | --------------------------------------------------------- |\n| `method`   | `string` | `\"GET\"` | HTTP method (`\"GET\"`, `\"POST\"`, `\"PUT\"`, `\"DELETE\"` etc.) |\n| `headers`  | `object` | `{}`    | Any custom headers (`Content-Type`, auth tokens, etc.)    |\n| `body`     | `object` | `null`  | Payload for non-GET requests (automatically stringified)  |\n| `debounce` | `number` | `0`     | Delay in milliseconds before the request is sent          |\n\n### What It Returns\n\n| Key         | Type       | Description                                          |\n| ----------- | ---------- | ---------------------------------------------------- |\n| `data`      | `any`      | The JSON response from the API (or `null` initially) |\n| `isLoading` | `boolean`  | `true` while request is in progress                  |\n| `error`     | `string`   | Error message if something goes wrong                |\n| `refetch`   | `function` | Manually re-trigger the request                      |\n\n---\n\n## Examples\n\n### 1. Simple GET Request\n\n```jsx\nimport useHttpRequest from \"@mdus/use-http-request-hook\";\n\nfunction Products() {\n  const { data, isLoading, error } = useHttpRequest(\"https://fakestoreapi.com/products\");\n\n  if (isLoading) return \u003cp\u003eLoading...\u003c/p\u003e;\n  if (error) return \u003cp\u003eError: {error}\u003c/p\u003e;\n\n  return (\n    \u003cul\u003e\n      {data?.map((item) =\u003e (\n        \u003cli key={item.id}\u003e{item.title}\u003c/li\u003e\n      ))}\n    \u003c/ul\u003e\n  );\n}\n```\n\n### 2. POST Request with JSON Body\n\n```jsx\nconst { data, error, isLoading } = useHttpRequest(\"https://api.example.com/users\", {\n  method: \"POST\",\n  headers: {\n    \"Content-Type\": \"application/json\",\n  },\n  body: {\n    name: \"Alice\",\n    email: \"alice@example.com\"\n  }\n});\n```\n\n### 3. Debounced GET Request (e.g., Search Input)\n\n```jsx\nconst { data, isLoading } = useHttpRequest(`https://api.com/search?q=${query}`, {\n  debounce: 500 // Waits 500ms after typing stops\n});\n```\n\n### 4. Manual Refetch\n\n```jsx\nconst { data, refetch } = useHttpRequest(\"https://api.com/stats\");\n\n\u003cbutton onClick={refetch}\u003eRefresh Data\u003c/button\u003e\n```\n\n---\n\n## Advanced Features\n\n### GET Caching\n\n* Only `GET` requests are cached by default\n* Cached in memory (not persisted to disk)\n* Avoids repeat requests during a session\n\n```js\n// Will use cache if already fetched:\nuseHttpRequest(\"https://api.com/items\");\n```\n\n### Waterfall Protection\n\nMultiple components requesting the **same GET URL** won't duplicate the request:\n\n```jsx\n// Component A\nuseHttpRequest(\"https://api.com/profile\");\n\n// Component B  \nuseHttpRequest(\"https://api.com/profile\");\n\n// ✅ Only one fetch will actually run — both use same in-flight promise\n```\n\n### Manual Cache Control\n\n```js\nimport { clearCache, invalidateURL } from \"@mdus/use-http-request-hook\";\n\nclearCache(); // Wipe all cached GET responses\ninvalidateURL(\"https://api.com/products\"); // Clear just one\n```\n\n---\n\n## How It Works (Beginner-Friendly Flow)\n\n1. You call `useHttpRequest(url, options)`\n2. The hook checks if this is a `GET` request and already cached\n3. If not cached, it creates a `fetch()` request with `AbortController`\n4. While the request is in progress, `isLoading` is `true`\n5. If successful, `data` is filled and cached (for `GET` only)\n6. If there's an error, it shows up in `error`\n7. If component unmounts or URL changes, the request is safely aborted\n\n### Auto Cleanup\n\n* Cancels in-progress requests if:\n  * Component unmounts\n  * URL or `options` change\n* Prevents memory leaks or setting state on an unmounted component\n\n---\n\n## How It Works Internally\n\n* Uses native `fetch()` with `AbortController` for safety\n* `GET` responses cached in a `Map` (session memory)\n* In-flight GET requests tracked in another `Map` to prevent waterfall issues\n* Uses `setTimeout` for debouncing and cleans up on unmount\n* React `useRef`, `useCallback`, and `useMemo` ensure stability across renders\n\n---\n\n## File Structure\n\n```\nuse-http-request-hook/\n├── src/\n│   └── useHttpRequest.js\n├── dist/\n│   └── index.js\n├── package.json\n└── README.md\n```\n\n---\n\n## Author\n\n**Md Umar Siddique**\n\n* GitHub: [@umarSiddique010](https://github.com/umarSiddique010)\n* LinkedIn: [md-umar-siddique](https://linkedin.com/in/md-umar-siddique)\n* X / Twitter: [@umarSiddique010](https://x.com/umarSiddique010)\n* Dev.to: [@umarSiddique010](https://dev.to/umarsiddique010)\n\n---\n\n## License\n\nMIT © 2025 Md Umar Siddique\n\n---\n\n## Final Note\n\nThis hook is designed to solve **real problems** React developers face every day — while staying small, composable, and dependency-free. It's a reflection of production-level thinking: eliminating duplication, managing edge cases, and creating a smoother dev experience.\n\nIf it helps you, feel free to star, use, and share.","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fumarsiddique010%2Fuse-http-request-hook","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fumarsiddique010%2Fuse-http-request-hook","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fumarsiddique010%2Fuse-http-request-hook/lists"}