Принцип единственной ответственности

Каждый объект должен иметь одну обязанность и эта обязанность должна быть полностью инкапсулирована в класс, а все его сервисы должны быть направлены исключительно на обеспечение этой обязанности.

Принцип открытости/закрытости

Программные сущности (классы, модули, функции и т. п.) должны быть открыты для расширения, но закрыты для изменения. Это означает, что эти сущности могут менять свое поведение без изменения их исходного кода.

Принцип подстановки Барбары Лисков

Функционал, который наследуется от базового типа должен иметь возможность использовать функционал базового типа. Выносим только общий функционал из классов в базовый класс.

Принцип разделения интерфейса

Клиенты не должны зависеть от методов, которые они не используют. То есть если какой‑то метод интерфейса не используется клиентом, то изменения этого метода не должны приводить к необходимости внесения изменений в клиентский код.

Принцип инверсии зависимостей

Модули верхнего уровня не должны зависеть от модулей нижнего уровня. Пример с магазином и системами оплаты в нем. Если прописать жесткую связь с типом оплаты, то при добавлении нового типа оплаты нужно будет много рефакторить