← Назад к вопросам

Приведи пример глобального хранилища

1.7 Middle🔥 141 комментариев
#JavaScript Core

Комментарии (1)

🐱
deepseek-v3.2PrepBro AI6 апр. 2026 г.(ред.)

Ответ сгенерирован нейросетью и может содержать ошибки

Пример глобального хранилища в React с использованием Redux

В современной фронтенд-разработке глобальное хранилище (state management) — это ключевой паттерн для управления состоянием приложения, которое должно быть доступно из многих компонентов. Один из самых популярных инструментов для этого — Redux. Я продемонстрирую полный пример настройки Redux в React-приложении для управления состоянием пользователя.

Архитектура примера

Пример включает:

  • Store (хранилище) — централизованное состояние.
  • Actions (действия) — объекты, описывающие что произошло.
  • Reducers (редюсеры) — чистые функции, обновляющие состояние.
  • React-компоненты — для отображения и взаимодействия.

1. Настройка хранилища (Store)

Сначала создадим хранилище с помощью configureStore из Redux Toolkit (современный подход):

// store.js
import { configureStore } from '@reduxjs/toolkit';
import userReducer from './features/user/userSlice';

export const store = configureStore({
  reducer: {
    user: userReducer,
  },
});

2. Создание слайса (Slice) для состояния пользователя

Redux Toolkit использует слайсы для объединения действий и редюсера:

// features/user/userSlice.js
import { createSlice } from '@reduxjs/toolkit';

const userSlice = createSlice({
  name: 'user',
  initialState: {
    name: '',
    email: '',
    isLoggedIn: false,
  },
  reducers: {
    login: (state, action) => {
      state.name = action.payload.name;
      state.email = action.payload.email;
      state.isLoggedIn = true;
    },
    logout: (state) => {
      state.name = '';
      state.email = '';
      state.isLoggedIn = false;
    },
    updateProfile: (state, action) => {
      state.name = action.payload.name || state.name;
    },
  },
});

export const { login, logout, updateProfile } = userSlice.actions;
export default userSlice.reducer;

3. Подключение хранилища к React-приложению

Обернём приложение в Provider из react-redux:

// index.js
import React from 'react';
import ReactDOM from 'react-dom';
import { Provider } from 'react-redux';
import { store } from './store';
import App from './App';

ReactDOM.render(
  <Provider store={store}>
    <App />
  </Provider>,
  document.getElementById('root')
);

4. Использование в компонентах

Пример компонента, который использует useSelector для чтения и useDispatch для обновления состояния:

// components/UserProfile.js
import React from 'react';
import { useSelector, useDispatch } from 'react-redux';
import { logout, updateProfile } from '../features/user/userSlice';

const UserProfile = () => {
  const user = useSelector((state) => state.user);
  const dispatch = useDispatch();

  const handleLogout = () => {
    dispatch(logout());
  };

  const handleUpdate = () => {
    dispatch(updateProfile({ name: 'Алексей' }));
  };

  return (
    <div>
      {user.isLoggedIn ? (
        <div>
          <h2>Профиль пользователя</h2>
          <p><strong>Имя:</strong> {user.name}</p>
          <p><strong>Email:</strong> {user.email}</p>
          <button onClick={handleUpdate}>Обновить имя</button>
          <button onClick={handleLogout}>Выйти</button>
        </div>
      ) : (
        <p>Пожалуйста, войдите в систему.</p>
      )}
    </div>
  );
};

export default UserProfile;

5. Логин компонента

Компонент для входа, который изменяет глобальное состояние:

// components/Login.js
import React, { useState } from 'react';
import { useDispatch } from 'react-redux';
import { login } from '../features/user/userSlice';

const Login = () => {
  const [name, setName] = useState('');
  const [email, setEmail] = useState('');
  const dispatch = useDispatch();

  const handleSubmit = (e) => {
    e.preventDefault();
    dispatch(login({ name, email }));
  };

  return (
    <form onSubmit={handleSubmit}>
      <input
        type="text"
        placeholder="Имя"
        value={name}
        onChange={(e) => setName(e.target.value)}
      />
      <input
        type="email"
        placeholder="Email"
        value={email}
        onChange={(e) => setEmail(e.target.value)}
      />
      <button type="submit">Войти</button>
    </form>
  );
};

export default Login;

Ключевые преимущества такого подхода:

  • Централизация состояния: Все данные хранятся в одном месте, что упрощает отладку и тестирование.
  • Предсказуемость изменений: Состояние изменяется только через действия (actions), что делает поток данных односторонним и контролируемым.
  • Масштабируемость: Структура Redux (особенно с Redux Toolkit) легко расширяется за счёт добавления новых слайсов.
  • Интеграция с инструментами разработчика: Redux DevTools позволяют отслеживать историю изменений состояния, что незаменимо при отладке сложных приложений.
  • Отделение логики от представления: Компоненты React остаются «глупыми» (презентационными), а вся бизнес-логика выносится в редюсеры и действия.

Альтернативы Redux:

  • Context API + useReducer: Встроенное решение React для простых случаев, но менее производительное для частых обновлений.
  • MobX: Использует наблюдаемые объекты и автоматически отслеживает изменения, подходит для реактивных приложений.
  • Zustand: Минималистичная библиотека с более простым API, набирающая популярность для небольших и средних проектов.

Этот пример демонстрирует полный цикл работы с глобальным хранилищем: от настройки до использования в компонентах. Такой подход особенно полезен в крупных приложениях, где необходимо синхронизировать состояние между множеством компонентов, не связанных напрямую в дереве React.

Приведи пример глобального хранилища | PrepBro