CosmosDb Sql 匹配文档之间数组中的公共值的查询

CosmosDb Sql query that matches common values in array between documents

我正在使用 Cosmos DB,我想编写一个 SQL 查询来匹配基于 id 的文档数组中的公共值。

为了详细说明,假设您有以下三个文档:

{
        "id": "2ECF4568-CB0E-4E11-A5CD-1206638F9C39",
        "entityType": "ServiceInformationFacility",
        "facilities": [
            {
                "id": "6F706BA3-27AD-45B8-9831-A531E37C4C17",
                "facilityName": "Kat Service Center",
                "phoneNumber": "9879561234"

            },
            {
                "id": "7F706BA3-27AD-45B8-9831-A531E37C4C17",
                "facilityName": "Honda Service Center",
                "phoneNumber": "9879561234"

            }]

    },
    {
        "id": "3ECF4568-CB0E-4E11-A5CD-1206638F9C39",
        "entityType": "ServiceInformationFacility",
        "facilities": [
            {
                "id": "8F706BA3-27AD-45B8-9831-A531E37C4C17",
                "facilityName": "Hyundai Service Center",
                "phoneNumber": "9879561234"

            },
            {
                "id": "7F706BA3-27AD-45B8-9831-A531E37C4C17",
                "facilityName": "Honda Service Center",
                "phoneNumber": "9879561234"

            }]

    },
    {
        "id": "6ECF4568-CB0E-4E11-A5CD-1206638F9C39",
        "entityType": "ServiceInformationFacility",
        "facilities": [
            {
                "id": "8F706BA3-27AD-45B8-9831-A531E37C4C17",
                "facilityName": "Hyundai Service Center",
                "phoneNumber": "9879561234"

            },
            {
                "id": "7F706BA3-27AD-45B8-9831-A531E37C4C17",
                "facilityName": "Honda Service Center",
                "phoneNumber": "9879561234"
            } ]
    }

我想写一个查询 return 所有基于 id.That 的公共设施意味着当传递 ID 列表时,应显示给定 ID 中存在的设施(不是 要么). 所以在上面的集合中,它应该只 return "facilityName": "Honda Service Center" 通过传递参数 id("2ECF4568-CB0E-4E11 -A5CD-1206638F9C39","3ECF4568-CB0E-4E11-A5CD-1206638F9C39","6ECF4568-CB0E-4E11-A5CD-1206638F9C39").

到目前为止我已经尝试过:

SELECT q.facilityName  FROM c
join q in c.facilities
where c.id in('6ECF4568-CB0E-4E11-A5CD-1206638F9C39','2ECF4568-CB0E-4E11-A5CD-1206638F9C39')AND c.entityType = 'ServiceInformationFacility'

它给了我所有的设施名称,但我只需要上述文件中常见的设施,即 "facilityName":"Honda Service Center"。

提前致谢

It gives me all the facility name but I need only facility which are common in the above documents that is "facilityName": "Honda Service Center".

我可能明白你的意思now.However,恐怕这在宇宙中是不可能的sql。我尝试计算 facilitiesName 交叉文档的出现次数,并得到最符合您需要的以下解决方案。

sql:

SELECT count(c.id) as cnt, f.facilityName from c 
join f in c.facilities
where array_contains(['6ECF4568-CB0E-4E11-A5CD-1206638F9C39','2ECF4568-CB0E-4E11-A5CD-1206638F9C39'],c.id,true)
AND c.entityType = 'ServiceInformationFacility'
group by f.facilityName

输出:

然后我尝试用一​​些 subquery 来扩展它,但没有成功。所以我建议使用存储过程来完成下一个 job.The 主要目的是循环上面的结果并判断 cnt 是否等于 [ids array].length.


更新存储过程代码的答案:

@idArray 的输入参数:["6ECF4568-CB0E-4E11-A5CD-1206638F9C39","2ECF4568-CB0E-4E11-A5CD-1206638F9C39"]

Sp代码:

function sample(idArray) {
    var collection = getContext().getCollection();

    var length = idArray.length;

    var sqlQuery = {
        "query":  'SELECT count(c.id) as cnt, f.facilityName from c join f in c.facilities '+
        'where array_contains( @idArray,c.id,true) ' +
        'AND c.entityType = "ServiceInformationFacility" group by f.facilityName',
        "parameters": [
            {"name": "@idArray", "value": idArray}
        ]
    }

    // Query documents and take 1st item.
    var isAccepted = collection.queryDocuments(
        collection.getSelfLink(),
        sqlQuery,
    function (err, feed, options) {
        if (err) throw err;
        if (!feed || !feed.length) {
            var response = getContext().getResponse();
            response.setBody('no docs found');
        }
        else {
            var response = getContext().getResponse();
            var returenArray = [];
            for(var i=0;i<feed.length;i++){                
                if(feed[i].cnt==length)
                    returenArray.push(feed[i])
            }

            response.setBody(returenArray);
        }
    });

    if (!isAccepted) throw new Error('The query was not accepted by the server.');
}

输出: