Наконец-то мы и добрались до того момента, когда наши усилия по созданию мощного и гибкого GraphQL API могут быть достойно оценены во фронтенд-приложениях! Сегодня мы поговорим о том, как связать наш GraphQL API с фронтендом с помощью популярного GraphQL-клиента — Apollo Client.
Выбор клиента для работы с GraphQL на фронтенде
Для взаимодействия с GraphQL API во фронтенде можно использовать различные инструменты. Однако Apollo Client — это не просто клиент для работы с GraphQL, это настоящий "швейцарский нож". Он упрощает создание запросов, управление состоянием данных и кеширование, экономя как время, так и нервы разработчиков.
Apollo Client автоматически кеширует данные, обновляя только то, что действительно изменилось, а это значительно ускоряет работу приложения. Особенно хорошо Apollo подходит для React, поскольку интегрируется с ним через удобные хуки, что упрощает взаимодействие с API. Помимо этого, у него есть множество полезных возможностей, таких как подписки, загрузка файлов и поддержка пагинации. А если вдруг возникнут вопросы, всегда можно обратиться к подробной документации, которую активно развивает сообщество.
Установка и настройка Apollo Client
Сначала убедитесь, что у вас есть React-проект. Если React ещё не установлен, создадим его с нуля. Далее мы установим Apollo Client и его зависимости.
Если у вас уже есть frontend на React, можно пропустить этот шаг. В противном случае:
npx create-react-app frontend
cd frontend
Теперь нам нужно установить библиотеки Apollo Client и GraphQL:
npm install @apollo/client graphql
Эта команда установит сам Apollo Client и библиотеку GraphQL, которая необходима для работы с запросами и мутациями.
Настройка Apollo Provider
Apollo Client использует ApolloProvider, чтобы сделать клиент доступным для всех компонентов React. Для подключения клиента давайте создадим файл ApolloProvider.js.
Добавьте в папке src новый файл ApolloProvider.js:
// src/ApolloProvider.js
import React from 'react';
import {
ApolloClient,
InMemoryCache,
ApolloProvider as Provider,
} from '@apollo/client';
const client = new ApolloClient({
uri: 'http://localhost:8000/graphql/', // Поменяйте на ваш адрес GraphQL API
cache: new InMemoryCache(),
});
export default function ApolloProvider({ children }) {
return <Provider client={client}>{children}</Provider>;
}
Мы создали Apollo Client, указав адрес GraphQL-сервера (uri) и определив кеширование через InMemoryCache. Этот кеш будет хранить данные запросов и обновлять их по мере необходимости.
Теперь подключим ApolloProvider в вашем приложении. Найдите файл src/index.js и замените содержимое на следующее:
import React from 'react';
import ReactDOM from 'react-dom';
import './index.css';
import App from './App';
import ApolloProvider from './ApolloProvider';
ReactDOM.render(
<ApolloProvider>
<App />
</ApolloProvider>,
document.getElementById('root')
);
Теперь Apollo Client готов к использованию в вашем приложении.
Создание запросов с Apollo Client
Настало время написать первый компонент, который будет выполнять запрос к нашему GraphQL API. Мы будем использовать хук useQuery от Apollo, чтобы выполнять запросы.
Допустим, у нас есть API, которое возвращает список книг (например, объект Book с полями id, title и author). Вот пример запроса на языке GraphQL:
query {
books {
id
title
author
}
}
Создадим React-компонент, который выполнит этот запрос.
Сначала импортируем функцию gql из Apollo Client и напишем запрос:
// src/queries.js
import { gql } from '@apollo/client';
export const FETCH_BOOKS_QUERY = gql`
query GetBooks {
books {
id
title
author
}
}
`;
Теперь создадим компонент BooksList, который будет выводить список книг:
// src/components/BooksList.js
import React from 'react';
import { useQuery } from '@apollo/client';
import { FETCH_BOOKS_QUERY } from '../queries';
function BooksList() {
const { loading, error, data } = useQuery(FETCH_BOOKS_QUERY);
if (loading) return <p>Загрузка...</p>;
if (error) return <p>Ошибка: {error.message}</p>;
return (
<div>
<h2>Список книг</h2>
<ul>
{data.books.map((book) => (
<li key={book.id}>
<strong>{book.title}</strong> - {book.author}
</li>
))}
</ul>
</div>
);
}
export default BooksList;
Теперь вставим компонент BooksList в App.js:
// src/App.js
import React from 'react';
import BooksList from './components/BooksList';
function App() {
return (
<div className="App">
<header className="App-header">
<h1>Моя библиотека</h1>
<BooksList />
</header>
</div>
);
}
export default App;
Запустите фронтенд-приложение командой:
npm start
И вуаля! Вы должны увидеть список книг, полученный через ваш GraphQL API.
Работа с мутациями
Запросы мы реализовали, но что делать, если нужно добавить или обновить данные? Здесь на сцену выходят мутации. Они создаются и используются аналогично запросам.
Добавим мутацию, которая будет добавлять новую книгу:
// src/mutations.js
import { gql } from '@apollo/client';
export const ADD_BOOK_MUTATION = gql`
mutation AddBook($title: String!, $author: String!) {
addBook(title: $title, author: $author) {
id
title
author
}
}
`;
Создадим компонент с формой для добавления новой книги:
// src/components/AddBookForm.js
import React, { useState } from 'react';
import { useMutation } from '@apollo/client';
import { ADD_BOOK_MUTATION } from '../mutations';
import { FETCH_BOOKS_QUERY } from '../queries'; // Чтобы обновить список книг после добавления
function AddBookForm() {
const [title, setTitle] = useState('');
const [author, setAuthor] = useState('');
const [addBook] = useMutation(ADD_BOOK_MUTATION, {
variables: { title, author },
refetchQueries: [{ query: FETCH_BOOKS_QUERY }], // Обновляем список книг после добавления
});
const handleSubmit = (e) => {
e.preventDefault();
addBook();
};
return (
<<orm onSubmit={handleSubmit}>
<h2>Добавить книгу</h2>
<input
type="text"
placeholder="Название"
value={title}
onChange={(e) => setTitle(e.target.value)}
/>
<input
type="text"
placeholder="Автор"
value={author}
onChange={(e) => setAuthor(e.target.value)}
/>
<button type="submit">Добавить</button>
</orm>
);
}
export default AddBookForm;
Добавьте этот компонент в ваш App.js или любой другой файл:
import AddBookForm from './components/AddBookForm';
// ...
<AddBookForm />
// ...
Теперь вы можете добавлять книги и моментально видеть обновлённый список.
Управление состоянием и кеширование
Apollo Client автоматически кеширует запросы, но вы также можете управлять кешем вручную. Например, если вы добавили новую книгу, вместо повторного выполнения запроса можно обновить кеш:
const [addBook] = useMutation(ADD_BOOK_MUTATION, {
update(cache, { data: { addBook } }) {
const { books } = cache.readQuery({ query: FETCH_BOOKS_QUERY });
cache.writeQuery({
query: FETCH_BOOKS_QUERY,
data: { books: [...books, addBook] },
});
},
});
Это позволяет избежать лишних запросов и сделать приложение более отзывчивым.
Вот так, шаг за шагом, мы интегрировали наш GraphQL API с фронтендом на React, используя Apollo Client. Теперь вы знаете, как выполнять запросы, мутации и управлять состоянием данных. Осталось только применить всё это в реальном проекте и собрать кучу лайков от пользователей! 🚀
ПЕРЕЙДИТЕ В ПОЛНУЮ ВЕРСИЮ