Я часто видел шаблон 1, наиболее часто используемый для докладчиков Rails.
1) Зачем ведущему нужен контекст представления?
2) Между шаблоном 1 и шаблоном 2 шаблон 2 кажется проще, так как вам не нужно оборачивать весь код блоком. Почему это не используется чаще? Есть ли недостаток в использовании этого? по сравнению с шаблоном 1?
3) С шаблоном 3, почему люди вообще не используют этот шаблон?
Ведущий
module ApplicationHelper
def present(model, presenter_class=nil)
klass = presenter_class || "#{model.class}Presenter".constantize
presenter = klass.new(model, self)
yield(presenter) if block_given?
end
end
class UserPresenter < ApplicationPresenter
def full_name
"#{@model.first_name} #{@model.last_name}"
end
def birth_year
return nil unless @model.birthdate
@model.birthdate.year
end
def nickel_per_year
return nil unless @model.birthdate
difference = Date.today.year - birth_year
@view.number_to_currency(difference * 0.05)
end
end
class ApplicationPresenter < SimpleDelegator
def initialize(model, view)
@model, @view = model, view
super(@model)
end
end
Узор 1
Использование помощника докладчика в представлении с блоком
Вид
<% @users.each do |u| %>
<% present(u) do |user| %>
<tr>
<td><%= user.full_name %></td>
<td><%= user.email %></td>
<td><%= user.birthdate %></td>
<td><%= user.birth_year %></td>
<td><%= user.nickel_per_year %></td>
<td><%= link_to 'Show', user %></td>
<td><%= link_to 'Edit', edit_user_path(user) %></td>
<td><%= link_to 'Destroy', user, method: :delete, data: { confirm: 'Are you sure?' } %></td>
</tr>
<% end %>
<% end %>
Узор 2
Использование презентера в представлении и установка переменной
Вид
<% @users.each do |u| %>
<% user = UserPresenter.new(user, self) %>
<tr>
<td><%= user.full_name %></td>
<td><%= user.email %></td>
<td><%= user.birthdate %></td>
<td><%= user.birth_year %></td>
<td><%= user.nickel_per_year %></td>
<td><%= link_to 'Show', user %></td>
<td><%= link_to 'Edit', edit_user_path(user) %></td>
<td><%= link_to 'Destroy', user, method: :delete, data: { confirm: 'Are you sure?' } %></td>
</tr>
<% end %>
Узор 3
Используя презентатор в контроллере, предполагая, что вы можете передать контекст представления при использовании такого решения. https://github.com/endofunky/oprah
UserController
def show
@user = UserPresenter.new(User.find(params[:id]), view_context)
end
def index
@users = Users.all.map {|user| UserPresenter.new(user, view_context) }
end