【问题标题】:Global Vs Local Secondary Indexes in DynamoDBDynamoDB 中的全局与本地二级索引
【发布时间】:2018-10-09 10:10:49
【问题描述】:

我仍然对本地二级索引的使用感到困惑。请在需要 LSI 与 GSI 时给我具体的用例。

例如,“GenreAlbumTitle”索引应该是 GSI 还是 LSI?https://docs.aws.amazon.com/amazondynamodb/latest/developerguide/HowItWorks.CoreComponents.html#HowItWorks.CoreComponents.PrimaryKey

我似乎无法理解需要 LSI 的必要性,因为我需要的任何索引都将覆盖表的整行,而不仅仅是特定于一个分区。如果有人也可以谈及成本方面,因为我知道 LSI 更便宜(但为什么更便宜)?

谢谢大家!

【问题讨论】:

    标签: indexing amazon-dynamodb


    【解决方案1】:

    Dynamo 中的每个项目都必须有一个唯一的主键。主键是基表索引。主键必须有一个分区键,并且可以选择有一个范围键(也称为排序键)。在分区内,项目按范围键排序。使用分区键访问项目很快。

    辅助索引允许您使用备用键查询表。 本地二级索引 (LSI) 与主键(索引)具有相同的分区键,但范围键不同。考虑 LSI 的方式是,它与主索引(键)相同的数据,只是按不同的属性排序。

    全局二级索引 (GSI) 的分区键与主键不同,因此是一组不同的数据。

    LSI 和 GSI 之间的一个重要区别是 LSI 从基表获取其吞吐能力,因为您需要单独购买 GSI 吞吐能力。换句话说,LSI 不会花费您任何费用,而 GSI 会比您的基表产生额外费用。

    让我们看一下 Music 表示例。假设基表具有此架构;

    Artist: (Primary Key) Partition Key
    SongTitle: (Primary Key) Range Key
    AlbumTitle:
    DateOfRelease:
    

    此表是歌曲列表。我可以非常有效地访问艺术家的所有歌曲(即艺术家使用分区键查询)。当我执行此查询时,歌曲将按 SongTitle 排序。我还可以使用唯一的主键非常有效地访问 Artist 和 SongTitle 的歌曲。

    现在假设我想获取艺术家的所有歌曲,但按 DateOfRelease 排序。在当前模式中,我需要获取所有歌曲,然后在我的应用程序中对它们进行排序。一个好的替代方法是创建一个新索引,其分区键为 Artist,范围键 DateOfRelease。这将是一个 LSI,因为索引 (Artist) 的分区键与主键的分区键相同。我不需要购买额外的吞吐容量,因为该索引会根据基表容量自行配置。

    现在假设我想按 AlbumTitle 访问歌曲,按 SongTitle 排序,即创建专辑列表。为了有效地做到这一点,我使用分区键 AlbumTitle 和范围键 SongTitle 创建了一个新索引。这是一个 GSI,因为分区键与主键不同。此 GSI 必须单独提供给基表,因此需要额外付费。

    在回答您的问题时,GenreAlbumTitle 是一个 GSI,因为它的分区键与 Music 不同。

    【讨论】:

    • 感谢 Stu,现在您已经耐心地用示例进行了解释。非常感谢!
    • 嗨,斯图,麻烦您了。我有另一个关于索引属性的相关问题,这里是数组的一部分stackoverflow.com/questions/50081983/…我想知道你是否知道答案。
    • 嗨 Stu 是否可以直接在全局二级索引上写入..?
    • 不,你只是写入基表。
    • 如果发布的数据是重复条目怎么办。 LSI 是否创建重复条目
    【解决方案2】:

    对于使用 LSI 的成本存在一些误解,所以让我在这里澄清一下。

    使用 LSI 不是免费的。就像 GSI 一样,dynamoDB 需要创建和维护表的额外部分副本才能快速获得结果。这种额外副本的维护将产生与 GSI 相同的额外读取、写入和存储成本。 (额外费用将以粗体显示)。唯一的区别是,您使用与主表相同的薪酬计划,而不是分配单独的薪酬计划。

    在讨论附加成本之前,让我再次总结一下部分复制表中存储了哪些信息。部分表副本 (LSI) 包含分区键(与原始表相同)、排序键(与原始表不同)以及任何其他投影属性。

    原始表格

    Artist (Primary Key) Song title (sort key) Album Title Date Of Release
    Michael Jackson Beat It Thriller December 1, 1982
    Weeknd The Hills Beauty Behind the Madness May 27, 2015,

    大规模集成电路

    Artist (Primary Key) Album Title (sort key) Date Of Release
    Michael Jackson Thriller December 1, 1982
    Weeknd Beauty Behind the Madness May 27, 2015,

    投影属性是我们要从 LSI 查询的附加信息。我可以说,“按Weeknd 显示专辑的所有发行日期,按专辑名称排序”。如您所见,我们不关心这里的歌名,也不包含在我们的 LSI 预测中。

    读取的额外费用

    • 对于仅使用 LSI 表即可满足的查询,您需要为 1 个读取单元付费。示例:“按 Weeknd 显示歌曲的所有发行日期,按专辑名称排序。”

    • 对于 LSI 不知道如何自行处理的查询,您需要支付 1 个额外读取单元的费用,这会迫使它转到主表寻求帮助。这将总共花费 2 个读取单元。示例:“显示所有发行日期和歌曲的歌曲名称,按 Weeknd,按专辑名称排序。”

    额外的写入费用

    (写入主表,有自己的写入成本,更改稍后传播到 LSI)

    • 如果对主表的更新导致在 LSI 中创建新行 => 1 个额外的写入单元
    • 如果对主表的更新导致 LSI 中现有行的键属性被更新 => 删除成本(1 个单元)+ 创建(1 个单元)= 2 个额外的写入单元强>
    • 如果对主表的更新导致 LSI 中现有行的非键属性被更新 => 1 个额外的写入单元
    • 如果对主表的更新导致删除 LSI 中现有行的现有属性 => 1 个额外的写入单元
    • 如果对主表的更新没有改变 LSI 的任何行 => 0 个额外的写入单元

    额外的存储费用

    • 您支付额外费用:(索引键大小 + 投影属性大小 + 开销)x 行数

    如您所见,如果我们对 LSI 不小心,额外的成本可能会变得难以承受。为了最大限度地降低成本,您必须:

    • 仔细考虑您的典型查询。您需要哪些类型的信息?
    • 在读取成本和存储成本之间存在权衡。如果将每个属性都投影到 LSI,则不会产生额外的读取成本,但存储成本会增加一倍。如果您仅投影关键属性,并且您经常获取关键属性以外的其他信息,则必须返回主表寻求帮助会产生大量额外的读取成本。
    • 对于大量写入的表,预计会导致写入成本大幅上升。请记住,如果对主表的更新更新了 LSI 中某个项目的键属性,您需要额外支付 2 个写入单元,而对于非关键属性,您需要额外支付 1 个写入单元。

    【讨论】:

      猜你喜欢
      • 2018-11-01
      • 1970-01-01
      • 1970-01-01
      • 2016-09-17
      • 1970-01-01
      • 1970-01-01
      • 2021-03-14
      • 1970-01-01
      • 2015-11-03
      相关资源
      最近更新 更多