Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/402.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java Microsoft Azure Cosmos DocumentDB最佳读取查询性能_Java_Mongodb_Azure_Azure Cosmosdb_Azure Cosmosdb Sqlapi - Fatal编程技术网

Java Microsoft Azure Cosmos DocumentDB最佳读取查询性能

Java Microsoft Azure Cosmos DocumentDB最佳读取查询性能,java,mongodb,azure,azure-cosmosdb,azure-cosmosdb-sqlapi,Java,Mongodb,Azure,Azure Cosmosdb,Azure Cosmosdb Sqlapi,我们已经在云中实现了一个Azure CosmosDB(带有SQL API的MongoDB)数据库。通过java,我们希望根据MongoDB中隐藏的数据生成报告。我对我的阅读查询的性能还不是很满意,我想知道我当前的设置可以改进什么 如前所述,我使用Java查询数据库。我使用Microsoft Azure DocumentDB库查询数据库: <dependency> <groupId>com.microsoft.azure</groupId> &l

我们已经在云中实现了一个Azure CosmosDB(带有SQL API的MongoDB)数据库。通过java,我们希望根据MongoDB中隐藏的数据生成报告。我对我的阅读查询的性能还不是很满意,我想知道我当前的设置可以改进什么

如前所述,我使用Java查询数据库。我使用Microsoft Azure DocumentDB库查询数据库:

<dependency>
    <groupId>com.microsoft.azure</groupId>
    <artifactId>azure-documentdb</artifactId>
    <version>1.16.2</version>
</dependency>
我们经常使用的查询如下所示:

{
    "deviceid": "xxx",
    "devicedata": {
        "datetime": "2018-08-28T00:00:02.104Z",
        "sensors": [
            {
                "p_A2": "93095",
                "p_A3": "303883",
                "p_batterycurrent": "4294967.10000",
                "p_batterygauge": "38.27700",
                "p_batteryvoltage": "13.59400",
                ** ... around 200 more key - value pairs ... **
            }
        ]
    },
    "id": "aa5d3cf5-10fa-48dd-a0d2-a536284eddac",
    "_rid": "PtEIANkbMQABAAAAAAAAAA==",
    "_self": "dbs/PtEIAA==/colls/PtEIANkbMQA=/docs/PtEIANkbMQABAAAAAAAAAA==/",
    "_etag": "\"00000000-0000-0000-4040-006a7f2501d4\"",
    "_attachments": "attachments/",
    "_ts": 1535619672
}
SELECT c.deviceid, 
    c.devicedata.datetime, 
    c.devicedata.sensors[0].p_A2, 
    c.devicedata.sensors[0].p_A3,
    c.devicedata.sensors[0].p_batterycurrent,
    c.devicedata.sensors[0].s_humidity 
FROM c 
WHERE c.deviceid = 'xxx'
    AND c.devicedata.datetime >= '2018-08-28T00:00:00.000Z' 
    AND c.devicedata.datetime < '2018-08-30T00:00:00.000Z' 
order by c.devicedata.datetime desc
我很确定MongoDB可以在几秒钟内查询数十万个文档,所以我很确定我的当前设置有问题


有什么建议吗?

我不能为您的问题提供一个明确的解决方案,但希望能为您提供一些想法,以获得一个具有理想性能水平的解决方案

好合身吗? 首先,为了解决这个问题,您确定您的场景非常适合noSQL吗?当主要场景使用精确定位数据(创建、按id选择、按id更新、按id删除)时,CosmosDB将大放异彩。是的,它确实可以进行有限的大规模操作和聚合,但查询数百万的用户正在推动它。另一方面,SQL设计用于处理大型数据集,在聚合方面非常出色

让我们假设这个设计决策是经过仔细权衡的,而noSQL最适合于未提及的原因

调试硬数据 不要对本地cosmosDB emulator进行性能测试。不要。这显然不是真的(考虑网络、存储带宽/寻道时间、系统影响),而只是模拟它。你可能会得到误导性的结果启动一个真实的测试实例

调试查询性能问题的第一步是启用,并查看这20秒的实际花费

此外,加载38000个文档很可能永远不会在一个批处理中到达,请检查实际上向cosmosDB服务器进行了多少次连续查询

另外,运行探查器并确保瓶颈确实在CosmosDB中。如果您在许多设备上进行许多连续调用和并发查询,那么在客户机中也可能会发生很多情况,并且查询会在网络上进行。确保您在客户端(GC、Http堆栈、内部锁定、连接/线程池等)中没有受到限制

数据/查询设计 减少查询数据 如果您已经知道设备ID,那么不要查询它38000多次,这只是一个问题

减小模型对象大小 /*大约还有200多个键值对*/

那是一个巨大的物体。我将测试将其拆分为更小的对象是否有助于cosmosDB在内部加载和处理文档方面花费更少的时间。例:

{
    "p_A2": "93095",
    "p_A3": "303883",
    "battery" : {
        "current": "4294967.10000",
        "gauge": "38.27700",
        "voltage": "13.59400"
    }
   ...
}
不确定docDB是如何在内部存储文档的(完整图形与子文档),但您可以测试它是否会产生影响。2岁与20岁之间的差异如此之大,这暗示着这可能是相关的

传感器阵列? 查询仅查询第一个测量集。是否需要阵列?您可以测试省略此级别是否对性能有任何影响

模型中的数据类型
电池电流
etc将传感器测量数值存储为长字符串。如果它们总是数字,那么您可以将它们存储为数字,并减少服务器和客户端中的文档大小。客户端性能可能会受到更大的影响(字符串=堆分配)。例如:
“4294967.10000”
在客户端(UTF-16)中是13个字符=26B

应用程序设计 你真的每次都需要38000或数百万份文件吗?考虑一下如果你能得到一个子集…

如果是数据移动,则考虑其他选项(数据工厂、更改馈送处理)以递增地传递测量值。如果这是请求,那么应用程序需要考虑加载<强>较小的时间框架< /强>(=更少的文档)和<强> >使用缓存< <强> >过去的时间框架。如果可以,请在缓存前预聚合结果。过去的传感器数据很可能不会改变


一如既往,考虑您的ROI商业案例。优化总是可能的,但有时调整业务需求而不是技术解决方案更为有利。

在运行时从文档中提取传感器数据。因此,正在有效地解析和处理字符串blob。提取传感器字段所需的资源消耗将向您收取费用

运行select*时,查询只返回整个blob,因此不需要解析

当选择仅包括已编制索引的字段时。索引数据很可能满足查询。因此,不需要访问文档数据

我会尝试两件事。在索引策略中包括传感器路径。这将增加查询引擎仅通过访问索引结构即可处理查询的概率


第二,通过删除订单,这将进一步减少服务器端的处理。

如果我是对的,您希望以某种方式聚合获取的记录。也许你应该减少你想从cosmosdb获取的数据量,为了更快,你应该把你的加总移到数据库端:所以我建议你在那里创建并做艰苦的工作,然后只获取结果。我会这样做的。也许你不需要编写存储过程,只需要做一些我不确定,我只玩了“经典”mongodb。谢谢,伙计,这确实是我们的一个选择,但有时我们不想做聚合,只想显示简单的数据。我想知道我是否尽了我所能来帮助表演。我觉得SQL Api并没有让事情变得更简单。也许你只是选择了不适合这份工作的工具。如果你愿意,也许更合身
{
    "p_A2": "93095",
    "p_A3": "303883",
    "battery" : {
        "current": "4294967.10000",
        "gauge": "38.27700",
        "voltage": "13.59400"
    }
   ...
}