Знакомимся с терминологией MVC
Пойдем по порядку. Model (Модель). Каково ее назначение?
- Хранит или имеет доступ к данным.
- Умеет с ними работать (создать, читать, редактировать, удалить).
- Содержит бизнес-логику работы с данными (на этом я остановлюсь подробнее дальше в статье).
- Знает как визуализировать данные, НО НЕ УМЕЕТ ЭТОГО ДЕЛАТЬ
- Знает как контролировать работу пользователя, НО НЕ УМЕЕТ ЭТОГО ДЕЛАТЬ
Две последние фразы, возможно, кажутся Вам странными. Что значит не умеет этого делать? А кто тогда умеет? Ответ прост:
- View (Представление) умеет визуализировать данные.
- Controller (Контроллер) умеет контролировать работу пользователя.
Пример задачи, которую будем решать с помощью MVC
правитьПредположим, что мы разрабатываем "Платежную систему для банка". Необходимо обеспечить выполнение двух видов платежей: исходящие (клиент платит деньги) и входящие (клиент получает деньги).
Назначение паттерна MVC
правитьНаша цель — отделить бизнес-логику от визуализации. Буквально это означает, что обработчик нажатия кнопки "Оплатить" не должен проверять возможность выполнения платежа (например, достаточно ли средств на счету при выполнении исходящего платежа). Зачем? Для того, чтобы повысить возможность повторного использования кода. В программе может быть несколько моделей, представлений и контроллеров. В нашем примере было бы неплохо сделать две модели (на каждый платеж), но для них обеих использовать одно представление (формы идентичны с точностью до мелких деталей).
Что такое "бизнес-логика"?
правитьБизнес-логика — это набор правил и ограничений объектов предметной области. Вот пример бизнес-логики в нашей задаче:
- IsMoneyEnough() — Проверяет, достаточно ли денег на счету для проведения оплаты.
- CalculateFees() — Считает комиссионные за осуществление платежа.
- NeedReportToNB() — Проверяет, превышает ли сумма установленный лимит, при котором нужно дополнительно отчитываться в нацбанк.
- IsCurrencyAllowed() — Проверяет, разрешена ли валюта на данном счете.
Бизнес-логика — это в большей степени высокоуровневые функции, которые решают задачу заказчика, а не способ хранения или подкраска строки в таблице.
При выполнении разных видов платежей необходимо контролировать его выполнение ( PaymentIsPossible() ). Идеологически мы имеем одно действие, но, в зависимости от модели (вида платежа), это будет выполняться по разному. Для входящего платежа нет смысла в методе IsMoneyEnough() — деньги только увеличиваются. CalculateFees() необходим в любом случае. И так далее.
Входит ли метод PaymentIsPossible() в бизнес-логику? Нет! Контроль действий — это обязанность контроллера, это интуитивно понятно даже из его названия.
Контроллер следит за корректностью действий, используя правила бизнес-логики (методы модели)
Надеюсь теперь ясно, что я подразумевал, говоря что модель знает как контролировать работу, а контроллер умеет это делать.