Skip to content

Safe-Mode-Ex/tech-store

Repository files navigation

TechStore — Интернет-магазин электроники

React Vite MUI Leaflet Vitest

Современный интернет-магазин электроники с каталогом товаров, корзиной и системой промокодов.


📋 Содержание


📝 Описание проекта

TechStore — это одностраничное приложение (SPA) интернет-магазина, разработанное на React с использованием современных инструментов и практик. Приложение предоставляет пользователям удобный интерфейс для просмотра каталога электроники, управления корзиной покупок и применения скидок через промокоды.

Ключевые особенности:

  • Адаптивный дизайн на базе Material UI
  • Компонентная архитектура
  • Валидация и линтинг кода
  • Модульное тестирование

✨ Основные функции

Каталог товаров

  • Сетка товаров — отображение карточек с изображениями, ценами и описаниями
  • Индикаторы скидок — визуальное отображение товаров со скидкой
  • Добавление в корзину — быстрое добавление товаров из каталога
  • Слайдер баннеров — промо-баннеры на главной странице
  • Популярные товары — секция с рекомендуемыми товарами

Страница товара

  • Детальная информация — полное описание товара с характеристиками
  • Галерея изображений — просмотр фотографий товара с навигацией
  • Связанные товары — рекомендации похожих товаров
  • Блок цены — отображение цены со скидкой и без

Корзина покупок

  • Таблица товаров — структурированное отображение выбранных товаров
  • Управление количеством — увеличение/уменьшение количества каждого товара
  • Лимит покупок — ограничение максимального количества одного товара (макс. 2 шт.)
  • Удаление товаров — удаление позиций из корзины

Промокоды

  • Проверка кода — валидация промокода при вводе
  • Автоматический расчёт — применение скидки 15% при вводе кода Кекс
  • Пересчёт итогов — автоматическое обновление суммы заказа

Карта и навигация

  • Интерактивная карта — отображение местоположения на базе Leaflet
  • Маршрутизация — построение маршрута между точками
  • Секция локации — информация о местоположении магазина

Уведомления

  • Информирование о лимитах — предупреждение при достижении максимального количества товара
  • Страница 404 — страница для несуществующих маршрутов

🛠 Стек технологий

Основной стек

Технология Версия Назначение
React 19.2.5 UI библиотека
React DOM 19.2.5 Рендеринг компонентов
React Router DOM 7.14.1 Маршрутизация
Vite 7.3.2 Сборка и dev-сервер

UI и стилизация

Технология Версия Назначение
Material UI 9.0.0 Компоненты интерфейса
MUI Icons 9.0.0 Иконки
Emotion 11.14.x CSS-in-JS стилизация

Карты и геолокация

Технология Версия Назначение
Leaflet 1.9.4 Интерактивные карты
React Leaflet 5.0.0 React-компоненты для Leaflet
Leaflet Routing Machine 3.2.12 Построение маршрутов

Качество кода

Технология Версия Назначение
ESLint 8.57.1 Линтинг JavaScript
eslint-config-htmlacademy 10.0.1 Конфигурация ESLint
Stylelint 16.6.0 Линтинг CSS
stylelint-config-htmlacademy 4.2.2 Конфигурация Stylelint

Тестирование

Технология Версия Назначение
Vitest 4.1.4 Unit-тестирование
@testing-library/react 16.3.0 Тестирование React компонентов
@testing-library/jest-dom 6.1.5 Матчеры для DOM
jsdom 26.1.0 Среда для тестов

🏗 Архитектура

src/
├── pages/               # Страницы приложения
│   ├── CartPage/        # Страница корзины
│   ├── CatalogPage/     # Страница каталога
│   ├── HomePage/        # Главная страница
│   └── ProductDetailPage/ # Страница детальной информации о товаре
├── components/           # React компоненты
│   ├── App/             # Корневой компонент приложения
│   ├── BackButton/      # Кнопка возврата
│   ├── BannerSlider/    # Слайдер баннеров
│   ├── CartItem/        # Элемент корзины
│   ├── CartTable/       # Таблица корзины
│   ├── CartTotals/      # Итоговые суммы корзины
│   ├── Footer/          # Подвал сайта
│   ├── GalleryDot/      # Точка навигации галереи
│   ├── GallerySlide/    # Слайд галереи
│   ├── Header/          # Шапка сайта
│   ├── IntroSection/    # Вводная секция
│   ├── LimitNotification/ # Уведомление о лимите
│   ├── LocationSection/ # Секция локации
│   ├── Map/             # Интерактивная карта
│   ├── NotFoundState/   # Страница 404
│   ├── PopularProductsSection/ # Секция популярных товаров
│   ├── PriceBlock/      # Блок цены
│   ├── ProductCard/     # Карточка товара
│   ├── ProductGallery/  # Галерея товара
│   ├── ProductGrid/     # Сетка товаров
│   ├── ProductInfo/     # Информация о товаре
│   ├── PromoCodeForm/   # Форма промокода
│   ├── QuantityControl/ # Контроль количества
│   ├── RelatedProductCard/ # Карточка связанного товара
│   ├── RelatedProducts/ # Связанные товары
│   └── RoutingControl/ # Контроль маршрутизации
├── hooks/               # Кастомные хуки
│   ├── useCartItem/     # Логика элемента корзины
│   ├── useGallery/      # Логика галереи
│   ├── useLimitNotification/ # Логика уведомлений о лимите
│   └── useProductDetail/ # Логика страницы товара
├── utils/               # Утилиты
│   ├── array/           # Функции для работы с массивами
│   ├── cart/            # Функции для работы с корзиной
│   └── price/           # Функции для работы с ценами
├── constants/           # Константы приложения
│   ├── cart.js          # Параметры корзины (лимиты, промокоды)
│   └── map.js           # Координаты для карты
├── data/                # Данные приложения
│   ├── banners.js       # Данные баннеров
│   ├── products.js      # Каталог товаров
│   └── productsDetail.js # Детальная информация о товарах
├── assets/              # Статические ресурсы
├── index.css            # Глобальные стили
└── main.jsx             # Точка входа

Принципы архитектуры

  • Атомарный дизайн — компоненты разделены по функциональности
  • Изоляция стилей — CSS-модули для каждого компонента
  • Централизация данных — константы и данные вынесены в отдельные директории
  • Чистые компоненты — презентационные компоненты без side-effects

🚀 Установка и запуск

Требования

  • Node.js ≥ 18.0.0
  • npm ≥ 9.0.0

Установка зависимостей

npm install

Запуск в режиме разработки

npm run dev

Приложение будет доступно по адресу: http://localhost:5173

Сборка для production

npm run build

Собранные файлы будут в директории dist/

Предпросмотр production-сборки

npm run preview

💡 Примеры использования

Для пользователей

1. Просмотр каталога

  • Откройте главную страницу
  • Просматривайте товары в сетке
  • Обратите внимание на карточки со скидками (маркер -X%)

2. Добавление в корзину

  • Нажмите кнопку «В корзину» на карточке товара
  • Товар автоматически добавится в корзину
  • При попытке добавить более 2 штук одного товара — появится уведомление о лимите

3. Управление корзиной

  • Перейдите в раздел корзины
  • Используйте кнопки + и - для изменения количества
  • Нажмите иконку корзины для удаления товара

4. Применение промокода

  • Введите промокод Кекс в поле промокода
  • Нажмите «Применить»
  • Итоговая сумма пересчитается с учётом скидки 15%

Для разработчиков

Запуск линтеров

# JavaScript/JSX
npm run lint:scripts
npm run lint:scripts:fix  # с автоматическим исправлением

# CSS
npm run lint:styles
npm run lint:styles:fix   # с автоматическим исправлением

Запуск тестов

npm run test              # интерактивный режим
npm run test -- --run     # однократный запуск

Добавление нового товара

// src/data/products.js
{
  id: 11,
  name: 'Название товара',
  price: 9990,
  discount: 10,                    // опционально
  description: 'Описание товара',
  image: 'https://example.com/image.jpg',
}

❓ FAQ

Q: Почему не могу добавить более 2 штук одного товара?
A: Это ограничение бизнес-логики (MAX_PRODUCT_QUANTITY = 2), предотвращающее перекупку товаров. Для изменения отредактируйте @/constants/cart.js:1.

Q: Какие промокоды работают?
A: Активный промокод — Кекс (скидка 15%). Добавить новые можно в @/constants/cart.js.

Q: Поддерживается ли TypeScript?
A: Текущая версия использует JavaScript. Для миграции на TypeScript установите typescript и @types/* пакеты, затем переименуйте файлы в .tsx.

Q: Как добавить страницу оформления заказа?
A: Используйте React Router DOM — добавьте маршрут в App компонент и создайте соответствующий компонент страницы.

Q: Можно ли подключить реальное API?
A: Да. Замените импорт статических данных в компонентах на fetch/axios запросы к вашему бэкенду.


👨‍💻 Для разработчиков

Стандарты кода

  • ESLint — конфигурация HTML Academy для JavaScript
  • Stylelint — конфигурация HTML Academy для CSS
  • Компоненты — функциональные с хуками, без классов
  • Именование — PascalCase для компонентов, camelCase для функций и переменных

Структура компонента

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

ComponentName/
├── ComponentName.jsx    # Компонент
├── ComponentName.css     # Стили
└── index.js              # Реэкспорт (опционально)

Тестирование

Тесты размещаются рядом с компонентами в файлах *.test.jsx:

import { render, screen } from '@testing-library/react';
import { describe, it, expect } from 'vitest';
import ProductCard from './ProductCard';

describe('ProductCard', () => {
  it('renders product name', () => {
    render(<ProductCard product={mockProduct} />);
    expect(screen.getByText('Product Name')).toBeInTheDocument();
  });
});

Конфигурация

  • vite.config.js — настройки Vite
  • vitest.config.js — настройки тестирования
  • .eslintrc.cjs — правила ESLint
  • .stylelintrc — правила Stylelint

📄 Лицензия

Проект создан в образовательных целях. Свободно используйте код для обучения и разработки.


Сделано с ❤️ на React + Vite

About

Fully built using ai agents

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors