如何检查 BsonDocument 中的嵌套 属性 - 包含不起作用
How to check for nested property in BsonDocument - Contains doesn't work
当我编写代码来获取嵌套的 属性 时,当整个路径不存在时它会失败 - 这很公平
bsonDoc["Meeting"]["Session"]["Time"]
我看不出有什么方法可以防止这种情况发生,写
bsonDoc.Contains("Meeting.Session.Time")
returns false
即使它存在
写 bsonDoc.Contains("Time")
也 returns 失败,即使它确实存在,所以它甚至不能检查字段 属性,如果它是嵌套的......?
文档甚至代码都不知道如何做我需要的事情。不确定是否可能。
有没有办法为嵌套的 bson 文档属性编写保护子句 - 即 BsonDocument class 是否具有嵌套的键检查机制?
我认为 BsonDocument
中没有任何方法支持使用嵌套的 属性.
获取 element/value
但是你可以实现logic/extension方法来处理:
概念:
用'.'分割键。
First-level 搜索。
2.1 首先 chainKey
将从 BsonDocument
通过 TryGetValue
搜索。
2.2 如果键已经存在,@value
(BsonValue
) 将包含值(查询嵌套级别时需要)。
2.3 如果key不存在,则跳出循环逻辑
Second-level 或进一步搜索
3.1 概念与2相同,只是会从BsonValue
开始搜索(如2.2所述)。
public static class BsonDocumentExtensions
{
public static bool TryGetChainedValue(this BsonDocument doc, string key, out BsonValue @value)
{
@value = default;
// Get key, value from passed BsonDocument for first time, then refer to BsonValue to get key, value for nested property
bool first = true;
try
{
if (String.IsNullOrWhiteSpace(key))
return false;
string[] chainedKeys = key.Split(".").ToArray();
bool hasKey = false;
foreach (var chainKey in chainedKeys)
{
if (first)
{
hasKey = doc.TryGetValue(chainKey, out @value);
first = false;
}
else
{
hasKey = (@value.ToBsonDocument()).TryGetValue(chainKey, out @value);
}
// Throw exception if key not existed.
if (!hasKey)
throw new Exception();
}
return true;
}
catch
{
@value = default;
return false;
}
}
}
上面的概念和下面的多重if逻辑是一样的:
if (doc.TryGetValue("Meeting", out BsonValue meetingValue))
{
if ((meetingValue.ToBsonDocument()).TryGetValue("Session", out BsonValue sessionValue))
{
if ((sessionValue.ToBsonDocument()).TryGetValue("Time", out BsonValue timeValue))
{
Console.WriteLine(timeValue);
}
}
}
当我编写代码来获取嵌套的 属性 时,当整个路径不存在时它会失败 - 这很公平
bsonDoc["Meeting"]["Session"]["Time"]
我看不出有什么方法可以防止这种情况发生,写
bsonDoc.Contains("Meeting.Session.Time")
returns false
即使它存在
写 bsonDoc.Contains("Time")
也 returns 失败,即使它确实存在,所以它甚至不能检查字段 属性,如果它是嵌套的......?
文档甚至代码都不知道如何做我需要的事情。不确定是否可能。
有没有办法为嵌套的 bson 文档属性编写保护子句 - 即 BsonDocument class 是否具有嵌套的键检查机制?
我认为 BsonDocument
中没有任何方法支持使用嵌套的 属性.
但是你可以实现logic/extension方法来处理:
概念:
用'.'分割键。
First-level 搜索。
2.1 首先
chainKey
将从BsonDocument
通过TryGetValue
搜索。2.2 如果键已经存在,
@value
(BsonValue
) 将包含值(查询嵌套级别时需要)。2.3 如果key不存在,则跳出循环逻辑
Second-level 或进一步搜索
3.1 概念与2相同,只是会从
BsonValue
开始搜索(如2.2所述)。
public static class BsonDocumentExtensions
{
public static bool TryGetChainedValue(this BsonDocument doc, string key, out BsonValue @value)
{
@value = default;
// Get key, value from passed BsonDocument for first time, then refer to BsonValue to get key, value for nested property
bool first = true;
try
{
if (String.IsNullOrWhiteSpace(key))
return false;
string[] chainedKeys = key.Split(".").ToArray();
bool hasKey = false;
foreach (var chainKey in chainedKeys)
{
if (first)
{
hasKey = doc.TryGetValue(chainKey, out @value);
first = false;
}
else
{
hasKey = (@value.ToBsonDocument()).TryGetValue(chainKey, out @value);
}
// Throw exception if key not existed.
if (!hasKey)
throw new Exception();
}
return true;
}
catch
{
@value = default;
return false;
}
}
}
上面的概念和下面的多重if逻辑是一样的:
if (doc.TryGetValue("Meeting", out BsonValue meetingValue))
{
if ((meetingValue.ToBsonDocument()).TryGetValue("Session", out BsonValue sessionValue))
{
if ((sessionValue.ToBsonDocument()).TryGetValue("Time", out BsonValue timeValue))
{
Console.WriteLine(timeValue);
}
}
}