У меня есть приложение, которое использует MVC, но я немного борюсь за то, как контроллер должен быть спроектирован. Например, представление одновременно просматривает только некоторое подмножество данных модели. Однако я не уверен, как именно это должно быть организовано. Например, нормально ли для представления или модели напрямую вызывать функции на контроллере? Через какой-то интерфейс? Или они полностью инкапсулированы и никогда не знают о контроллере или друг о друге?
Просто как редактирование; Это пользовательское приложение, которое написано не в какой-либо веб-среде, поэтому я не ищу подробностей, касающихся этой среды, и могу свободно выбирать.
Ответы:
Контроллер контролирует поток активности. Пользователь выполняет это действие, контроллер передает данные представления в домен, который затем делает все, что ему нужно, на основе ответа (ов), контроллер сообщает платформе, какое представление следует показать далее (и дает ему достаточно данных для выполнения). так).
Таким образом, контроллер должен быть в некоторой степени связан с моделью предметной области. то есть. Вы можете поместить сервисный уровень между ними, но, по строгому определению, он станет частью домена.
Он также связан с данными представления, но не с самим представлением. то есть. он просто говорит «показать мнение клиента, используя эту информацию о клиенте». Затем структура решает, где ей найти это представление.
Теперь это должно позволить вам отделить модель домена от представления, используя модель представления тех же данных. Некоторые разработчики делают это, некоторые нет, и я думаю, что это в основном вопрос личных предпочтений.
В Rails вам очень рекомендуется выдвигать доменные объекты (ActiveRecord) в представление и полагать, что представление не использует этот доступ (например, вы не должны вызывать customer.save из представления, даже если оно будет доступно).
В мире .NET мы склонны снижать риск, не допуская того, что не должно происходить, и, возможно, по этой причине, мне кажется, что модель отдельного представления более популярна.
источник
Примечание: Роберт К. Мартин (он же Дядя Боб) объясняет это гораздо лучше и юмористичнее в своей лекции « Архитектура потерянных лет» . Немного долго, но учит много хороших концепций.
tl; dr: не думайте и не планируйте свое приложение с точки зрения MVC. Инфраструктура MVC - это просто деталь реализации.
Наиболее запутанная вещь в MVC - разработчики пытаются использовать все компоненты, склеенные вместе.
Попробуйте мыслить с точки зрения программы, а не с точки зрения структуры.
У вашей программы есть цель. Он берет некоторые данные, работает с данными и возвращает некоторые данные.
Таким образом,
controller
механизм доставки вашей программы.$user->addToCart($product)
addToCart
функцияuser
объекта) выполняет работу, для которой она предназначена, и возвращает ответ (скажем,success
)view
: например. в объекте контроллера$this->render($cartView('success')
Таким образом, контроллеры отделены от программы и используются в качестве механизма доставки. Они не знают, как работает ваша программа, они просто знают, какую часть программы нужно вызывать для запросов.
Если вы хотите использовать другой фреймворк, ваше приложение не будет нуждаться в изменениях, вам просто нужно написать соответствующие контроллеры для вызова вашей программы для запросов.
Или, если вы хотите сделать настольную версию, ваше приложение останется прежним, вам просто нужно будет подготовить механизм доставки.
А то
Model
. Думайте об этом как о механизме постоянства.Таким образом, в вашей программе есть объекты, которые содержат данные.
При добавлении продукта в корзину, вы можете добавить
product::id
кuser::shoppingCart
.А если вы хотите сохранить данные, вы можете использовать
model
часть инфраструктуры, которая обычно состоит из ORM, для сопоставления классов с таблицами базы данных.Если вы хотите изменить используемый ORM, ваша программа останется прежней, изменится только информация сопоставления. Или, если вы хотите избежать одновременного использования баз данных, вы можете просто записать данные в простые текстовые файлы, и ваше приложение останется прежним.
Итак, сначала напишите свою программу. Если вы программируете способом «OO», используйте простые старые объекты языка. Сначала не думайте с точки зрения MVC.
источник
MVC
такое. Вот почему я написалMVC Framework
.Мартин Фаулер хорошо описывает парадигму MVC. Вот ссылка на его статью об этом http://martinfowler.com/eaaDev/uiArchs.html
Обратите внимание на его цитату о Separated Presentation «Идея Separated Presentation заключается в том, чтобы сделать четкое разделение между объектами домена, которые моделируют наше восприятие реального мира, и объектами презентации, которые являются элементами GUI, которые мы видим на экране».
источник
Вот простой пример того, как MVC может использоваться в типичном приложении Java Swing ...
Допустим, у вас есть панель, содержащая кнопку и текстовое поле. Когда кнопка нажата, происходит событие, которое приводит к некоторому изменению состояния в приложении. Как только изменение состояния зарегистрировано, TextField становится отключенным.
Таким образом, это будет типичный подход, используемый простым приложением MVC ...
Контроллер регистрируется как слушатель событий View. Когда кнопка нажата, само представление не обрабатывает событие; Контроллер делает. Контроллер специфичен для Swing, так как должен иметь дело с событиями, связанными с Swing.
Контроллер получает это уведомление и должен решить, кто должен обрабатывать его (представление или модель). Поскольку это событие изменит состояние приложения, оно решает переслать информацию в модель, которая отвечает за данные и логику программы. Некоторые делают ошибку, помещая программную логику в контроллер, но в ООП модели представляют как данные, так и поведение. Прочитайте Мартина Фаулера о его взгляде.
Сообщение получено Моделью в соответствующем контексте. То есть он полностью лишен каких-либо ссылок на Swing или любых других специфических ссылок для графического интерфейса. Это сообщение говорит о модели и только модели. Если вы обнаружите, что импортируете в модель операторы javax.swing, вы неправильно кодируете модель.
Затем модель устанавливает свое состояние как «отключено» и переходит к уведомлению любых заинтересованных сторон об изменении этой модели. Заинтересовавшись этим событием, View уже зарегистрировался в качестве наблюдателя любых изменений модели. Как только событие изменения состояния модели выявляется представлением, оно продолжает отключать свой TextField. Представление также может получать информацию только для чтения непосредственно из своей модели, не проходя через контроллер (обычно через специальный интерфейс, предоставляемый моделью для такой деятельности).
Продвигая такую слабую связь между презентацией и бизнес-логикой и уровнями данных, вы обнаружите, что ваш код гораздо более удобен в обслуживании. По мере роста систем ваш подход к MVC будет расти. Например, Hierarchical MVC - это расширение, часто используемое для связывания триад MVC вместе, чтобы сформировать большие корпоративные системы без объединения подсистем вместе.
источник
Сцепление (вид вы хотите избежать) предполагает взаимную зависимость между двумя классами. То есть Foo зависит от Bar, а Bar зависит от Foo, так что вы не можете реально изменить одно без изменения другого. Это плохо.
Однако вы не можете избежать некоторых зависимостей. Классы должны знать немного друг о друге, иначе они никогда не будут общаться.
В шаблоне MVC Контроллер управляет связью между Моделью домена и Представлением представления. Таким образом, Контроллер должен знать достаточно о Модели, чтобы попросить ее сделать то, что он должен делать. Контроллер также должен знать достаточно о представлении, чтобы иметь возможность представить его клиенту или пользователям. Таким образом,
ModelController зависит от обоих. Тем не менее, представление может прекрасно существовать без контроллера - там нет никакой зависимости. Точно так же Модель не зависит от контроллера - она просто есть. Наконец, Модель и Вид полностью отделены друг от друга.По сути, Контроллер - это уровень косвенности, который отделяет Представление от Модели, так что они не должны знать друг о друге.
источник
По моему опыту, как правило , модель зависит только с точки зрения, а не специфична, часто в качестве наблюдателя ... если это имеет какое - либо такое соединение на всех.
Представление, как правило, сочетается с тем, на что оно смотрит, что имеет смысл. Трудно придумать вид, который можно отделить от того, что он просматривает ... но иногда вы можете иметь частичную связь или что-то в этом роде.
Контроллер часто стремится соединиться с обоими. Это также имеет некоторый смысл, поскольку его задача - превратить события просмотра в изменения модели.
Конечно, это всего лишь тенденция, которую я наблюдал, и она ничего не говорит о каком-либо конкретном примере.
Чтобы понять, что такое MVC и каковы отношения связывания, вы должны посмотреть, как возник MVC. Среда, в которой был создан MVC, была такой, в которой «виджеты» как элементы формы, с которыми можно создавать диалоги, не существовали. «Вид» был коробкой, и он рисовал вещи. Текстовое представление будет блоком, который будет рисовать текст. Представление списка было коробкой, которая нарисует список. «Контроллер» получил все события мыши и клавиатуры от системы пользовательского интерфейса, которые имели место в этом представлении; не было никаких событий "textChanged" или "selectionChanged". Контроллер будет принимать все эти события низкого уровня и генерировать взаимодействие с моделью. Модель, будучи измененной, уведомит свои взгляды; с тех пор мы стали рассматривать эти отношения как «наблюдателя», и это
В этом суть паттерна MVC. Поскольку такого рода низкоуровневое программирование пользовательского интерфейса, как правило, больше не выполняется, MVC развивалась во многих различных направлениях. Некоторые вещи, которые сегодня носят такое название, совсем не похожи на MVC, и их действительно следует называть чем-то другим. Это все еще может использоваться, хотя в смысле диалога в целом, взаимодействующего с более крупным объектом. Хотя есть много лучших альтернатив.
По сути, все, что MVC должен был решить, теперь происходит внутри виджетов и нам больше не нужно использовать.
Для тех, кто считает, что знает лучше:
http://www.codeproject.com/Articles/42830/Model-View-Controller-Model-View-Presenter-and-Mod
http://msdn.microsoft.com/en-us/library/ff649643.aspx
Я уверен, что есть и другие, но это только верхняя часть списка в Google. Как видите, модель во многом зависит от интерфейса представления в МНОГИХ реализациях. Обычно модель является наблюдаемой, а вид - наблюдателем.
Но почему факты мешают ...
Статья, уже опубликованная в другом ответе, также поддерживает мои заявления:
http://martinfowler.com/eaaDev/uiArchs.html
Если люди хотят продолжать говорить, что ВСЕ в индустрии дизайна не правы, тогда это нормально.
источник
Если контроллер был тесно связан с представлением, то мы будем в мире веб-форм. У вас будет код, который будет привязан к файлу шаблона (применимо к веб-формам ASP.NET)
Из-за этого контроллер не связан с моделью или представлением. Это просто механизм для обработки запросов и отправки ответов.
Вид тесно связан с моделью. Внесите изменения в свою модель (например, измените ее свойство), и вам придется вносить изменения в свой вид.
Модель не тесно связана с видом. Внесите изменения в представление, и это не повлияет на модель.
Модель ничего не знает о контроллере или видах, где он может быть использован. Поэтому модель не тесно связана с видом или контроллером.
Еще один способ думать об этом:
Внесите изменения в контроллер - вид и модель не будут затронуты
Вносить изменения в модель - представление будет нарушено, так как оно зависит от модели
Внесите изменения в представление - модель и контроллер не будут затронуты
Эта слабая связь в проектах MVC позволяет легко их тестировать.
источник