Couchbase-将文档中的数组与同一存储桶中的另一个文档进行连接

时间:2018-10-25 05:24:45

标签: couchbase n1ql

我正在努力在Couchbase的同一存储桶中的两种文档之间执行联接查询。

详细信息: 值区名称:lifext-stage

重要说明:两个文档都在同一个存储桶中,但是两个文档都有不同的类型字段,可在查询时用来标识它们。

第一句话将type字段设置为moment

第二个文档的type字段设置为user

第一个文档架构:

{
      "allCongrats": [
        {
          "congratulatory": "“The invariable mark of wisdom is to see the miraculous in the common.” -Ralph Waldo Emerson",
          "orderedId": 14
        }
      ],
      "congratulatory": null,
      "cueRecommendations": [
        {
          "iconName": "Waking_Up",
          "recommendation": "Waking Up"
        },
      ],
      "deliveryMethod": "audio",
      "description": "Complete a 60-second practice for unwinding stress by taking in the good",
      "duration": 60000,
      "effort": "med",
      "id": "moment-82435b7dca1eff75066b14a7c47ac046",
      "moduleId": "module-48f41a55ab24166c7ab1d1d8d825c776",
      "moduleType": "CULTIVATE_OPTIMISM",
      "orderedId": 1,
      "practice": "Gratitude",
      "textDuration": "60 sec",
      "title": "60 Seconds of Optimism",
      "type": "moment"
    }

第二个文档架构:

{
      "assessments": [],
      "cohortId": "cohort-a855864e-12b9-4e34-bd1f-2a89e581de1b",
      "dashboardIntroSeen": false,
      "email": "pros@aviahealthinnovation.com",
      "firstAssessmentCompleted": false,
      "firstName": "Phil",
      "focusId": null,
      "id": "user-00259a727b52cf35595e175134f49584",
      "lastName": "Ros",
      "longestStreak": 0,
      "modules": [],
      "moments": [
        {
          "completedDates": null,
          "lastCompletedMomentDate": null,
          "lastCongratulatoryId": null,
          "moduleId": "module-48f41a55ab24166c7ab1d1d8d825c776",
          "momentId": "moment-82435b7dca1eff75066b14a7c47ac046",
          "orderedId": 0,
          "userMomentId": "userMoment-58445416-9878-45d9-8221-6d6f76bf0a42"
        }
      ],
      "organizationId": "organization-fd779338-1361-4789-8da8-1ea37b0a3906",
      "signupTs": "2017-11-29T19:49:25.613Z",
      "streak": 0,
      "tokenValidator": "d9dcf699c23bacd33d6d841c454447d375990c51daa109cd5ffa5ff29bc7e6b0b76a26825267efb6b6873533ae711f82",
      "type": "user"
    }

如您所见,第二个文档包含一个包含momentId键的moments数组。此momentId键映射到第一个文档中的id键。

我想将第二个文档中的每个时刻项与第一个文档结合起来并返回结果。

此示例的预期结果:

{
      "allCongrats": [
        {
          "congratulatory": "“The invariable mark of wisdom is to see the miraculous in the common.” -Ralph Waldo Emerson",
          "orderedId": 14
        }
      ],
      "congratulatory": null,
      "cueRecommendations": [
        {
          "iconName": "Waking_Up",
          "recommendation": "Waking Up"
        },
      ],
      "deliveryMethod": "audio",
      "description": "Complete a 60-second practice for unwinding stress by taking in the good",
      "duration": 60000,
      "effort": "med",
      "id": "moment-82435b7dca1eff75066b14a7c47ac046",
      "moduleId": "module-48f41a55ab24166c7ab1d1d8d825c776",
      "moduleType": "CULTIVATE_OPTIMISM",
      "orderedId": 1,
      "practice": "Gratitude",
      "textDuration": "60 sec",
      "title": "60 Seconds of Optimism",
      "type": "moment",
      "completedDates": null,
      "lastCompletedMomentDate": null,
      "lastCongratulatoryId": null,
      "momentId": "moment-82435b7dca1eff75066b14a7c47ac046",
      "orderedId": 0,
      "userMomentId": "userMoment-58445416-9878-45d9-8221-6d6f76bf0a42"
    }

以下是我尝试过但未能获得任何结果的一些查询:

SELECT *
FROM (SELECT um
FROM `lifext-stage` a 
UNNEST a.moments as um
WHERE a.type="user") as u
INNER JOIN `lifext-stage` m
ON u.um.momentId = m.id
WHERE m.type="moment"

上面的查询给我以下错误:

[
  {
    "code": 3000,
    "msg": "syntax error - at u",
    "query_from_user": "SELECT *\nFROM (SELECT um\nFROM `lifext-stage` a \nUNNEST a.moments as um\nWHERE a.type=\"user\") as u\nINNER JOIN `lifext-stage` m\nON u.um.momentId = m.id\nWHERE m.type=\"moment\""
  }
]

我尝试过的第二个查询:

SELECT g.*, ARRAY_AGG({"node":n, "data":d}) AS node_data
FROM `lifext-stage` AS g UNNEST g.moments AS n JOIN `lifext-stage` AS d ON n.momentId = d.id
WHERE g.type="user" AND d.type="moment"

过去两天我一直在为此苦苦挣扎,在此方面的任何帮助将不胜感激。在此先感谢:)

1 个答案:

答案 0 :(得分:2)

需要Couchbase版本5.50

CREATE INDEX ix1 ON `lifext-stage` (id) WHERE type = "moment";

SELECT *
FROM `lifext-stage` AS u
UNNEST u.moments AS um
JOIN `lifext-stage` AS m ON um.momentId = m.id
WHERE m.type = "moment" AND u.type = "user";

以下博客在ANSI JOIN上有用例示例。

https://blog.couchbase.com/ansi-join-support-n1ql/