按照插入的顺序保存json数据 - django

时间:2013-09-27 13:28:54

标签: django json

我的django应用中有一个JSONField。数据可能如下所示:

{
"05/2013" : 101,
"04/2013" : 100.9,
"03/2013" : 100.5,
"02/2013" : 100.3,
"01/2013" : 100.3
}

这是一个价格指数。当我从字段中获取数据时,我想保留插入数据的顺序。

我查看了使用OrderedDict的{​​{3}}。 Dict(我猜)使用词法排序,因此输出会以这种格式丢失它的原始顺序。 我尝试将日期翻转为格式2012-012012-02等等,但输出仍然是加扰的。部分输出:

"2011-08":104.2,
  "2011-09":104,
  "2011-02":102.3,
  "2011-03":102.5,
  "2011-01":102,
  "2011-06":104,
  "2011-07":103.7,
  "2011-04":103.1,
  "2011-05":103.6,
  "2013-04":100.9,
  "2013-05":101,
  "2012-10":106,
  "2012-11":105.5,

我不确定这是什么类型的,我在寻找解决方案方面落后一步。 欣赏任何想法。

修改 这是模型字段声明

from jsonfield import JSONField
...
values = JSONField(null=True, blank=True, verbose_name=_("values"),load_kwargs={'object_pairs_hook': collections.OrderedDict})
...

2 个答案:

答案 0 :(得分:2)

这是一个有趣的问题,特别是因为无法保证javascript对象,JSON本身或python dict中的字段顺序

考虑到上述情况,如果我们将在数据库+序列化+反序列化+表示的某种组合中正确设置我们的订单,它将仅适用于此(非常窄)配置

e.g。 django-jsonfield序列化(默认情况下)JSON到文本字段,所以在数据库级别它可能是安全的,但从少数json模块(json,simplejson,ujson,yajl)的反序列化完成到字典,然后所有订单都丢失< / p>

django 1.9引入了本机postgresql JSONField - 在这里你甚至没有数据库级别的保证,因为数据在内部存储为jsonb - 二进制优化的JSON

在我看来,不是搜索序列化到OrderedDict,而是更改数据的存储方式,如果订单很重要 - 让我们将数据存储在表中:

[{date: "05/2013", price: 101},
 {date: "04/2013", price: 100.9},
 {date: "03/2013", price: 100.5},
 {date: "02/2013", price: 100.3},
 {date: "01/2013", price: 100.3}]

我们保证订单,数据可以线性处理,我们不依赖于特殊实现。

答案 1 :(得分:2)

如果您需要保持JSONFIeld中的键顺序,则可以为本地JSONField覆盖db_type以使用json而不是jsonb:

class RawJSONField(JSONField):

    def db_type(self, connection):
        return 'json'

来自Postgres documentation

主要的实际差异是效率之一。 json数据类型存储输入文本的精确副本,处理函数必须在每次执行时重新解析; jsonb数据以分解后的二进制格式存储,由于增加了转换开销,因此输入速度稍慢,但由于不需要解析,因此处理速度明显更快。 jsonb还支持索引编制,这可能是一个很大的优势。

如果您不需要基于JSON blob的内容对数据进行索引,并且确实需要维护实例化字典时创建的键顺序(也许您正在使用进行假设的客户端库) JSON键顺序),那么这可能对您有用。