gpt4 book ai didi

ruby-on-rails - 动态扩展 Virtus 实例属性

转载 作者:数据小太阳 更新时间:2023-10-29 06:50:05 25 4
gpt4 key购买 nike

假设我们有一个 Virtus 模型 User

class User
include Virtus.model
attribute :name, String, default: 'John', lazy: true
end

然后我们创建该模型的一个实例并从 Virtus.model 扩展以动态添加另一个属性:

user = User.new
user.extend(Virtus.model)
user.attribute(:active, Virtus::Attribute::Boolean, default: true, lazy: true)

当前输出:

user.active? # => true
user.name # => 'John'

但是当我尝试获取 attributes 或通过 as_json(或 to_json)或 Hash< 将对象转换为 JSON 时 通过 to_h 我只得到后扩展属性 active:

user.to_h # => { active: true }

是什么导致了这个问题,我怎样才能在不丢失数据的情况下转换对象?

附言

我找到了 github issue , 但似乎终究没有修复(那里推荐的方法也不太稳定)。

最佳答案

根据 Adrian 的发现,这里有一种方法可以修改 Virtus 以实现您想要的功能。所有规范都通过此修改。

从本质上讲,Virtus 已经有了父级 AttributeSet 的概念,但只有在 class 中包含 Virtus.model 时才会这样。 .我们也可以扩展它以考虑实例,甚至允许在同一对象中使用多个 extend(Virtus.model)(尽管这听起来不是最优的):

require 'virtus'
module Virtus
class AttributeSet
def self.create(descendant)
if descendant.respond_to?(:superclass) && descendant.superclass.respond_to?(:attribute_set)
parent = descendant.superclass.public_send(:attribute_set)
elsif !descendant.is_a?(Module)
if descendant.respond_to?(:attribute_set, true) && descendant.send(:attribute_set)
parent = descendant.send(:attribute_set)
elsif descendant.class.respond_to?(:attribute_set)
parent = descendant.class.attribute_set
end
end
descendant.instance_variable_set('@attribute_set', AttributeSet.new(parent))
end
end
end

class User
include Virtus.model
attribute :name, String, default: 'John', lazy: true
end

user = User.new
user.extend(Virtus.model)
user.attribute(:active, Virtus::Attribute::Boolean, default: true, lazy: true)

p user.to_h # => {:name=>"John", :active=>true}

user.extend(Virtus.model) # useless, but to show it works too
user.attribute(:foo, Virtus::Attribute::Boolean, default: false, lazy: true)

p user.to_h # => {:name=>"John", :active=>true, :foo=>false}

也许这值得为 Virtus 做一个 PR,你怎么看?

关于ruby-on-rails - 动态扩展 Virtus 实例属性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44046603/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com