尝试创建一个has_one
关系的新记录(并正确指定了所有inverse_of
)时,表单被禁用:
此协会的代码如下:
class Visit < ActiveRecord::Base
has_one :mri, dependent: :destroy, inverse_of: :visit
accepts_nested_attributes_for :mri, update_only: true
...
end
class Mri < ActiveRecord::Base
belongs_to :visit, inverse_of: :mri, touch: true
...
end
当我用accepts_nested_attributes
删除整行时,我得到一个缺失的表单,没有:
使用rails_admin配置禁用嵌套表单(如下所示)会产生相同的结果。
config.model Visit do
edit do
configure :mri do
nested_form false
end
end
end
答案 0 :(得分:4)
这些问题来自于Rails Admin,IMO的两个漏洞。
了解Rails Admin有两种关联形式是很有用的。一个是经典的(打开一个创建窗口),另一个是&#34; nested_form&#34;在页面中显示表单。 nested_form
参数可以直接更改,如上面的问题所示,但Rails管理员会自动将其设置为accepts_nested_attributes_for
中包含的关联。
第一个错误是accepts_nested_attributes_for: ..., update_only: true
得到&#34;解释&#34;通过rails Admin as&#34;我不想在创建时给出参数&#34;。这种解释似乎wrong,因为update_only
在rails中更改的行为仅涉及对象更新,并且不会阻止在创建时传递嵌套参数。此外,我原本期望回归经典形式而不是完全禁用的形式。
解决此问题的一种快速且通常有害的方法是将update_only
更改为默认false
。
第二个错误更令人惊讶,因为&#39;在你脸上&#39;。如shown in the wiki,has_one
关系的经典(非嵌套)关联表单如果您没有指定自己的ID设置者和获取者,则无法正确初始化。因此,如果您没有nested_attributes,则需要在模型中包含这样的行:
class Visit < ActiveRecord::Base
has_one :mri, dependent: :destroy, inverse_of: :visit
def mri_id
self.mri.try :id
end
def mri_id=(id)
self.mri = Mri.find_by_id(id)
end
...
end
最后,利用我们对第一个bug的理解,为我的初始问题提供了最优雅的解决方案。 Rails管理模板的source code显示Rails管理员为字段对象的update_only
属性存储nested_form
参数。我们可以直接配置它以实现所需的行为(应该是默认的imo):
config.model Visit do
edit do
configure :mri do
nested_form[:update_only] = false
end
end
end
PS:这个帖子相当长,但这个简单的问题最终导致了一个兔子洞,所以我想分享我的发现 - 我希望它有所帮助。非常感谢RA开发人员,他们为Rails提供了功能最多,功能最丰富的管理门户之一(曾经)。我已经打开了a couple个问题。