Endpoint-Guide/Невеличкий гайд по http сервісу та requestʼах.md

126 lines
6.0 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

### Пару важливих речей:
- Метод = функція
- Класс != тип - в TS є такі штуки як `AxiosResponse<IResponse<T>, any>` і потрібно розуміти що ці штуки працюють зовсім по другому. Навіть якщо я десь забув поправити - це важливо памʼятати
- any = unknown - формально мені б любий Senior Typescript девелопер язика за таке відірвав, але в цілому тут воно має різницю тільки в тому що при використанні того чи іншого ESlint видає різні помилки які треба виправляти. Це typescript, розслабся і получай задоволення
загальний перелік інструментів та ліб:
- tanstack query
- axios
піду з кінця:
коли ти хочеш відправити реквест на сервак, чи то Get чи то Post, звичайно це робиться через створений hook:
```ts
import { useQuery } from "@tanstack/react-query";
import { gameService } from "@/shared/services/game.service";
import { transformApiDataToGames } from "../components/gamesSlider/gamesSlider.utils";
export const useGetGames = () => {
const query = useQuery({
queryKey: ["games"],
queryFn: gameService.getGames,
});
const games =
query.data && query.data.length > 0
? transformApiDataToGames(query.data)
: [];
return { games, ...query };
};
```
тут можна побачити декілька речей:
- хук використовує tanstack query для реквесту
- танстак використовує допоміжну функцію класу GameService визначену в папці shared/services/
- Після отримання даних, воно перетворюється на локальний класс Game, достатньо незручний спосіб, краще його не використовувати, але в цьому випадку було необхідно
тепер як видно по цим речам, нам треба допоможна сервісна функція, яка використовує не просто fetch(), а повноцінний написаний Діаною http service:
```ts
import { HttpService } from "./http.service";
import { axiosClient } from "./axios-client";
import { IGameApiResponse } from "../types/game.types";
export class GameService extends HttpService {
getGames = async () => {
const response = await this.get<IGameApiResponse[]>(`rpg-events`);
return response;
};
}
export const gameService = new GameService(axiosClient);
```
тут можна побачити що достає з сервака цей реквест, і що воно привʼязана до клієнта аксіоса, який і дозволяє використовувати http протокол.
подивившись ближче, можна побачити що в файлі https.service.ts є імплементація axiosClient - НЕ ДИВИСЬ НА НЕЇ - це дефолт, і він в нашому випадку на самий крайній випадок, справжня імплементація axiosClient яка використовується ось тут:
```ts
export const gameService = new GameService(axiosClient);
```
виходить з файлу axios-client.ts (я потратив не одну годину шукаючи і розбираючись що і де)
Отже, axiosClient є імплементацією яка повністю повинна замінити fetch(), та з досвіду - працює набагато краще
Те що найголовніше для фетчингу ігор є в цій функції get:
```ts
public async get<T>(
url: string,
config?: IHttpConfig,
): Promise<AxiosResponse<IResponse<T>, any>> {
const response = await this.axiosInstance.get<IResponse<T>>(
url,
config as AxiosRequestConfig,
);
return response;
}
```
звідси треба розуміти тільки те що `Promise<AxiosResponse<IResponse<T>, any>>` це тип, який проходить через ще один шар, що є в класі HttpService.
```ts
public async get<T>(url: string, config?: IHttpConfig): Promise<T> {
return this.fetchingService
.get<AxiosResponse<IResponse<T>, unknown>>(this.getFullApiUrl(url), {
...config,
headers: {
...config?.headers,
...this.populateContentTypeHeaderConfig(),
},
})
.then((result) => {
this.checkResponseStatus(result);
return result.data as T;
});
}
// допоміжна функція для знаходження повного url
// працює дивно коли в url є localhost, але якщо вписати в NEXT_PUBLIC_BACKEND_URL=https://inrium.org.ua/api то буде працювати бездоганно
private getFullApiUrl(url: string): string {
return `${this.baseUrl}/${url}`;
}
```
ось це і є та самий метод який є тут, та який тобі і вертає T напряму звідси:
```ts
// rpg-events - частина повної url: http[s]://[NEXT_PUBLIC_BACKEND_URL | BASE_URL]/api/rpg-events.
const response = await this.get<IGameApiResponse[]>(`rpg-events`);
return response
```
тому response в цьому випадку має тип `IGameApiResponse[]`.
В загальному це виглядає так:
`request by hook -> http.service -> axios-client`
axios-client фетчить потрібні дані з сервака, і якщо помилок немає то передає на `const response`
# Не бійся задавати найпростіші та найтупіші питання, відповім на все