繁体   English   中英

Azure Cosmos DB 的重写分区键策略

[英]Write-heavy partition key strategy for Azure Cosmos DB

我们在生产中使用 CosmosDB 来存储 HTTP 请求/响应审计数据。 这些数据的结构一般如下:

{
    "id": "5ff4c51d3a7a47c0b5697520ae024769",
    "Timestamp": "2019-06-27T10:08:03.2123924+00:00",
    "Source": "Microservice",
    "Origin": "Client",
    "User": "SOME-USER",
    "Uri": "GET /some/url",
    "NormalizedUri": "GET /SOME/URL",
    "UserAgent": "okhttp/3.10.0",
    "Client": "0.XX.0-ssffgg;8.1.0;samsung;SM-G390F",
    "ClientAppVersion": "XX-ssffgg",
    "ClientAndroidVersion": "8.1.0",
    "ClientManufacturer": "samsung",
    "ClientModel": "SM-G390F",
    "ResponseCode": "OK",
    "TrackingId": "739f22d01987470591556468213651e9",
    "Response": "[ REDACTED ],   <— Usually quite long (thousands of chars)
    "PartitionKey": 45,
    "InstanceVersion": 1,
    "_rid": "TIFzALOuulIEAAAAAACACA==",
    "_self": "dbs/TIFzAA==/colls/TIFzALOuulI=/docs/TIFzALOuulIEAAAAAACACA==/",
    "_etag": "\"0d00c779-0000-0d00-0000-5d1495830000\"",
    "_attachments": "attachments/",
    "_ts": 1561630083
}

我们目前每天编写大约 150,000 - 200,000 个与上述类似的文档,其中/PartitionKey作为在容器上配置的分区键路径。 PartitionKey 的值是 C#.net 中随机生成的一个介于 0 到 999 之间的数字。

但是,我们看到每日热点,其中单个物理分区的最大值可以达到 2.5K - 4.5K RU/s,而其他的则非常低(大约 200 RU/s)。 这会影响成本,因为我们需要为最大的使用分区提供吞吐量。

第二个因素是我们存储了相当多的数据,接近 1TB 的文档,我们每天增加几 GB。 因此,我们目前有大约 40 个物理分区。

结合这两个因素意味着我们最终必须至少提供 120,000 - 184,000 RU/s 之间的某个地方。

我应该提一下,我们几乎不需要查询这些数据; 除了在 Cosmos 数据浏览器中非常偶然的临时手动构造查询。

我的问题是……通过简单地使用“id”列作为我们的分区键(或随机生成的 GUID),然后设置一个合理的 TTL,我们会在需要的 RU/s 和数据分布方面做得更好吗?所以我们没有不断增长的数据集?

我知道这需要我们重新创建集合。

非常感谢。

每个物理分区的最大吞吐量

虽然使用 id 或 GUID 会为您提供比您今天拥有的随机数更好的基数,但您运行的任何查询都将非常昂贵,因为它总是跨分区并且需要处理大量数据。

我认为更好的选择是使用一个合成键,它结合了多个属性,这些属性既具有高基数,又用于查询数据。 可以在此处了解有关这些的更多信息, https://docs.microsoft.com/en-us/azure/cosmos-db/synthetic-partition-keys

至于 TTL,我肯定会为您需要的数据保留设置它。 Cosmos 将使用未使用的吞吐量对数据进行 TTL 处理,因此永远不会妨碍。

最后,您还应该考虑(如果您还没有)使用自定义索引策略并排除任何从未查询过的路径。 特别是“响应”属性,因为您说它有数千个字符长。 这可以在像您这样的大量写入场景中节省大量 RU/s。

根据我的经验,我看到宇宙会随着新数据而退化。 更多的数据意味着更多的物理分区。 因此,您需要将更多的吞吐量分配给它们中的每一个。 目前我们开始将旧数据归档到 blob 存储中,以避免此类问题并保持物理分区的数量不变。 我们使用 cosmos 作为热存储,然后旧数据进入 blob 存储作为冷存储。 我们减少了分配给每个物理分区的 RU,从而节省了资金。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM