Swr: Top level data shared to children components

Created on 13 May 2020  路  3Comments  路  Source: vercel/swr

Hey, I'm using swr to load data at the top level since I only update the data every X hours and there are only 2 endpoints to request, so I placed it on a container component that looks as follow

```typescript
const DataLoader: React.FC = ({ children }: DataLoaderProps) => {
const { i18n } = useTranslation();
const language = i18n.language;

const categories = useSwr(endpoints.CATEGORY + language, api.category.getAll);
const points = useSwr(endpoints.POINT + language, api.point.getAll);

return <>{children};
};
````

Categories is an array of items and same applies for the points, my question is, what would be the best way to use this data on children components?
The first idea that came to my mind was using React context, but I'm not sure if that would be efficient, having duplicated data in memory, other option could be using the cache from swr, but I don't feel very confident about it because, if I have a page for category "Y" I would have to fetch all data from cache and filter the correct category.
For example:
```typescript
const categoryY = cache
.get(endpoints.CATEGORY + language)
.filter((category) => category.id === 'Y');
````

Another downside would be that after the data being refreshed by the refreshInterval I wouldn't see the updates.
This is more of a question than an issue so feel free to close it if you believe it makes sense :)

Most helpful comment

@tiagocorreiaalmeida would that be possible that creating 2 hooks for consuming categories and points, and then you use them in the children components?

Example

const useCategories = (language) => {
  return useSwr(endpoints.CATEGORY + language, api.category.getAll);
};

const usePoints = (language) => {
  return useSwr(endpoints.POINT + language, api.point.getAll);
};

in the children components where you need to consume the data

const { i18n } = useTranslation();
const language = i18n.language;

const points = usePoints(language);
const yCategories = useCategories(language).filter((category) => category.id === 'Y')

All 3 comments

@tiagocorreiaalmeida would that be possible that creating 2 hooks for consuming categories and points, and then you use them in the children components?

Example

const useCategories = (language) => {
  return useSwr(endpoints.CATEGORY + language, api.category.getAll);
};

const usePoints = (language) => {
  return useSwr(endpoints.POINT + language, api.point.getAll);
};

in the children components where you need to consume the data

const { i18n } = useTranslation();
const language = i18n.language;

const points = usePoints(language);
const yCategories = useCategories(language).filter((category) => category.id === 'Y')

That works for sure @huozhi, I can also create a specific hook to pick right away the correct category was just trying to figure out if this was a good way and seems like it is, thanks for your idea and time

@huozhi

import useSwr, { responseInterface } from 'swr';
import { useTranslation } from 'react-i18next';

import api from 'services/api';
import { Categories, Points, Category, Point } from 'services/api/schemas';
import endpoints from 'services/api/endpoints';

const usePoints = (): responseInterface<Points, unknown> => {
  const { i18n } = useTranslation();
  const language = i18n.language;

  return useSwr(endpoints.POINT + language, api.point.getAll);
};

const useCategories = (): responseInterface<Categories, unknown> => {
  const { i18n } = useTranslation();
  const language = i18n.language;

  return useSwr(endpoints.CATEGORY + language, api.category.getAll);
};

const useCategory = (categoryId: number): Category | undefined => {
  return useCategories().data?.items.find((item) => (item.id === categoryId));
};

const usePoint = (pointId: number): Point | undefined => {
  return usePoints().data?.items.find((item) => (item.id === pointId));
};

export { useCategories, useCategory, usePoint, usePoints };

Thanks once again I believe this can be closed

Was this page helpful?
0 / 5 - 0 ratings

Related issues

nainardev picture nainardev  路  4Comments

polc picture polc  路  3Comments

loveholly picture loveholly  路  3Comments

bcomnes picture bcomnes  路  3Comments

bywo picture bywo  路  4Comments