couchdb / cloudant时间序列查询

时间:2016-08-25 12:43:08

标签: couchdb time-series cloudant

我有一个cloudant数据库,其中包含来自多个设备的一系列度量。 每个设备发送许多措施,但有三个是感兴趣的:温度,纬度和经度。 由于系统的设计,每个值都是一个单独的度量(我不能轻易地在插入时加入温度,纬度和经度),在数据库中我有一组这样的度量:

{
  "device": "foo",
  "name": "temperature",
  "date": <timestamp>,
  "value": <value>
},
{
  "device": "foo",
  "name": "latitude",
  "date": <timestamp>,
  "value": <value>
},
{
  "device": "foo",
  "name": "longitude",
  "date": <timestamp>,
  "value": <value>
},

所以从概念上讲,我有3个时间序列。 我想提取每个时间序列的最新度量,最好按设备分组。

类似的东西:

{
  device1: {
    "temperature": {
      date: <date>,
      value: <value>
    },
    "latitude": {
      date: <date>,
      value: <value>
    },
   "longitude": {
      date: <date>,
      value: <value>
   }
  },
  "device2": {
    ...
  }
}

我不期望这种语法准确,这只是我所期待的数据集的概念。

我可以一起加入位置测量,但问题是相同的:如何将每个设备的最后一个ts条目组合在一起?

1 个答案:

答案 0 :(得分:1)

首先,我会使用这样的数据结构:

{
    "type":"temperature",
    "date":"1472528116698",
    "value":"35",
    "device":"device1"
}

type属性可以是温度,纬度,经度。

然后你需要一些观点。就个人而言,我更喜欢通过类型获得一个_design文档,并且查询也会更容易。

例如,对于温度,你会有一个这样的_design文档:

{
   "_id": "_design/temperature",
   "_rev": "8-91e594df623063ed3ad7111cde09eecb",
   "language": "javascript",
   "views": {
       "byDevice": {
           "map": "function(doc) {\n    if ((doc.type + '').toLowerCase() === 'temperature' && doc.device)\n        emit(doc.device);\n}\n"
       },
       "lastestByDevice": {
           "map": "function(doc) {\n    if ((doc.type + '').toLowerCase() === 'temperature' && doc.device && doc.value)\n        emit(doc.device,doc.value);\n}\n",
           "reduce": "function(keys, values, rereduce) {\n    var max = Number.MIN_VALUE;\n    for (var i = 0; i < values.length; i++) {\n        var val = parseFloat(values[i]);\n        if (val > max)\n            max = val;\n    }\n    return max;\n}\n"
       }
   }
}

请求示例:

  

http://localhost:5984/db/_design/temperature/_view/latestByDevice?group_level=1&reduce=true

如果您使用具有reduce功能的最新设备,它将返回每个设备的最大值。我们这个例子,你应该能够有一个良好的开端。我不知道你是如何接收和建立数据的,但如果你更愿意按设备分组,那也是可能的。