简单地说,联系人可以拥有各种相关的时间窗口,这些时间窗口可能是也可能不是活动时间表。即:
模型
class Contact < ActiveRecord::Base
has_many :schedules
has_many :time_windows, :through => :schedules
accepts_nested_attributes_for :schedules, :allow_destroy => true
end
class TimeWindow < ActiveRecord::Base
has_many :schedules
has_many :contacts, :through => :schedules
end
class Schedule < ActiveRecord::Base
belongs_to :contact
belongs_to :time_window
end
查看
<% TimeWindow.all.each do |tw| %>
<% schedule = Schedule.find_by_contact_id_and_time_window_id(@contact.id, tw.id)
schedule ||= Schedule.new %>
<p>
<%= f.label tw.description %>
<%= hidden_field_tag "contact[schedules_attributes][][id]", schedule.id %>
<%= check_box_tag "contact[schedules_attributes][][time_window_id]",
tw.id, @contact.time_windows.include?(tw) %>
<%= check_box_tag "contact[schedules_attributes][][active]", nil,
schedule.active %>
</p>
<% end %>
这提交了类似的内容:
Parameters: { "commit" => "Update", "contact" => {
"group_ids" => ["2"], "enabled" => "1",
"schedules_attributes" => [ { "time_window_id"=>"1", "id"=>"46"},
{ "time_window_id" => "2", "id" => "42", "active" => "on" },
{ "time_window_id" => "3", "id" => "43"},
{ "time_window_id" => "4", "id" => "44", "active" => "on"}],
"last_name" => ...
控制器中的更新操作基本上是库存,除了处理另一个我使用Advanced Rails Recipes一书中的“处理多个模型”示例编写的相关模型的另一个实例。
根据this API doc,我认为上述情况应该有效。但是,没有关于计划的更新。这显示在服务器日志中:
[4;35;1mSchedule Update (0.2ms)[0m [0mUPDATE `schedules` SET `updated_at` = '2010-09-30 20:39:49', `active` = 0 WHERE `id` = 42[0m
[4;36;1mSchedule Update (0.1ms)[0m [0;1mUPDATE `schedules` SET `updated_at` = '2010-09-30 20:39:49', `active` = 0 WHERE `id` = 44[0m
(NetBeans给了我那些愚蠢的“[0m”的输出。我不知道那里有什么问题。)
SQL显示“active”布尔字段在检查时被设置为0。如何才能正确设置有效位?
作为后续,我将如何组织这个以完全取消“连接”?我想我需要从表单中提交一个:_delete with Schedule,但是如果涉及一个复选框,我将如何有条件地执行此操作?
感谢您提供的任何帮助。 Rails对我来说是一个巨大的主题,我想“做对”。我真的很接近这里,但必须有一种方法来做到这一点 - 不仅仅是正确的 - 而是优雅的。对于正确的Rails来说,视图代码感觉太麻烦了。 ; - )
答案 0 :(得分:0)
我一直在尝试不同的方法来解决这个问题,而且我已经想出了这个,这是有效的。大多。唯一的问题是它没有处理每个“时间窗口”没有“时间表”。表单将呈现,我将获得一个禁用的check_box(以防止我尝试删除不存在的东西),但我没有办法将其添加回去,并且在没有它的情况下提交将抛出params hash(并导致Rails给我一个“Expected Hash(got Array)”错误)
<% TimeWindow.all.each do |tw| %>
<% schedule = Schedule.find_by_contact_id_and_time_window_id(@contact.id, tw.id)
schedule ||= Schedule.new %>
<% f.fields_for "schedules_attributes[]", schedule do |sf| %>
<p>
<%= sf.label tw.description %>
<%= sf.hidden_field :id %>
<%= sf.check_box :_destroy, :disabled => schedule.new_record? %>
<%= sf.check_box :active %>
</p>
<% end %>
<% end %>
请注意,“schedules_attributes []”数组会自动为您提供HTML中大括号内的现有ID(这很好),但是_attributes哈希期望与其他属性一起使用“id”以便有意义子哈希。
我在这里学到的一个重要经验是,“check_box_tag”方法没有(似乎)给我一个配对的隐藏字段,让Rails在未经检查的情况下进行解析。我原以为这个。手动添加一个就搞得一团糟,这让我最终放入了“fields_for”方法,并在找到合适的语法之前尝试了许多化身,以便得到我想要的东西。
我已经意识到我的模型在这个设置中不太合适,所以我要改变它,但是我非常接近这个答案,我想至少能够达到这个目的。在我开始前看到了结束。