项目BsonDocument没有查询集合

时间:2017-08-15 16:56:51

标签: mongodb bson

如何在不查询集合的情况下将一个BsonDocument投影到新实例?

输入:BsonDocumentnew string[] { "_id", "meta.name", "type" }

输出:BsonDocument仅填充上述元素

1 个答案:

答案 0 :(得分:0)

痒划伤

输入

{
  "_id" : ObjectId("58b454f40960a1788ef48ebc"),
  "schema" : {
    "id" : "asset",
    "version" : {
      "major" : 1,
      "minor" : 0
    }
  },
  "type" : "asset",
  "meta" : {
    "name" : "Most Amazing Product",
    "type" : null,
    "legacy" : {
      "url" : "https://s3.amazonaws.com/bucket_name/guid"
    }
  },
  "content" : {
    "is_s3" : true,
    "s3_bucket" : "bucket_name",
    "s3_key" : "guid.doc",
    "url" : "https://s3.amazonaws.com/guid.doc"
  },
  "modified-date" : ISODate("2017-08-09T15:25:57.972Z"),
  "modified-by" : "api"
}

nuget: MongoDB.Driver 2.4.4
using MongoDB.Bson;
using MongoDB.Bson.Serialization;
using MongoDB.Bson.IO;

BsonDocument original = BsonDocument.Parse(@"{ ""_id"" : ObjectId(""58b454f40960a1788ef48ebc""), ""schema"" : { ""id"" : ""asset"", ""version"" : { ""major"" : 1, ""minor"" : 0 } }, ""type"" : ""asset"", ""meta"" : { ""name"" : ""Most Amazing Product"", ""type"" : null, ""legacy"" : { ""url"" : ""https://s3.amazonaws.com/bucket_name/guid"" } }, ""content"" : { ""is_s3"" : true, ""s3_bucket"" : ""bucket_name"", ""s3_key"" : ""guid.doc"", ""url"" : ""https://s3.amazonaws.com/guid.doc"" }, ""modified-date"" : ISODate(""2017-08-09T15:25:57.972Z""), ""modified-by"" : ""api"" }");

string[] fields = new[] { "_id", "meta.name", "type" };

BsonDocument projection = new BsonDocument();
foreach (var fieldName in fields)
{
    BsonDocument source = original;
    BsonDocument target = projection;
    string[] parts = fieldName.Split(new[] { "." }, StringSplitOptions.RemoveEmptyEntries);
    for (int i = 0; i < parts.Length; i++)
    {
        string currentName = parts[i];
        if (i == parts.Length - 1)
        {
            if(source.Contains(currentName))
                target[currentName] = source[currentName];
        }
        else
        {
            // Does the source have a current property at this level
            if (source.Contains(currentName))
            {
                // first time this has been visited on target
                if (target.Contains(currentName) == false)
                {
                    target.Add(currentName, new BsonDocument());
                }
                source = source[currentName] as BsonDocument;
                target = target[currentName] as BsonDocument;
            }
            else
            {
                // no need to go any further if the source doesn't have the property specified
                break;
            }
        }
    }
}

结果

{
  "_id" : ObjectId("58b454f40960a1788ef48ebc"),
  "meta" : {
    "name" : "Most Amazing Product"
  },
  "type" : "asset"
}