Skip to content

Commit

Permalink
Merge pull request #3963 from reduxjs/rtkq-without-hooks
Browse files Browse the repository at this point in the history
  • Loading branch information
markerikson committed Dec 8, 2023
2 parents 70c1c5c + 61c54b2 commit 167ba5d
Showing 1 changed file with 26 additions and 7 deletions.
33 changes: 26 additions & 7 deletions docs/rtk-query/usage/usage-without-react-hooks.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -23,24 +23,26 @@ Cache subscriptions are used to tell RTK Query that it needs to fetch data for a
With React hooks, this behavior is instead handled within [`useQuery`](../api/created-api/hooks.mdx#usequery), [`useQuerySubscription`](../api/created-api/hooks.mdx#usequerysubscription), [`useLazyQuery`](../api/created-api/hooks.mdx#uselazyquery), and [`useLazyQuerySubscription`](../api/created-api/hooks.mdx#uselazyquerysubscription).

```ts title="Subscribing to cached data" no-transpile
const promise = dispatch(api.endpoints.getPosts.initiate())
const { refetch } = promise
// interact with the cache in the same way as you would with a useFetch...() hook
const {data, refetch, isLoading, isSuccess, /*...*/} = dispatch(api.endpoints.getPosts.initiate())
const { data, isLoading, isSuccess /*...*/ } = await promise
```

## Removing a subscription

Removing a cache subscription is necessary for RTK Query to identify that cached data is no longer required. This allows RTK Query to clean up and remove old cache data.

The result of dispatching the [`initiate`](../api/created-api/endpoints.mdx#initiate) thunk action creator of a query endpoint is an object with an `unsubscribe` property. This property is a function that when called, will remove the corresponding cache subscription.
The result of dispatching the [`initiate`](../api/created-api/endpoints.mdx#initiate) thunk action creator of a query endpoint is a Promise with an `unsubscribe` property. This property is a function that when called, will remove the corresponding cache subscription.

With React hooks, this behavior is instead handled within [`useQuery`](../api/created-api/hooks.mdx#usequery), [`useQuerySubscription`](../api/created-api/hooks.mdx#usequerysubscription), [`useLazyQuery`](../api/created-api/hooks.mdx#uselazyquery), and [`useLazyQuerySubscription`](../api/created-api/hooks.mdx#uselazyquerysubscription).

```ts title="Unsubscribing from cached data" no-transpile
// Adding a cache subscription
const result = dispatch(api.endpoints.getPosts.initiate())
const promise = dispatch(api.endpoints.getPosts.initiate())

// Removing the corresponding cache subscription
result.unsubscribe()
promise.unsubscribe()
```

## Accessing cached data & request status
Expand All @@ -49,18 +51,35 @@ Accessing cache data and request status information can be performed using the `

:::caution

The `endpoint.select()` function creates a _new_ selector instance - it isn't the actual selector function itself!
The `endpoint.select(arg)` function creates a _new_ selector instance - it isn't the actual selector function itself!

:::

With React hooks, this behaviour is instead handled within [`useQuery`](../api/created-api/hooks.mdx#usequery), [`useQueryState`](../api/created-api/hooks.mdx#usequerystate), and [`useLazyQuery`](../api/created-api/hooks.mdx#uselazyquery).

```ts title="Accessing cached data & request status" no-transpile
const result = api.endpoints.getPosts.select()(state)
const { data, status, error } = result
const { data, isSuccess, isError, error } = result
```

Note that unlike the auto-generated query hooks, derived booleans such as `isLoading`, `isFetching`, `isSuccess` are not available here. The raw `status` enum is provided instead.
Note that unlike with the auto-generated hooks, there is no `isFetching` flag, and the `isLoading` flag will be true if the status is pending, regardless of if there is already data.

### Memoization

Because the `endpoint.select(arg)` function returns a new selector each time it's called, and because this instance itself is memoized, it can be desirable to memoize the creation of a selector (for example, to then use that memoized instance in another selector). This can be done with `createSelector`:

```ts title="Creating a memoized selector creator" no-transpile
const createGetPostSelector = createSelector(
(id: string) => id,
(id) => api.endpoints.getPost.select(id)
)

const selectGetPostError = createSelector(
(state: RootState) => state,
(state: RootState, id: string) => createGetPostSelector(id),
(state, selectGetPost) => selectGetPost(state).error
)
```

## Performing mutations

Expand Down

0 comments on commit 167ba5d

Please sign in to comment.