【问题标题】:How to store hierarchical data through FIWARE Cygnus with MongoDB如何通过 FIWARE Cygnus 和 MongoDB 存储分层数据
【发布时间】:2018-04-26 11:06:48
【问题描述】:

我已经部署了一个 FIWARE 配置来接收来自 TheThingsNetwork 的 MQTT 消息。该配置使用 IoTAgent-JSON、Orion 和 Cygnus,以及用于 Cygnus 的 MongoDB 后端。

消息已正确持久化到 MongoDB。不幸的是,消息数据具有层次结构,消息的某些部分在 MongoDB 中显示为字符串,而不是嵌入的子文档。

这使得查询数据变得困难。

详情如下:

消息格式由TTN MQTT Data API定义。

我在 Orion 上定义了一个实体类型如下:

curl http://localhost:1026/v2/entities -X POST -H "content-type: application/json" -H "fiware-service: myservice" -H "fiware-servicepath: /mypath" -d @- << EOF
{
    "id": "TtnMqttMessage",
    "type": "TtnMqttMessge",
    "app_id": { "type": "Text", "value": "my-app-id" },
    "dev_id": { "type": "Text", "value": "my-dev-id" },
    ...
    "metadata": { "type": "StructuredValue", "value": {
        "airtime": 46336000,
        "time": "1970-01-01T00:00:00Z",
        ...
        "gateways": 
        [ 
            {
                "gw_id": "gw1",
                "timestamp": 12345,
                "time": "1970-01-01T00:00:00Z",
                ...
                "altitude": 6
            }
        ]
    } }
}
EOF

特别是,在上面的配置中,metadata 是一个结构化值,包含gateways 的数组。

在 IoTAgent-JSON 上,提供服务和设备:

curl http://localhost:4041/iot/services -X POST -H "content-type: application/json" -H "fiware-service: myservice" -H "fiware-servicepath: /mypath" -d @- << EOF
{
    "services": [
        {
            "apikey": "my_app_id",
            "entity_type": "TtnMqttMessage",
            "resource": "/iot/json"
        }
    ]
}
EOF

curl http://localhost:4041/iot/devices?options=keyValues -X POST -H "content-type: application/json" -H "fiware-service: myservice" -H "fiware-servicepath: /mypath" -d @- << EOF
{
    "devices": [{
        "device_id": "my_device_id",
        "entity_name": "TtnMqttMessage",
        "entity_type": "TtnMqttMessage",
        "timezone": "Europe/Zurich",
        "transport": "MQTT"
    }]
}
EOF

最后,建立了从 Orion 到 Cygnus 的通知订阅:

curl http://localhost:1026/v1/subscribeContext -H "content-type: application/json" -H "fiware-service: myservice" -H "fiware-servicepath: /mypath" -X POST  -d @- << EOF
{
    "entities": [
        {
            "type": "TtnMqttMessage",
            "isPattern": "false",
            "id": "TtnMqttMessage"
        }
    ],
    "attributes": [ "app_id", "dev_id", "hardware_serial", "port", "counter",  "is_retry",  "confirmed", "payload_raw", "payload_fields", "metadata" ],
    "reference": "http://cygnus:5050/notify",
    "duration": "P100Y",
    "notifyConditions": [
        {
            "type": "ONCHANGE",
            "condValues": [ "app_id", "dev_id", "payload_raw", "counter" ]
        }
    ]
}
EOF

收到的消息被持久化到MongoDB:

> mongo
> ...
> db['..collectionname...'].findOne();
{
    "_id" : ObjectId("5adf0b904cedfd001cd72113"),
    "recvTime" : ISODate("2018-04-24T10:48:47.605Z"),
    "app_id" : "my-app-id",
    "confirmed" : "false",
    "counter" : "2",
    "dev_id" : "my-dev-id",
    "hardware_serial" : "0102030405060708",
    "is_retry" : "false",
    "metadata" : "{\"airtime\":4.6336e+07,\"time\":\"1970-01-01T00:00:00Z\",\"frequency\":868.1,\"modulation\":\"LORA\",\"data_rate\":\"SF7BW125\",\"bit_rate\":50000,\"coding_rate\":\"4/5\",\"latitude\":52.2345,\"longitude\":6.2345,\"altitude\":2,\"gateways\":[{\"gw_id\":\"gw1\",\"timestamp\":12345,\"time\":\"1970-01-01T00:00:00Z\",\"channel\":0,\"rssi\":-25,\"snr\":5,\"rf_chain\":0,\"latitude\":52.1234,\"longitude\":6.1234,\"altitude\":6}]}",
    "payload_fields" : "{}",
    "payload_raw" : "AQIDBA",
    "port" : "1"
}

如上所示,属性metadata,特别是它包含的数组gateways,存储为字符串而不是JSON 子文档。

如何以易于查询的格式保存数据?例如。

  • metadata 下嵌入子文档(非规范化形式)
  • 或以规范化形式,其中metadata 是引用消息主文档的单独文档。

【问题讨论】:

    标签: mongodb fiware fiware-orion fiware-cygnus


    【解决方案1】:

    创建的实体看起来结构良好,我注意到您使用 v2 创建实体,但您订阅使用 v1 接收通知,我知道这是正确的方法,但可能是由于这个原因产生了错误的行为.

    【讨论】:

    • 亲爱的 anmunoz,感谢您的建议。我使用 v2 创建了订阅。这需要使用"attrsFormat": "legacy",因为据我所知,Cygnus 只实现了 NGSIv1。不幸的是,MongoDB 中的结果数据与以前相同。我还尝试将normalizedkeyValuesvalues 作为 attrsFormat。但是,这导致订阅期间出现错误。
    • 您好 Juergen,我一直在测试,您是对的,使用 v2 订阅并不能解决问题。正如您所提到的,Cygnus 仅实现了 NGSIv1,它解决了将元数据字段存储为 JSON 对象的问题。目前,我们正在努力更新 Cygnus 来以本地方式管理 NGSIv2,但它仍在进行中。一旦我们有新版本可用,我会告诉你。
    • 非常感谢您的所有努力。目前,我编写了一个脚本来解析和处理 FIWARE 外部的 JSON 文本。希望 Cygnus 更新发布时不再需要它。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-03-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多