Рельсы Модель, Вид, Контроллер и помощник: что идет куда?


в Ruby on Rails Development (или MVC в целом), какое быстрое правило я должен следовать относительно того, где поставить логику.

пожалуйста, ответьте утвердительно - с положите это сюда, а не не кладите это туда.

10   152   2008-09-13 20:18:01

10 ответов:

MVC

контроллер: поместите здесь код, который имеет отношение к разработке того, что хочет пользователь, и решает, что им дать, выясняя, вошли ли они в систему, должны ли они видеть определенные данные и т. д. В конце концов, контроллер смотрит на запросы и решает, какие данные (модели) показывать и какие представления отображать. Если вы сомневаетесь, является ли код должен идти на контроллер, то он, пожалуй, не стоит. Держать ваши контроллеры худой.

посмотреть: представление должно содержать только минимальный код для отображения ваших данных (модели), оно не должно выполнять много обработки или вычисления, оно должно отображать данные, вычисленные (или суммированные) моделью или сгенерированные из контроллера. Если ваше представление действительно нуждается в обработке, которая не может быть выполнена моделью или контроллером, поместите код в Помощник. Много кода на Ruby в представлении, делает страницы жесткими разметки читать.

модель: ваша модель должна быть где все ваш код, который относится к вашим данным (сущности, которые составляют ваш сайт, например, пользователи, Почта, учетные записи, друзья и т. д.) жизни. Если код нуждается в сохранении, обновлении или обобщении данных, связанных с вашими сущностями, поместите его здесь. Он будет повторно использоваться в ваших представлениях и контроллерах.

чтобы добавить к ответу pauliephonic:

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

шаблон MVC действительно касается только пользовательского интерфейса и ничего больше. Вы не должны помещать какую-либо сложную бизнес-логику в контроллер, поскольку он управляет представлением, но не логикой. Контроллер должен заботиться о выборе правильного представления и делегировать более сложные вещи в модель домена (модель) или бизнес-уровень.

Domain Driven Design имеет концепцию сервисов, которая является местом, где вы придерживаетесь логики, которая должна организовать ряд различных типов объектов что обычно означает логику, которая естественным образом не принадлежит классу модели.

Я обычно думаю о сервисном уровне как API моих приложений. Мои слои сервисов обычно сопоставляются довольно близко к требованиям приложения, которое я создаю, таким образом, слой сервиса действует как упрощение более сложных взаимодействий, найденных на более низких уровнях моего приложения, т. е. вы можете достичь той же цели, минуя слои сервиса, но вам придется потянуть гораздо больше рычагов, чтобы сделать это работает.

обратите внимание, что я не говорю о рельсах здесь я говорю об общем архитектурном стиле, который решает вашу конкретную проблему.

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

нам нужны умные модели, тонкие контроллеры и тупые взгляды.

http://c2.com/cgi/wiki?ModelViewController

путь рельсов должен иметь тощие контроллеры и толстые модели.

поместите вещи, связанные с авторизацией / контролем доступа в контроллер.

модели все о ваших данных. Валидация, отношения, CRUD, бизнес-логика

представления о показе ваших данных. Отображение и получение только ввода.

контроллеры управляют тем, какие данные идут от вашей модели к вашему представлению (и какой вид) и от вашего представления к вашей модели. Контроллеры также могут существовать без моделей.

Мне нравится думать контролер в качестве охранника / администратора, который направляет вам клиента (запрос) к соответствующему счетчику, где вы задаете кассиру (просмотр) вопрос. Затем кассир (просмотр) идет и получает ответ от менеджера (модели), которого вы никогда не видите. Затем вы возвращаетесь к охраннику/администратору (контроллеру) и ждете, пока вам не будет предложено перейти к другому кассиру (просмотр), который сообщает вам ответ, который менеджер (модель) сказал им в ответ на вопрос другого кассира (просмотр).

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

Итак, чтобы расширить метафору, в моем стереотипном и нереалистичном мире рассказчики (взгляды) хороши, но пустоголовы и часто верьте всему, что вы говорите им, охранник / регистраторы минимально вежливы, но не очень хорошо осведомлены, но они знают, где люди должны и не должны идти, а менеджеры действительно уродливы и злые, но знают все и могут сказать, что правда, а что нет.

одна вещь, которая помогает правильно отделить, - это избежать" передачи локальных переменных от контроллера для просмотра " анти-шаблона. Вместо этого:

# app/controllers/foos_controller.rb:
class FoosController < ApplicationController

  def show
    @foo = Foo.find(...)
  end

end

#app/views/foos/show.html.erb:
...
<%= @foo.bar %>
...

попробуйте переместить его в геттер, который доступен в качестве вспомогательного метода:

# app/controllers/foos_controller.rb:
class FoosController < ApplicationController

  helper_method :foo

  def show
  end

  protected

  def foo
    @foo ||= Foo.find(...)
  end

end

#app/views/foos/show.html.erb:
...
<%= foo.bar %>
...

Это упрощает изменение того, что помещается в "@foo" и как оно используется. Это увеличивает разделение между контроллером и видом, не делая их более сложными.

Ну, это отчасти зависит от того, с чем имеет дело логика...

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

кроме того, быстрый бит google показывает еще несколько конкретных примеры того, что куда идет.

модель: требования к проверке, отношения данных, методы создания, методы обновления, методы уничтожения, методы поиска (обратите внимание, что вы должны иметь не только общие версии этих методов, но и если есть что-то, что вы делаете много, например, находите людей с рыжими волосами по фамилии, то вы должны извлечь эту логику, чтобы все, что вам нужно сделать, это вызвать find_redH_by_name("smith") или что-то в этом роде)

вид: это должно быть все о форматировании данных, а не об обработке данных.

контроллер:здесь идет обработка данных. Из интернета: "цель контроллера-ответить на действие, запрошенное пользователем, взять любые параметры, которые пользователь установил, обработать данные, взаимодействовать с моделью, а затем передать запрошенные данные в окончательной форме в представление."

надеюсь, что это поможет.

в простых терминах, как правило,, модели будут иметь все коды, связанные с таблицами, их простыми или сложными отношениями (думайте о них как о SQL-запросах, включающих несколько таблиц), манипулирование данными/переменными для получения результата с использованием бизнес-логики.

контроллеры будет иметь код/указатели на соответствующие модели для требуемой работы.

вид примет пользовательский ввод / взаимодействие и отобразит полученный ответ.

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

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

j