我正在为应用程序的工厂生成器开发REST Api,以允许也使用REST创建模型实例,我想知道如何允许模型的嵌套属性而无需对属性进行硬编码。
假设我有一个名为“餐厅”的模型
class Restaurant < ApplicationRecord
has_one :cost, dependent: :destroy, inverse_of: :grant
has_one :address, dependent: :destroy, inverse_of: :grant
has_one :owner, dependent: :destroy, inverse_of: :grant
accepts_nested_attributes_for :cost, :address, :owner
...
其中的关联也具有其自己的模型属性和一个工厂
FactoryGirl.define do factory :restaurant, class Restaurant do
after(:create) do |restaurant|
restaurant.cost = assign_attributes(attributse_for(:cost_factory))
restuarnat.address = assign_attributes(attributes_for(:address_factory))
restaurant.owner = assign_attributes(attributes_for(:owner_factory))
end
...
end
,其中的嵌套关联也有自己的工厂。我正在以这种格式通过REST API传递JSON正文
{
"restaurant": {
"cost_attributes": {
"staff": 123
"tables": 123
}
}
我知道我可以通过这些方式允许属性
params.permit(:restaurant)
.permit(cost_attributes: [:staff, :tables],
address_attributes: [:address_attr_1],
owner_attributes: [:owner_attr_1]]
但是我正在使用的实际模型有很多关联。对所有内容进行硬编码将很痛苦。 有没有办法我可以允许参数通过而不是在控制器中进行硬编码?目前,这就是我的想法
params.permit(Restaurant.nested_attributes_options.keys)
但是显然这行不通。
答案 0 :(得分:1)
这是收集嵌套属性名称的一种方法:
mod = Restaurant
nested_attributes = mod.nested_attributes_options.keys.each_with_object({}) do |association, hash|
hash[:"#{association}_attributes"] = association.
to_s.
classify.
constantize.
send(:attribute_names).
map(&:to_sym)
end
params.permit(:restaurant).permit(nested_attributes)
此代码有点通用,请随时根据您的特定用例进行修改。
答案 1 :(得分:0)
要改善您的答案,以下是一种使用反射递归收集所有深层嵌套属性名称的方法:
IF'S