在Rails 5中,我有一个带有属性的模型,其值永远不会直接设置,而是始终在before_save
回调中计算。我想保护这个属性不被模型外部更新,所以像f一样调用。即update_attribute()
会失败。我在模型中使用attr_readonly
来实现我想要的东西,并且它工作得很好,直到我意识到它阻止所有更新!也来自模型本身。因为根据Rails API docs这是正确的行为,拒绝修改特定属性但仅限于外部的最佳方法是什么?
答案 0 :(得分:1)
您可以覆盖设置者。在模型上:
def protected_attr_name=(val)
# raise SomeException
end
这会禁用:
model.protected_attr_name = "value" # => raise exception
model.update_attributes(protected_attr_name: "value") # => raise exception
然后在你的before_save
方法/块中
write_attribute(:protected_attr_name, calculated_value)
与attr_readonly
一样,您可以选择不引发异常,而不是做任何事情。这可能会让处理相同代码库的其他人感到困惑/沮丧,并且可能是非常明显的行为。
此外 - 如果在before_save
中计算始终,请考虑是否需要此保护,或者更清晰的属性命名是否可以有效地解决问题。