在 Cosmos DB 中查询嵌套对象

Posted

技术标签:

【中文标题】在 Cosmos DB 中查询嵌套对象【英文标题】:Querying nested objects in Cosmos DB 【发布时间】:2021-12-14 12:58:31 【问题描述】:

我查看了许多答案并尝试了各种方法来查询我在 Cosmos DB 中拥有的嵌套对象。该数据库包含大量不同类型的 json 类型对象。我已经能够成功查询列表中第一个对象的子对象,但不能查询后续对象。

对象本身如下所示:


    "id": "d44c1ff6-d5b0-41b0-b84c-2a6c20f99ada",
    "deviceUID": "10203040501020304051-8",
    "time": "2021-10-27T12:49:53.1174041Z",
    "connectorId": 1,
    "meterValues": 
        "eairo": 1013363236,
        "cio": 4
    ,
    "hash": "8ADAED5BBF663AAFE93644CA071573906CC409F70231105F10C5CEE5AE8FC341"

而我的连接和查询如下:

cnxn: pyodbc.Connection = pyodbc.connect(
"""DRIVER=CData ODBC Driver for Cosmos DB;
   AccountEndpoint=x;
   AccountKey=y;""")
df = pd.read_sql_query("SELECT m.id, m.deviceUID, m.time, m.meterValues.eairo FROM metering m WHERE m.deviceUID <> null", cnxn)

事实证明,SELECT 的 m.meterValues.eairo 部分存在问题。报错如下:

pandas.io.sql.DatabaseError: Execution failed on sql 'SELECT m.id, m.deviceUID, m.time, m.meterValues.eairo FROM metering m WHERE m.deviceUID <> null': ('HY000', "[HY000] No table found with the alias 'meterValues'. (-1) (SQLExecDirectW)")

知道我哪里可能出错了吗?

【问题讨论】:

你不需要说FROM metering m - 只需说FROM m。除此之外:您应该尝试使用适用于 Cosmos DB 的本机 Python SDK,而不是 ODBC 库(请记住,Cosmos DB 不是本机关系数据库,它的 SQL 语法是您在关系数据库中找到的一个子集) .我怀疑你会得到更好的结果,因为你目前正试图将 Cosmos DB 强制转换为关系数据库接口。 太好了,感谢 David,SDK 完成了这项工作。 【参考方案1】:

这要归功于 David,SDK 轻而易举地完成了这项工作。

编码如下:

from azure.cosmos import CosmosClient
import json

url = 'x'
key = 'y'
client = CosmosClient(url, credential=key)

database = client.get_database_client('z')
container = database.get_container_client('metering')

for item in container.query_items(
        query="SELECT m.id, m.deviceUID, m.time, m.meterValues.eairo FROM 
        metering m WHERE m.deviceUID <> null",
        enable_cross_partition_query=True):
    print(json.dumps(item, indent=True))

【讨论】:

以上是关于在 Cosmos DB 中查询嵌套对象的主要内容,如果未能解决你的问题,请参考以下文章

用于 cosmos db json 中嵌套对象的 Linq

如何在 Azure Cosmos DB 的一个查询中选择多个聚合值

Cosmos DB 在查询中不尊重 Json.Net CamelCaseNamingStrategy [重复]

Cosmos DB,如果我在使用 SkipToken 查询时更新某些项目会发生啥?

Cosmos DB - 查询所选分区的最新文档?

Azure 函数:如何将 http 触发器函数的查询字符串参数绑定到 Cosmos DB 的 SQL 查询