---
sidebar_position: 9
---

# SOLID

SOLID в React помогает:
- Держать компоненты маленькими и читаемыми (S).
- Делать их расширяемыми через props и композицию (O).
- Гарантировать предсказуемость работы компонентов (L).
- Избегать перегруженных пропсов и интерфейсов (I).
- Упрощать замену реализаций (API, стейт-менеджер и т.д.) через абстракции (D).

Принципы SOLID — это набор из пяти ключевых принципов объектно-ориентированного программирования и проектирования, которые помогают создавать гибкие, поддерживаемые и масштабируемые программные системы. Аббревиатура SOLID была введена Робертом Мартином (известным также как Uncle Bob) и расшифровывается следующим образом:

## Simple responsibility principle (принцип единой ответственности)
У класса должна быть только одна причина для изменения, то есть у него должна быть только одна ответственность или работа. Этот принцип помогает сделать занятия более целенаправленными, более понятными и менее подверженными ошибкам.

**Применение во Фронтенде:** Каждый компонент/модуль должен выполнять одну задачу.
В React:
- Компонент выполняет **одну задачу**: либо отображает UI, либо управляет состоянием, но не всё сразу.
- Логика выносится в **хуки** или **сервисы**, чтобы компоненты оставались "чистыми".

Пример:
- ❌ Плохо: `UserProfile` компонент, который извлекает, проверяет, отображает и управляет состоянием.
- ✅ Хорошо: `UserProfile` компонент, который только отображает, и отдельный хук (`useUser`), который извлекает данные.

## Open – Closed Principle (Принцип открытости/закрытости)
Программные сущности должны быть открыты для расширения, но закрыты для модификации. Это означает, что вы должны иметь возможность добавлять новые функции в систему, не изменяя существующий код.
Мы можем расширить функциональный компонент и добавить новый компонент пользовательского интерфейса, не затрагивая первый/базовый компонент. Это реализация открытости для расширения, но закрытости для модификации.

**Применение во Фронтенде:** Код должен быть расширяемым без переписывания старой логики.
- Используем **props** для настройки поведения.
- Применяем **композицию** вместо жёсткого наследования.

Вместо того, чтобы переписывать старые компоненты, проектируйте их так, чтобы можно было добавлять новые функции с помощью свойств/хуков/расширений.  
Пример: Хотите добавить новый стиль кнопки? Добавьте свойство для расширения стилей, не дублируйте весь компонент.


## Liskov Substitution principe (принцип замены Лискова)
Объекты суперкласса должны быть заменяемы объектами его подклассов без нарушения корректности программы. Другими словами, подклассы должны иметь возможность заменять свои базовые классы без возникновения ошибок.

**Применение во Фронтенде:** Кнопка `Button` всегда должна действовать как кнопка, независимо от того, является ли она основной, дополнительной или отключенной.

В React:
- Это проявляется в **контрактах компонентов**: если компонент принимает `props`, он должен работать предсказуемо для любого допустимого значения.
- Не заставляй компонент вести себя неожиданно из-за "хаков" или скрытой логики.

## Interface segregation principle (Принцип разделения интерфейсов)
Клиентов не следует заставлять зависеть от интерфейсов, которые они не используют. Вместо этого интерфейсы следует разделить на более мелкие, более целенаправленные интерфейсы, соответствующие потребностям клиента.\
Лучше много маленьких интерфейсов, чем один "толстый".

**Применение во Фронтенде:** Не заставляйте компоненты принимать свойства, которые они не используют.
- ❌ Плохо: Много лишних свойств в компоненте, 80% которого не используется.
- ✅ Хорошо: Используйте только те свойства которые используются в компоненте.

В React:
- Не перегружай компонент кучей пропсов.
- Делай узко специализированные пропсы или выноси сложные конфигурации в отдельные структуры.

Пример: Вместо `user: {id, name, email, role, lastLogin, preferences}`, возможно, вам для UserAvatar нужны только `name` и `profilePic`.
```js
// ❌ Плохо: слишком много пропсов
<Card title subtitle image footer isLoading isActive hasError />

// ✅ Лучше: разделяем интерфейсы
<Card>
  <CardHeader title="..." subtitle="..." />
  <CardBody>...</CardBody>
  <CardFooter>...</CardFooter>
</Card>
```

## Dependency inversion principle (Инверсия зависимости)
Высокоуровневые модули не должны зависеть от низкоуровневых модулей. Вместо этого, оба должны зависеть от абстракций. Это помогает в разъединении модулей, делая их более пригодными для повторного использования и более простыми для тестирования.

**Применение во Фронтенде:** Опирайтесь на абстракции, а не на детали.
- Вместо жесткого задания функций API в компонентах внедрите сервисный уровень.
- Если завтра ваш API изменится, вы меняете логику сервиса, а не всё приложение.

В React:
- Используем контекст или hooks для работы с зависимостями (например, API или хранилище).
- Компоненты не должны жёстко зависеть от конкретной реализации.

## Преимущества SOLID:
1. **Гибкость:** Код становится проще расширять и модифицировать.
2. **Поддерживаемость:** Упрощается понимание и исправление ошибок.
3. **Тестируемость:** Код, соответствующий SOLID, легче тестировать.
4. **Масштабируемость:** Система становится более устойчивой к изменениям и росту.

🚀 **_Источник: ChatGPT_**
