Skip to content

2015-12-06 #18

@yorkie

Description

@yorkie

typify-json

今天完成了一个新库:https://github.com/weflex/typify-json ,创造这个库的原因起于 Fibula.js 的开发过程中,我使用了如下的代码:

const exec = require('child_process').execSync;
exec(`mongo --eval "db.foo.insert(${JSON.stringify(input)})"`);

如果input的值包含有Date这样的值,那么JSON.stringify的时候就会默认地把Date转换成字符串再插入数据库中了,这个不是我们想要的结果。

因此,typify-json 使用了与JSON类似的 API:

const typifyJSON = require('typify-json');
const exec = require('child_process').execSync;
exec(`mongo --eval "db.foo.insert(${typifyJSON.stringify(input)})"`);

这样如果我们输入:

{
  "date": new Date()
}

那它等价于如下的"Shell语句":

> db.foo.insert({"date":new Date()})

在开发这个库的过程中,我尝试过很多方案:

  1. 使用JSON.stringify(input, replacer)的方式去重写,不过后来发现最后我所需要的并不是一个标准的 JSON,因此无法通过这种方法得出;
  2. 在上一个方案未果后,决定试试Date的值使用一个特殊的散列值存储在一个WeakMap内,然后在最后使用正则换掉,不过这种方法不够直观简单,WeakMap的API也不够稳定,于是作罢。

在尝试方法2时,还发现了JSON.stringifyreplacer函数有一个比较奇怪的特性,比如以下代码:

JSON.stringify({
  foo: {
    date: new Date()
  }
}, function (key, val) {
  console.log(key, val);
});

key为"date"的时候,发现对应的val已经不是一个字符串类型了,所以只能在上一层,即key等于"foo"的时候,来判断。

Metadata

Metadata

Assignees

No one assigned

    Labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions