0

我不确定这是我面临的 MongoDB 问题还是其中一种工具(NoSQLBooster、Studio 3T)。我可以在 NoSQLBooster 中使用以下代码并且它可以工作。但 Studio 3T 抱怨 JSON 无效。我想我更喜欢 studio 3T,因为它似乎有更多的功能,是否有解决方法来制作这个有效的 JSON?投影的 .toString() 部分显示“无效 JSON”有问题(尽管这将在 NoSQLBooster 中起作用)。

$project:
    {
        _id: 0,
        "Country": "$country",
        "Zip From": {
            $cond: {
                if: { "$lt": [{ "$strLenCP": "$postcodeFrom" }, 4] },
                then: { $concat: ["0", "$postcodeFrom".toString()] },
                else: "$postcodeFrom".toString()
            }
        },
        "FRPUW": "0",
        "Estimated Delivery (days)": "$rate.serviceDeliveryDays"
    }
4

1 回答 1

4

您可以在此处使用的是现代版本或$substr现代版本。第一个在新版本中被认为已弃用,并“别名”为. 它长期以来一直具有将“整数/双精度”转换为字符串的效果:$substrBytes$substrCP$substrBytes

 { "$project": {
   "_id": 0,
   "Country": "$country",
   "Zip From": {
      "$cond": {
        "if": { "$lt": [{ "$strLenCP": { "$substr": ["$postcodeFrom",0,10] } }, 4] },
        "then": { "$concat": ["0", { "$substr": ["$postcodeFrom",0,10] }] },
        "else": { "$substr": ["$postcodeFrom", 0, 10 ] }
      }
   },
   "FRPUW": "0",
   "Estimated Delivery (days)": "$rate.serviceDeliveryDays"
 }}

从 MongoDB 4.0 开始,您可以使用$toString别名来$convert代替:

 { "$project": {
   "_id": 0,
   "Country": "$country",
   "Zip From": {
      "$cond": {
        "if": { "$lt": [{ "$strLenCP": { "$toString": "$postcodeFrom" } }, 4] },
        "then": { "$concat": ["0", { "$toString": "$postcodeFrom",0,10] }] },
        "else": { "$toString": "$postcodeFrom" }
      }
   },
   "FRPUW": "0",
   "Estimated Delivery (days)": "$rate.serviceDeliveryDays"
 }}

唯一的“捕获”$substr及其变体是您需要包含最大字符串长度作为第三个参数。这可以是任何大于结果字符串预期长度的数字。这里我使用10一个合理的长度,但如果你期望更大的结果,那么增加这个数字。

唯一需要注意的是 using$substr不适用于其他类型。更“正式”的方法是$toString涵盖所有“类型”的大多数情况。实际的形式$convert实际上是针对预期的“类型转换”可能会失败的情况,然后允许“错误处理程序”回退到返回默认值或其他“有效”表达式。

此外,作为“聚合表达式”,这些语句因此对任何实现语言都“有效”,而不仅仅是 JavaScipt,这与主要误解相反,它实际上根本不是 MongoDB 的正式语言,除非在服务器评估的专门任务中,这是无论如何逐渐弃用和删除。

注意- 在您引用“有效 JSON”的问题中有一点“用词不当”。这实际上与 JSON 无关,而是聚合框架仅理解“有效表达式”而不理解您尝试使用的“JavaScript 表达式”这一事实。

与常见的误解相反,当您在聚合管道的内容中看到包含“JavaScript 表达式”的其他代码时,该代码实际上并没有“在服务器上执行”。实际发生的是表达式被“本地”评估,然后结果被转换为 BSON,“那个”是在服务器上执行的。

简而言之,您不能将“BSON 字段表达式”传递给“JavaScript 函数”或其他本地表达式,因为这不是在评估语句时实际发生的情况。

于 2018-05-29T01:10:00.023 回答