UNPKG

elhala-query

Version:

A lightweight, educational implementation of React Query concepts with Suspense support.

168 lines (122 loc) 4.1 kB
# elhala-query 📦 A lightweight, educational implementation of React Query concepts with Suspense support. > 🧠 "El Hala" (الحالة) means _"state"_ in Arabic. ## Educational Purpose **elhala-query** is a minimal, beginner-friendly clone of React Query, built **strictly for educational purposes**. This project demonstrates core data fetching concepts including Suspense integration and cache management. ⚠️ **IMPORTANT**: Not for production use. Missing production-grade optimizations and extensive testing. ## Keywords `react`, `query`, `suspense`, `data-fetching`, `state-management`, `error-boundaries`, `educational`, `react-query`, `hooks`, `cache` ## Learning Goals Learn through code: - Query caching mechanisms - Suspense integration patterns - Error Boundary integration - State management for async operations - Refetch/Stale-while-revalidate patterns - Core React Query concepts simplified ## Features - Traditional loading/error states - Suspense mode support - Error Boundary integration - Automatic cache garbage collection - Stale-while-revalidate pattern - Manual refetching - Query deduplication ## Basic Usage ### Traditional Loading States ```jsx import { useQuery } from "elhala-query"; function UserProfile({ userId }) { const { data, isLoading, error, refetch } = useQuery(["user", userId], () => fetch(`/api/users/${userId}`).then((res) => res.json()) ); if (isLoading) return <div>Loading...</div>; if (error) return <div>Error: {error.message}</div>; return ( <div> <h1>{data.name}</h1> <button onClick={refetch}>Refresh</button> </div> ); } ``` ### Suspense Mode ```jsx import { useSuspenseQuery } from "elhala-query"; import { Suspense } from "react"; import ErrorBoundary from "./ErrorBoundary"; function Profile() { const { data, refetch } = useSuspenseQuery(["profile"], () => fetch("/api/profile").then((res) => res.json()) ); return ( <div> <h1>{data.name}</h1> <button onClick={refetch}>Refresh</button> </div> ); } function App() { return ( <ErrorBoundary fallback={<div>Error loading profile!</div>}> <Suspense fallback={<div>Loading profile...</div>}> <Profile /> </Suspense> </ErrorBoundary> ); } ``` ## Mutation API ### `useMutation` Manage side-effects with full lifecycle tracking: ```jsx import { useMutation } from "elhala-query"; function AddTodo() { const { mutate, isLoading, isError, error } = useMutation((newTodo) => fetch("/api/todos", { method: "POST", body: JSON.stringify(newTodo), }) ); const handleSubmit = (e) => { e.preventDefault(); mutate({ title: e.target.title.value }); }; return ( <form onSubmit={handleSubmit}> <input name="title" /> <button type="submit" disabled={isLoading}> {isLoading ? "Adding..." : "Add Todo"} </button> {isError && <div>Error: {error.message}</div>} </form> ); } ``` ## Key Concepts Demonstrated ### **Suspense Integration** - Promise throwing/reconciliation - Suspense/Error Boundary coordination - Re-suspension on refetch/stale data ### **Cache Management** - Query deduplication - Stale-time configuration - Cache garbage collection ### **State Transitions** - Loading/error/success states - Background refetch indicators - Optimistic updates pattern ## For Learners **Recommended learning path:** 1. Study the `createQuery` cache implementation 2. Examine `useSuspenseQuery` Suspense integration 3. Explore `QueryObserver` state management 4. Implement a new feature (e.g., optimistic updates) 5. Compare with React Query's production implementation ## Production Alternatives While elhala-query demonstrates Suspense patterns, consider these for production: - [TanStack Query (React Query)](https://tanstack.com/query/) - [SWR](https://swr.vercel.app/) - [RTK Query](https://redux-toolkit.js.org/rtk-query/overview) ## Contribution This project is maintained for educational purposes. Contributions through issues/pull requests are welcome for educational improvements.