我正在使用 data_mapper/sinatra 并尝试使用 attr_accessor 创建一些属性。示例代码如下:
require 'json'
class Person
include DataMapper::Resource
property :id, Serial
property :first_name, String
attr_accessor :last_name
end
ps = Person.new
ps.first_name = "Mike"
ps.last_name = "Smith"
p ps.to_json
产生以下输出:
"{\"id\":null,\"first_name\":\"Mike\"}"
显然,我希望它同时提供名字和姓氏属性。关于如何让它以人们期望的方式工作以便我的 json 具有所有属性的任何想法?
此外,请随意解释为什么我的期望(我会获得所有属性)不正确。我猜测某些内部属性列表没有添加 attr_accessor 实例变量或其他内容。但即便如此,为什么呢?
最佳答案
Datamapper 有自己的序列化库 dm-serializer
,提供 to_json
任何 Datamapper 资源的方法。如果您需要带有 require 'data_mapper'
的 Datamapper在您的代码中,您正在使用 data_mapper
meta-gem那requires dm-serializer as part of it’s set up .
to_json
方法由dm-serializer
提供仅序列化对象的 Datamapper 属性(即您使用 property
指定的属性),而不是“正常”属性(您使用 attr_accessor
定义的属性)。这就是为什么你会得到 id
和first_name
但不是last_name
.
为了避免使用 dm-serializer
您需要明确要求您需要的那些库,而不是依赖 data_mapper
。您至少需要dm-core
也许还有其他。
“正常”json
库在默认 to_json
中不包含任何属性调用一个对象,它只使用对象 to_s
方法。因此在这种情况下,如果替换 require 'data_mapper'
与 require 'dm-core'
,你会得到类似 "\"#<Person:0x000001013a0320>\""
的信息.
要创建您自己的对象的 json 表示形式,您需要创建自己的 to_json
方法。一个简单的例子就是在 json 中硬编码你想要的属性:
def to_json
{:id => id, :first_name => first_name, :last_name => last_name}.to_json
end
您可以创建一个方法来查看对象的属性和属性,并从中创建适当的 json,而不是以这种方式对它们进行硬编码。
请注意,如果您创建自己的 to_json
您仍然可以调用 require 'data_mapper'
的方法,你的to_json
将取代 dm-serializer
提供的。事实上dm-serializer
还添加了 as_json
method您可以使用它来创建组合 to_json
方法,例如:
def to_json
as_json.merge({:last_name => last_name}).to_json
end
关于ruby - data_mapper、attr_accessor 和序列化 仅序列化属性而不序列化 attr_accessor 属性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12024298/