Коротка відповідь
seniorGraphQL — це специфікація запитів, що дозволяє клієнту отримувати саме ті дані, які йому потрібні. Він працює через один endpoint, де клієнт описує структуру відповіді у вигляді схеми типів. Сервер обробляє запит, виконує резолвери і повертає JSON‑об’єкт, що відповідає запитаній схемі.
Повне пояснення
Що це і навіщо
GraphQL — декларативна мова запитів, розроблена Meta (Facebook). Вона замінює традиційний REST‑API, дозволяючи клієнту отримувати лише потрібні поля і вкладені об’єкти, що зменшує кількість мережевих запитів.
Ключові принципи
- Schema: опис типів, полів і взаємозв’язків. Сервер валідує запити за схемою.
- Query / Mutation / Subscription: три типи операцій. Query читає, Mutation змінює стан, Subscription підписується на події.
- Resolvers: функції, що повертають дані для конкретного поля. Вони можуть викликати БД, зовнішні API або кеш.
Як це працює
Клієнт надсилає GraphQL‑запит у форматі JSON або тексту. Сервер парсить його, перевіряє на відповідність схемі, а потім виконує резолвери послідовно або паралельно. Результат повертається у вигляді JSON‑об’єкта, що точно відповідає запитаній структурі.
Практика й реалізація
- Node.js:
apollo-server,graphql-yoga. Приклад:
const { ApolloServer, gql } = require('apollo-server');
const typeDefs = gql`type Query{hello: String}`;
const resolvers = { Query:{ hello: () => 'world' } };
new ApolloServer({ typeDefs, resolvers }).listen();
- React:
@apollo/clientз хукомuseQuery.
const { data } = useQuery(gql`query{ user{id,name} }`);
- Prisma: інтегрується як резолвер, що викликає
prisma.user.findMany().
Тестування
- Jest +
graphql-requestдля інтеграційних тестів.
import { request } from 'graphql-request';
test('fetch user', async () => {
const data = await request(url, `{ user{id} }`);
expect(data.user).toBeDefined();
});
Оптимізація запитів
- Batching:
DataLoaderоб’єднує кілька запитів до БД. - Caching: Apollo Client має вбудований кеш, а сервер може використовувати
@cacheControl. - Pagination: Relay‑стиль (
first,after) або offset‑style.
Безпека
- Валідація: GraphQL самостійно перевіряє типи, але слід обмежити глибину запитів (
depthLimit). - Authorization: контекстуальний
authу резолвері. - Rate limiting: застосовувати на рівні HTTP‑серверу.
Особливості в контексті ORM
- Prisma: генерує типи TypeScript, що відповідають GraphQL‑схемі.
- TypeORM: можна створювати резолвери, що працюють з
EntityManager. - Mongoose: схеми MongoDB можна конвертувати у GraphQL‑типи за допомогою
type-graphql.
Часті помилки
- Надмірна глибина запитів →
depthLimit. - Відсутність кешу → повільні запити.
- Неправильна схема → runtime‑помилки.
- Синхронні резолвери → блокують event loop.
- Неправильне використання
@include/@skip→ непотрібні поля. - Відсутність типізації → труднощі в розробці.
- Неправильна обробка помилок → неясні відповіді клієнту.
- Перевантаження сервера → використання
DataLoaderі кешу.
Cheatsheet
- Query:
{ users { id, name } } - Mutation:
mutation{ createUser(name:"A") { id } } - Subscription:
subscription{ newMessage { text } }