【问题标题】:DynamoDB - Global Secondary Index on set itemsDynamoDB - 设置项目的全局二级索引
【发布时间】:2016-02-07 01:40:08
【问题描述】:

我有一个具有以下属性的发电机表:

  • id(数字 - 主键)
  • 标题(字符串)
  • created_at(数字 - 长)
  • 标签(StringSet - 包含一组标签,比如 android、ios 等)

我希望能够通过标签进行查询 - 获取所有标记为 android 的项目。我怎样才能在 DynamoDB 中做到这一点?似乎全局二级索引只能基于 ScalarDataTypes(即数字和字符串)而不是集合内的项目。

如果我采用的方法是错误的,另一种方法是创建不同的表或更改属性也可以。

【问题讨论】:

    标签: amazon-dynamodb


    【解决方案1】:

    索引的键模式。索引键模式中的每个属性 必须是字符串、数字或二进制类型的顶级属性。 不允许嵌套属性和多值集。其他 键模式的要求取决于索引的类型:对于 全局二级索引,hash属性可以是任意标量表 属性。范围属性是可选的,它也可以是任何标量 表属性。对于本地二级索引,哈希属性必须 与表的 hash 属性和 range 属性相同 必须是非键表属性。

    • Amazon 建议为此类问题创建一个单独的一对多表。更多信息在这里:Use one to many tables

    【讨论】:

    • 有谁知道 2018 年是否仍然如此?
    • @cryanbhu 是的,如果你想索引属性,它们不能嵌套
    【解决方案2】:

    您需要为此查询创建一个单独的表。 如果您有兴趣根据标签获取所有项目,那么我建议保留一个带有主键的表:
    hash: tag
    range: id

    这样您就可以使用一个非常简单的Query 来按标签获取所有项目。

    【讨论】:

    • 标签不能是主键。它只能是索引的键。主键必须是唯一标识符。
    • 哈希+范围=主键。 Tag+id 是唯一的,因为 id 是唯一的(根据您的问题)
    • 将哈希作为标签会导致负载不均匀,因为没有大量不同的标签值。将 id 作为散列,将标签作为新表的范围,GSI 将标签作为散列,将 id 作为范围是推荐的方式。 slideshare.net/AmazonWebServices/deep-dive-amazon-dynamodb(查看幻灯片 33)。
    • 我可能应该在原始问题中指定。不过谢谢你的建议。
    • 我希望该设计对您有用,但请记住,GSI 在非均匀负载方面与主键存在相同的问题。这意味着从理论上讲,无论它是否是主键/GSI,您都会为标签哈希支付更多费用/获得糟糕的性能。
    【解决方案3】:

    这是一个很老的帖子,很抱歉恢复它,但我想看看“单表设计”

    基本上,不要再将您的数据视为结构化数据 - 拥抱非规范化

    id(数字 - 主键) 标题(字符串) created_at(数字 - 长) 标签(StringSet - 包含一组标签,比如 android、ios 等)

    而不是带有“标题”的 nosql 表:
    id|title|created_at|tags

    这样想:

    pk|sk    |data....
    id|id    |{title, created_at}
    id|id+tag|{id, tag} <- create one record per tag
    

    您仍然可以通过查询pk=idsk begins with id 来返回所有内容,并将标签加入应用逻辑中的 id 记录

    您可以使用 GSI 将 id|id+tag 投影到 tag|id 中,这仍然需要您针对您的数据编写两个查询以获取给定标签的项目(获取 id 然后获取项目),但您赢了'不必复制您的数据,您不必扫描,当您的访问模式不依赖标签时,您仍然可以在一个查询中获取您的项目。

    FWIW 我会首先考虑您的所有访问模式,然后再考虑如何构建复合键和/或 GSI

    干杯

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-03-02
      • 1970-01-01
      • 1970-01-01
      • 2015-11-03
      • 1970-01-01
      相关资源
      最近更新 更多