我正在使用在一个列中包含序列化值的Rails数据库。这些值应该是常规的Hash
,但是由于不正确地清除了参数,它们被存储为HashWithIndifferentAccess
或Parameters
。例如,一个列条目如下所示:
--- !ruby/object:ActionController::Parameters
parameters: !ruby/hash:ActiveSupport::HashWithIndifferentAccess
windowHeight: 946
documentHeight: 3679
scrollTop: 500
permitted: false
我想用Python的yaml
实现来阅读它,但是当我尝试这样做时,我得到了:
*** yaml.constructor.ConstructorError: could not determine a constructor for the tag '!ruby/object:ActionController::Parameters'
in "<unicode string>", line 1, column 5:
--- !ruby/object:ActionController::P ...
^
因此,由于某种原因,它需要一个构造函数。但是很显然,该值本身只是一个常规字典。我怎么还能读呢?
答案 0 :(得分:1)
您可以使用PyYAML解析器的add_constructor(loader, node)
函数,该函数可让您为无法识别的对象类型实现自定义构造函数。
在该构造函数中,可以调用函数loader.construct_pairs(node)
以从原始节点内容中获取键值元组。使用字典理解,我们可以创建原始字典。
由于条目是嵌套的,因此我们必须将构造函数应用于这两种对象类型。
完整的示例如下:
import yaml
def convert_entry(loader, node):
return { e[0]: e[1] for e in loader.construct_pairs(node) }
yaml.add_constructor('!ruby/hash:ActiveSupport::HashWithIndifferentAccess', convert_entry)
yaml.add_constructor('!ruby/object:ActionController::Parameters', convert_entry)
yaml.load(input_string)
这是somehow documented,但很难找到很多示例。