Страница 348 русского перевода:
Принцип действия
Типовое решение модель-представление—контроллер подразумевает выделение трех отдельных ролей. Модель— это объект, предоставляющий некоторую информацию о домене. У модели нет визуального интерфейса, она содержит в себе все данные и поведе¬ние, не связанные с пользовательским интерфейсом. В объектно-ориентированном кон¬тексте наиболее "чистой" формой модели является объект модели предметной области (Domain Model, 140). В качестве модели можно рассматривать и сценарий транзакции (Transaction Script, 133), если он не содержит в себе никакой логики, связанной с пользо¬вательским интерфейсом. Подобное определение не очень расширяет понятие модели, однако полностью соответствует распределению ролей в рассматриваемом типовом ре¬шении.
Представление отображает содержимое модели средствами графического интерфейса. Таким образом, если наша модель — это объект покупателя, соответствующее представ¬ление может быть фреймом с кучей элементов управления или HTML-страницей, запол¬ненной информацией о покупателе. Функции представления заключаются только в ото¬бражении информации на экране. Все изменения информации обрабатываются третьим "участником" нашей системы — контроллером. Контроллер получает входные данные от пользователя, выполняет операции над моделью и указывает представлению на необхо¬димость соответствующего обновления. В этом плане графический интерфейс можно рассматривать как совокупность представления и контроллера.
Говоря о типовом решении модель—представление—контроллер, нельзя не подчеркнуть два принципиальных типа разделения: отделение представления от модели и отделение контроллера от представления.
Отделение представления от модели — это один из фундаментальных принципов про¬ектирования программного обеспечения. Наличие подобного разделения весьма важно по ряду причин.
• Представление и модель относятся к совершенно разным сферам программирова¬
ния. Разрабатывая представление, вы думаете о механизмах пользовательского ин¬
терфейса и о том, как сделать интерфейс приложения максимально удобным для
пользователя. В свою очередь, при работе с моделью ваше внимание сосредоточе¬
но на бизнес-политиках и, возможно, на взаимодействии с базой данных. Очевид¬
но, при разработке модели и представления применяются разные (совершенно
разные!) библиотеки. Кроме того, большинство разработчиков специализируются
только в одной из этих областей.
• Пользователи хотят, чтобы, в зависимости от ситуации, одна и та же информация
могла быть отображена разными способами. Отделение представления от модели
позволяет разработать для одного и того же кода модели несколько представлений,
а точнее, несколько абсолютно разных интерфейсов. Наиболее наглядно данный
подход проявляется в том случае, когда одна и та же модель может быть представ¬
лена с помощью толстого клиента, Web-обозревателя, удаленного API или интер¬
фейса командной строки. Даже в пределах одного и того же Web-интерфейса в
разных местах приложения одному и тому же покупателю могут соответствовать
разные страницы.
• Объекты, не имеющие визуального интерфейса, гораздо легче тестировать, чем объекты с интерфейсом. Отделение представления от модели позволяет легко про¬тестировать всю логику домена, не прибегая к таким "ужасным" вещам, как сред¬ства написания сценариев для поддержки графического интерфейса пользователя.
Ключевым моментом в отделении представления от модели является направление зависимостей: представление зависит от модели, но модель не зависит от представления. Программисты, занимающиеся разработкой модели, вообще не должны быть осведомле¬ны о том, какое представление будет использоваться. Это существенно облегчает разра¬ботку модели и одновременно упрощает последующее добавление новых представлений. Кроме того, это означает, что изменение представления не требует изменения модели.
Данный принцип тесно связан с распространенной проблемой. При использовании толстого клиента с множеством диалоговых окон на экране могут одновременно нахо¬диться несколько представлений одной и той же модели. Если пользователь внесет из¬менения в модель посредством одного представления, эти изменения должны быть от¬ражены и во всех остальных представлениях. Чтобы это было возможным при отсутствии двунаправленной зависимости, необходимо реализовать типовое решение наблюдатель (Observer) [20] с использованием метода распространения событий (event propagation) или в виде типового решения слушатель (Listener). В этом случае представление будет выполнять роль "наблюдателя" за моделью: как только модель будет изменена, представ¬ление генерирует соответствующее событие и все остальные представления обновляют свое содержимое.
Отделение контроллера от представления не играет такой важной роли, как предыду¬щий тип разделения. Действительно, по иронии судьбы практически во всех версиях Smalltalk разделение на контроллер и представление не проводилось. Классическим при¬мером необходимости подобного разделения является поддержка редактируемого и не-редактируемого поведения. Этого можно достичь при наличии одного представления и двух контроллеров (для двух вариантов использования), где контроллеры являются стра¬тегиями [20], используемыми представлением. Между тем на практике в большинстве систем каждому представлению соответствует только один контроллер, поэтому разделе¬ние между ними не проводится. О данном решении вспомнили только при появлении Web-интерфейсов, где отделение контроллера от представления оказалось чрезвычайно полезным.
Тот факт, что в большинстве инфраструктур пользовательских интерфейсов не про¬водилось разделение на представление и контроллер, привел к множеству неверных тол¬кований типового решения модель-представление—контроллер. Да, наличие модели и представления очевидно, но где же контроллер? Многие решили, что контроллер нахо¬дится между моделью и представлением, как в контроллере приложения (Application Controller, 397). Данное заблуждение еще более усугубил тот факт, что в обоих названиях фигурирует слово "контроллер". Между тем, несмотря на все положительные качества контроллера приложения, он ничем не похож на контроллер типового решения модель-представление—контроллер.
Описанные принципы — это все, что требуется для понимания данного набора типо¬вых решений. Если же вам захочется еще немного покопаться в типовом решении мо¬дель-представление—контроллер, обратитесь к источнику [33] — там содержится лучшее на данный момент описание этого типового решения.
Назначение
Как уже отмечалось, ценность типового решения модель—представление—контроллер
заключается в наличии двух типов разделения. Отделение представления от модели — один из основополагающих принципов, на котором держится все проектирование про¬граммного обеспечения, и пренебрегать им можно только тогда, когда речь идет о совсем простых системах, в которых модель вообще не имеет какого-либо реального поведения. Как только в приложении появляется невизуализированная логика, разделение стано¬вится крайне необходимым. К сожалению, во многих инфраструктурах пользовательских интерфейсов реализовать подобное разделение довольно сложно, а там, где это неслож¬но, о нем все равно забывают.
Отделение представления от контроллера не так важно, поэтому рекомендую прово¬дить его только в том случае, когда оно действительно нужно. Подобная необходимость практически не возникает в системах с толстыми клиентами, а вот в Web-интерфейсах отделение контроллера весьма полезно. Большинство рассматриваемых здесь типовых решений, предназначенных для проектирования Web-приложений, основаны именно на этом принципе.
А вообще это уже стандарт. Посмотрите RUP как описывает реализацию системного ВИ: как минимум 1 граничный класс (вот вам и view) , который соединяется с 1 как минимум управляющим классом (т.е. контроллером) и наконец, класс-сущность, опять же как минимум 1 (ничто иное как перзистент сущность, т.е. нечто что важно хранить или формировать между вычислениями, хранится может как угодно, но обычно в виде реляционных таблиц)
Применительно к ООП, можно сказать:
классы-сущности не обладают поведением (трудно поведение хранить в реляционной бд), хотя это на самом деле и не так, но для просты можно, т.е. хранят важнейшую информацию от предметной области некоего бизнеса или приложения, например вот это самое сообщение, помеченное как ответ на тему и привязанное к автору, т.е. мне
далее
класс-контроллер, т.е. некий объект, который осуществялет связь интерфейса (в нашем случае вот этого самого редактора сообщений и базы данных в которой это сообщение потом будет сохранено), т.е. когда я нажму кнопочку отправить, ентот самый класс контроллер, а возможно и целая масса этих классов, проверит мое сообщение на профпригодность, допустимость и т.п. Если все окей, пошелет запрос на соединение с БД сервером, выберет БД или сразу нужную таблицу, осуществит запрос на добавление, проверит отклик и выдаст управление на обновление страницы.
Здесь мы видим четоке разделение полномочий и действия принципов ООП: как минимум инкапсуляция, разделение отвественности