Quick Start
Purpose and Scope
This page gets a new SWR user from an empty React component to the first working data-fetching hook. The repository README frames SWR as a React Hooks library for data fetching, and the quick-start path is intentionally small: import the default hook, call it with a request key and a fetcher function, then render loading, error, and data states. The E2E site README adds the local development context for trying the library in a Next.js application, including the development-server commands and the convention that API routes are served under the application API path. Sources: README.md, e2e/site/README.md
The important mental model is that the hook does not ask the component to manage its own request lifecycle by hand. Instead, the component declares what data it needs, gives SWR a stable identifier for that request, and responds to the state that SWR returns. The README explains that SWR first returns cached data when available, sends a request to revalidate, and then updates the component with fresh data. Even in the smallest example, that stale-while-revalidate model is why the UI can be fast while still converging on current server state. Sources: README.md
Relevant Source Files
- README.md - Defines SWR as a React Hooks data-fetching library, introduces the stale-while-revalidate model, and contains the public quick-start example using the default
useSWRimport. - e2e/site/README.md - Documents how to run the repository's Next.js E2E site locally and explains where example pages and API routes live in that app.
Minimal Hook Usage
The README quick start uses the default export from the package and names it as useSWR. In a component, the hook is called with a key and a fetcher. The key is normally the URL of the API endpoint, and the fetcher is any asynchronous function that accepts that key and returns the requested data. This keeps transport details outside the hook itself: the fetcher can use the browser Fetch API, a project HTTP client, or another asynchronous data source, as long as it resolves with the data shape the component expects. Sources: README.md
import useSWR from 'swr'
function Profile() {
const { data, error, isLoading } = useSWR('/api/user', fetcher)
if (error) return <div>failed to load</div>
if (isLoading) return <div>loading...</div>
return <div>hello {data.name}!</div>
}Read the example from top to bottom as a rendering contract. Before the request finishes, the README says data is undefined and isLoading is true, so the component should render a loading branch instead of dereferencing the data object. If the fetcher rejects or returns an error condition represented as an error, the component renders the failure branch. Once the fetcher completes successfully, SWR sets the data, clears the loading state, and rerenders the component so the final branch can use the returned value. Sources: README.md
A minimal fetcher can be project-specific, but it should match the shape described by the README: it receives the key and returns data asynchronously. For a URL key, a common implementation is a small wrapper around fetch that converts the response into JSON. The quick-start snippet intentionally does not prescribe that implementation because SWR is transport and protocol agnostic. That means the same hook pattern can sit above REST endpoints, GraphQL clients, local async storage, or any other promise-returning source, while the component code still reads the same way. Sources: README.md
const fetcher = url => fetch(url).then(res => res.json())Core Primitives
The first primitive is the request key. A key is the unique identity of the request and, in the quick start, is the string path for the user API endpoint. The same key is also the value passed into the fetcher, so it connects the component declaration to the underlying request. In later SWR usage, keys also become the handle for cache entries, revalidation, and mutation, but the quick-start rule is simple: choose a stable value that identifies the data the component needs. Sources: README.md
The second primitive is the fetcher. SWR does not require a specific HTTP client and does not limit the application to a particular protocol. The README explicitly says the fetcher can be any asynchronous function, which is why the quick start treats it as a dependency supplied by the application. This division is useful in real projects because it lets teams centralize authentication headers, response validation, error normalization, or typed API clients in the fetcher while keeping the React component focused on rendering state. Sources: README.md
The third primitive is the returned state object. The README quick start names three fields: data, error, and isLoading. These fields are enough to build the initial user experience without additional local component state. Loading and error branches should generally appear before the success branch because the data field can be absent while the request is in flight. When the fetcher settles, SWR updates the appropriate fields and rerenders the component, so the render output follows the request lifecycle without manual effect wiring. Sources: README.md
Running a Local Next.js Playground
To try the quick-start pattern inside this repository, use the documented Next.js E2E site flow. The E2E site README says to run a development server with one of the supported package-manager commands, then open the local application in a browser. It also notes that editing the app page updates the page automatically, which makes the site a convenient place to experiment with hook calls, loading branches, and API routes while seeing the result immediately in the browser. Sources: e2e/site/README.md
npm run dev
# or
yarn dev
# or
pnpm devThe E2E site README identifies app/page.tsx as the page to start editing and explains that API routes can be accessed under the local API path. It also states that files in pages/api are mapped to API endpoints instead of React pages. That is directly relevant to the README quick start because the example key is an API-style path. In a Next.js playground, you can pair a component using SWR with a local API route, which keeps both sides of the example inside the same application while preserving the client/server boundary. Sources: e2e/site/README.md
Step-by-Step First Component
Start by defining or importing a fetcher that returns a promise for the data your component needs. Next, import the default hook from the package and call it during render with a stable key. Then add rendering branches in the order shown by the README: handle an error, handle the loading state, and only then render the successful data view. This order prevents accidental reads from undefined data and makes the component behavior explicit for every request phase. Sources: README.md
After the component works, verify the data path. If the key is a URL, make sure the endpoint exists and returns the shape that the success branch expects. In the sample component, the final render uses a name property on the returned data, so the endpoint should return an object with that field. If you are testing in the Next.js E2E site, the README guidance for API routes tells you where to place endpoint code and how those files map to browser-accessible paths. Sources: README.md, e2e/site/README.md
Common First Checks
If the component stays in the loading branch, first inspect the fetcher rather than the hook call. The README defines the fetcher as the asynchronous function that accepts the key and returns the data, so a fetcher that never resolves will leave the component waiting. If the component moves to the error branch, inspect the request, response handling, and any thrown exceptions. The hook is reporting the result of the fetcher, so the quickest debugging path is usually to confirm that the key is correct and the fetcher resolves with the expected value. Sources: README.md
If the success branch renders but the displayed field is missing, check the data contract between the API response and the component. The quick-start snippet assumes an object with a name field, but SWR itself does not create that shape. It passes through the data returned by the fetcher. This is a useful separation of concerns: SWR coordinates cache, loading, error, and revalidation behavior, while the application owns endpoint design and response parsing. For stronger guarantees, move next to the TypeScript and fetcher-focused pages. Sources: README.md
Next Steps
Once the first hook is working, the next useful topics are the stale-while-revalidate model, keys and serialization, global configuration, and the useSWR API reference. Those pages expand the same primitives used here into cache behavior, automatic revalidation, shared fetchers, fallback data, and typed hook usage. If you want a runnable application rather than a single component, continue with the basic examples and the server-rendering examples, which apply the same quick-start contract inside complete Next.js projects. Sources: README.md, e2e/site/README.md