DynamoDB 基本概念
DynamoDB 是 AWS 独有的完全托管的 NoSQL Database。它的思想来源于 Amazon 2007 年发表的一篇论文:Dynamo: Amazon’s Highly Available Key-value Store。在这篇论文里,Amazon 介绍了如何使用 Commodity Hardware 来打造高可用、高弹性的数据存储。想要理解 DynamoDB,首先要理解 Consistent Hashing。Consistent Hashing 的原理如下图所示:
它的概念是:
以后添加新的Node时,映射发生变化,只需要把相应的变化了的Vnode迁移到新的Node上即可。在这种结构下,Sharding/Replica对程序员基本上是透明的。
基本 DynamoDB 组件包括:表、项目、属性
下图是一个名为 People 的表,其中显示了一些示例项目和属性:
请注意有关 People 表的以下内容:
这里,我们将看到第一个概念:主键。
创建表时,除表名称外,您还必须指定表的主键。主键唯一标识表中的每个项目,因此,任意两个项目的主键都不相同。 DynamoDB 支持两种不同类型的主键:
如果表具有简单主键(只有分区键),DynamoDB 将根据其分区键值存储和检索各个项目。同时,DynamoDB 使用分区键的值作为内部哈希函数的输入值,从而将项目写入表中。哈希函数的输出值决定了项目将要存储在哪个分区。 要从表中读取某个项目,必须为该项目指定分区键值。DynamoDB 使用此值作为其哈希函数的输入值,从而生成可从中找到该项目的分区。(此时,分区键必须是唯一的,不可重复。)
下图显示了名为 Pets 的表,该表跨多个分区。表的主键为 AnimalType(仅显示此键属性)。在这种情况下,DynamoDB 会根据字符串 Dog 的哈希值,使用其哈希函数决定新项目的存储位置。请注意,项目并非按排序顺序存储的。每个项目的位置由其分区键的哈希值决定。
DynamoDB 使用分区键值作为对内部哈希函数的输入。来自哈希函数的输出决定了项目将存储到的分区(DynamoDB 内部的物理存储)。具有相同分区键的所有项目按排序键值的排序顺序存储在一起。两个项目可具有相同的分区键值,但这两个项目必须具有不同的排序键值。
为将某个项目写入表中,DynamoDB 会计算分区键的哈希值以确定该项目的存储分区。在该分区中,可能有几个具有相同分区键值的项目,因此 DynamoDB 会按排序键的升序将该项目存储在其他项目中。
要读取表中的某个项目,您必须为该项目指定分区键值和排序键值。DynamoDB 会计算分区键的哈希值,从而生成可从中找到该项目的分区。
如果我们查询的项目具有相同的分区键值,则可以通过单一操作 (Query) 读取表中的多个项目。DynamoDB 将返回具有该分区键值的所有项目。或者,也可以对排序键应用某个条件,以便它仅返回特定值范围内的项目。
假设 Pets 表具有由 AnimalType(分区键)和 Name(排序键)构成的复合主键。
下图显示了 DynamoDB 写入项目的过程,分区键值为 Dog、排序键值为 Fido。
DynamoDB支持在一个表上创建一个或多个二级索引。利用 secondary index,除了可对主键进行查询外,还可使用替代键查询表中的数据。
DynamoDB 支持两种索引:
最多可以为每个表定义 5 个全局二级索引和 5 个本地二级索引。
下图显示了示例 Music 表,该表包含一个名为 GenreAlbumTitle 的新索引
对于Music表,我们不仅可以按 Artist(分区键)或按 Artist 和 SongTitle(分区键和排序键)查询数据项。还可以按 Genre 和 AlbumTitle 查询数据。
请注意有关 GenreAlbumTitle 索引的以下内容:
DynamoDB 对表中的属性支持很多不同的数据类型。可按以下方式为属性分类:
当创建表或secondary index时,必须指定每个主键属性(分区键和排序键)的名称和数据类型。此外,每个主键属性必须定义为字符串、数字或二进制类型。
标量类型包括数字、字符串、二进制、布尔值和 null。
数据类型 | 说明 | 示例 |
---|---|---|
字符串 | 字符串是使用 UTF-8 二进制编码的 Unicode。字符串的长度必须大于零且受限于最大 DynamoDB 项目大小 400 KB。 | "Bicycle" |
数字 | 数字可为正数、负数或零。数字最多可精确到 38 位 - 超过此位数将导致意外 | 300 |
二进制 | 二进制类型属性可以存储任意二进制数据,如压缩文本、加密数据或图像。DynamoDB 会在比较二进制值时将二进制数据的每个字节视为无符号。二进制属性的长度必须大于零且受限于最大 DynamoDB 项目大小 400 KB。 | 这是一个采用 Base64 编码文本的二进制属性: dGhpcyB0ZXh0IGlzIGJhc2U2NC1lbmNvZGVk |
布尔值 | 布尔类型属性可以存储 true 或 false。 | true |
空 | 空代表属性具有未知或未定义状态。 | NULL |
如果将主键属性定义为字符串类型属性,以下附加限制将适用:
DynamoDB 使用基础的 UTF-8 字符串编码字节整理和比较字符串。例如,“a”(0x61) 大于“A”(0x41),“¿”(0xC2BF) 大于“z”(0x7A)。
可使用字符串数据类型表示日期或时间戳。执行此操作的一种方法是使用 ISO 8601 字符串,如以下示例所示:
也可以使用数字数据类型表示日期或时间戳
数字范围
在 DynamoDB 中,数字以可变长度形式表示。系统会删减开头和结尾的 0。
所有数字将作为字符串通过网络发送到 DynamoDB,以最大程度地提高不同语言和库之间的兼容性。但是,DynamoDB 会将它们视为数字类型属性以方便数学运算。
Note
如果数字精度十分重要,则应使用从数字类型转换的字符串将数字传递给 DynamoDB。
如果将主键属性定义为二进制类型属性,以下附加限制将适用:
在将二进制值发送到 DynamoDB 之前,我们必须采用 Base64 编码格式对其进行编码。收到这些值后,DynamoDB 会将数据解码为无符号字节数组,将其用作二进制属性的长度。
文档类型包括列表和映射。这些数据类型可以互相嵌套,用来表示深度最多为 32 层的复杂数据结构。 只要包含值的项目大小在 DynamoDB 项目大小限制 (400 KB) 内,列表或映射中值的数量就没有限制。
数据类型 | 说明 | 示例 |
---|---|---|
列表 | 列表类型属性可存储值的有序集合。列表用方括号括起:[ ... ]。列表类似于 JSON 数组。列表元素中可以存储的数据类型没有限制,列表元素中的元素也不一定为相同类型。 | FavoriteThings: ["Cookies", "Coffee", 3.14159] |
映射 | 映射类型属性可以存储名称/值对的无序集合。映射用大括号括起:{ ... }。映射类似于 JSON 对象。映射元素中可以存储的数据类型没有限制,映射中的元素也不一定为相同类型。 | 示例如下 |
{ Day: "Monday",
UnreadEmails: 42,
ItemsOnMyDesk: [ "Coffee Cup", "Telephone",
{
Pens: { Quantity : 3}, Pencils: { Quantity : 2}, Erasers: { Quantity : 1}
}
]
}
DynamoDB 让您可以使用映射/列表中的单个元素
DynamoDB 支持表示数字、字符串或二进制值集的类型。集中的所有元素必须为相同类型(
集中的每个值必须是唯一的。集中的值的顺序不会保留。不支持空集。
Example (字符串集、数字集和二进制集)
# 必须是相同的数据类型# 字符串集["Black", "Green" ,"Red"]# 数字集[42.2, -19, 7.5, 3.14]# 二进制集["U3Vubnk=", "UmFpbnk=", "U25vd3k="]
DynamoDB 的api操作主要用于控制层面、数据层面和DynamoDB Streams。
控制层面 操作可让我们可以创建和管理DynamoDB表。它们还可让我们可以使用依赖于表的索引、流和其他对象。
数据层面操作可让我们对表中的数据执行创建、读取、更新和删除(也称为 CRUD)操作。某些数据层面操作还可让我们可以从secondary index中读取数据。
Batch 操作比调用多次单个请求(DeleteItem, GetItem, PutItem)更有效,因为秩序一个网络请求即可操作多个项目。
DynamoDB Streams 操作可对表启用或禁用流,并能允许对包含在流中的数据修改记录的访问。
DynamoDB 中的表、属性和其他对象必须具有名称。名称应该简明扼要 - 例如,Products、Books 和 Authors 之类的名称是都是不言而喻的。
下面是 DynamoDB 的命名规则:
与很多其他数据库管理系统相似,DynamoDB 也具有一系列保留关键字和特殊字符。
DynamoDB允许使用这些关键字和特殊符号用于命名,但我们不建议这么做
有关更多信息,请参阅 为属性名称和值使用占位符(2)。
引用链接: