2017-12-18 12 views
1

私はIoTデバイスから連続して受け取った測定値のコレクションを扱っています。各測定には、次の文書スキーマがあります。複数のMongoDBドキュメントを1つにマージするには?

デバイスがどのようにプログラムされているかに応じて、デバイスの属性ごとに異なる測定値があります。デバイスがN秒ごとにデータを送信すると、N秒ごとにデバイスの属性としてドキュメントが挿入されます。 「recvTime」フィールドに同じ時刻インスタンスを持つすべてのドキュメント。

私の問題は、特定の時間に対応するすべての測定データを1つのドキュメントで折りたたみたいということです。この方法では、デバイス上の属性と同じ数のドキュメントではなく、N秒ごとにすべてのデバイス測定値を持つドキュメントを作成します。このようなものに

{ 
    "_id" : ObjectId("58e3c885713c09001a0c2125"), 
    "recvTime" : ISODate("2017-04-18T16:23:38.928Z"), 
    "entityId" : "t01", 
    "entityType" : "Thing", 
    "attrName" : "Temperature", 
    "attrType" : "text", 
    "attrValue" : "32.5" 
}, 
{ 
    "_id" : ObjectId("58e3c885713c09001a0c2125"), 
    "recvTime" : ISODate("2017-04-18T16:23:38.928Z"), 
    "entityId" : "t01", 
    "entityType" : "Thing", 
    "attrName" : "Preassure", 
    "attrType" : "text", 
    "attrValue" : "512" 
} 

:私はこれを変換したい二つの属性温度preassureと例えば

{ 
    "_id" : ObjectId("58e3c885713c09001a0c2125"), 
    "recvTime" : ISODate("2017-04-18T16:23:38.928Z"), 
    "entityId" : "t01", 
    "entityType" : "Thing", 
    "Temperature" : "32.5", 
    "Preassure" : "512" 
} 

が使用してこれを行う方法はありますMongo Aggregation Frameworkでのクエリのみ?私はアプリケーション内でそれをする必要はありません。

ありがとうございます。

答えて

0

以下の集計は3.6で使用できます。

$group$$ROOT$pushという完全なタイムスタンプドキュメントをグループ化するには、 $filter

$objectToArrayは、グループ化されたドキュメントをマージする$reduceオペレータに$arrayToObject$mergeObjects続いて名前を変更するために必要なキーをフィルタリングします。

$replaceRootトップレベルにマージされたドキュメントを昇格させる。

[{"$group":{ 
    "_id":"$recvTime", 
    "data":{"$push":"$$ROOT"} 
}}, 
{"$replaceRoot":{ 
    "newRoot":{ 
    "$reduce":{ 
     "input":"$data", 
     "initialValue":{}, 
     "in":{ 
     "$mergeObjects":[ 
      {"$arrayToObject":{ 
      "$filter":{ 
       "input":{"$objectToArray":"$$this"}, 
       "cond":{"$not":{"$in":["$$this.k",["attrName","attrValue","attrType"]]}} 
      } 
      }}, 
      {"$arrayToObject":[[{"k":"$$this.attrName","v":"$$this.attrValue"}]]}, 
      "$$value" 
      ] 
     } 
    } 
    } 
}}] 
+0

ありがとう!私はあなたの提案を試みます、 –

関連する問題