将 MongoDB 作为 AWS DMS 源 - AWS Database Migration Service

本文属于机器翻译版本。若本译文内容与英语原文存在差异,则一律以英文原文为准。

将 MongoDB 作为 AWS DMS 源

AWS DMS 支持将 MongoDB 版本 3.x 和 4.0 作为数据库源。

如果您是首次使用 MongoDB,请注意以下重要的 MongoDB 数据库概念:

  • 中的记录是一个MongoDB文档,它是由字段和值对组成的数据结构。字段值可以包含其他文档、数组和文档数组。文档大致相当于关系数据库表中的行。

  • 中的集合 是一组文档,并且大致相当于关系数据库表。MongoDB

  • 在内部,MongoDB 文档以压缩格式存储为二进制 JSON (BSON) 文件,其中包含文档中每个字段的类型。每个文档都有唯一的 ID。

将 AWS DMS 作为源时,MongoDB 支持两种迁移模式。在创建 终端节点时,您可以使用 AWS 管理控制台通过 Metadata mode (元数据模式)nestingLevel 参数指定迁移模式,或者使用额外的连接属性 MongoDB 指定迁移模式。所选的迁移模式将影响目标数据的结果格式,如下所述。

文档模式

在文档模式下,MongoDB 文档按原样迁移,这意味着文档数据将合并到目标表中名为 _doc 的单个列中。文档模式是您将 MongoDB 作为源终端节点时的默认设置。

例如,请考虑名为 MongoDB 的 myCollection 集合中的以下文档。

> db.myCollection.find() { "_id" : ObjectId("5a94815f40bd44d1b02bdfe0"), "a" : 1, "b" : 2, "c" : 3 } { "_id" : ObjectId("5a94815f40bd44d1b02bdfe1"), "a" : 4, "b" : 5, "c" : 6 }

在使用文档模式将数据迁移到关系数据库表后,数据结构如下所示。文档中的数据字段将合并到 MongoDB 列中。 _doc

oid_id _doc
5a94815f40bd44d1b02bdfe0 { "a" : 1, "b" : 2, "c" : 3 }
5a94815f40bd44d1b02bdfe1 { "a" : 4, "b" : 5, "c" : 6 }

您可以选择将额外连接属性 extractDocID 设置为 true,以创建第二个名为 "_id" 的列以作为主键。如果要使用 CDC,请将此参数设置为 true,除非使用 Amazon DocumentDB 作为目标。

在文档模式中,AWS DMS 按如下方式管理集合的创建和重命名:

  • 如果您将一个新集合添加到源数据库,则 AWS DMS 将为该集合创建一个新的目标表并复制所有文档。

  • 如果您重命名源数据库上的现有集合,则 AWS DMS 不会重命名目标表。

表模式

在表模式中,AWS DMS 将 MongoDB 文档中的每个顶级字段转换为目标表中的一个列。如果已嵌套字段,则 AWS DMS 会将嵌套值平展到单个列中。随后,AWS DMS 将关键字段和数据类型添加到目标表的列集。

对于每个 MongoDB 文档,AWS DMS 会将每个键和类型添加到目标表的列集中。例如,通过使用表模式,AWS DMS 将上一个示例迁移到下表中。

oid_id a b c
5a94815f40bd44d1b02bdfe0 1 2 3
5a94815f40bd44d1b02bdfe1 4 5 6

嵌套值平展到包含键名 (以句点分隔) 的列中。该列的名称是为由句点分隔的平展字段名的联接。例如,AWS DMS 将具有嵌套值字段(如 {"a" : {"b" : {"c": 1}}})的 JSON 文档迁移到名为 a.b.c. 的列中

为了创建目标列,AWS DMS 扫描指定数量的 MongoDB 文档并创建所有字段及其类型的集合。然后,AWS DMS 使用此集合来创建目标表的列。如果您使用控制台创建或修改 MongoDB 源终端节点,则可以指定要扫描的文档数。默认值为 1000 个文档。如果您使用 AWS CLI,则可以使用额外的连接属性 docsToInvestigate

在表模式中,AWS DMS 按如下方式管理文档和集合:

  • 当您将一个文档添加到现有集合时,将复制该文档。如果某些字段在目标中不存在,则不会复制这些字段。

  • 当您更新文档时,复制更新后的文档。如果某些字段在目标中不存在,则不会复制这些字段。

  • 完全支持文档删除。

  • 在 CDC 任务期间,添加新集合不会导致在目标上生成新的表。

  • 不支持重命名集合。

将 MongoDB 作为 AWS DMS 源时所需的权限

对于使用 AWS DMS 源的 MongoDB 迁移,您可以创建具有根权限的用户账户,也可以仅在要迁移的数据库上创建具有权限的用户。

以下代码创建将作为根账户的用户。

use admin db.createUser( { user: "root", pwd: "password", roles: [ { role: "root", db: "admin" } ] } )

以下代码在要迁移的数据库上创建具有最低权限的用户。

use database_to_migrate db.createUser( { user: "dms-user", pwd: "password", roles: [ { role: "read", db: "local" }, "read"] })

为 CDC 配置 MongoDB 副本集

要将持续复制或 CDC 用于 MongoDB,AWS DMS 需要访问 MongoDB 操作日志 (oplog)。要创建 oplog,您需要部署一个副本集 (如果没有副本集)。有关更多信息,请参阅 文档MongoDB。

您可以将 CDC 用于作为源终端节点的 MongoDB 副本集的主节点或辅助节点。

将独立实例转换为副本集

  1. 使用命令行,连接到 mongo.

    mongo localhost
  2. 停止 mongod 服务。

    service mongod stop
  3. 使用以下命令重新启动 mongod

    mongod --replSet "rs0" --auth -port port_number
  4. 使用以下命令测试与副本集的连接:

    mongo -u root -p password --host rs0/localhost:port_number --authenticationDatabase "admin"

如果您计划执行文档模式迁移,请在创建 _id as a separate column 终端节点时选择选项 MongoDB。通过选择此选项,将创建另一个名为 _id 的列以作为主键。AWS DMS 需要第二列以支持数据操作语言 (DML) 操作。

将 MongoDB 作为 AWS DMS 源时的安全要求

AWS DMS 支持 MongoDB 的两种身份验证方法。 这两种身份验证方法用于加密密码,因此它们仅在 authType 参数设置为 PASSWORD 时使用。

身份验证方法如下:MongoDB

  • MONGODB-CR 使用 – 2.x 身份验证时的默认值。MongoDB

  • SCRAM-SHA-1 使用 – 版本 3.x 身份验证时的默认值。MongoDB

如果未指定身份验证方法,AWS DMS 将使用 MongoDB 源版本的默认方法。

并行分段 MongoDB 集合和迁移

为了提高迁移任务的性能,MongoDB 源终端节点支持并行完全加载功能的范围分割选项。换言之,通过将表映射 JSON 设置用于并行完全加载,您可以并行使用线程迁移分段集合。有关更多信息,请参阅表和集合设置规则和操作

以下示例显示了一个 MongoDB 集合,其中包含七个项目,并将 _id 作为主键。


                    包含七个项目的 MongoDB 集合。

要将集合拆分为三个段并并行迁移,您可以将表映射规则添加到迁移任务,如以下 JSON 示例所示。

{ "rules": [ { "rule-type": "selection", "rule-id": "1", "rule-name": "1", "object-locator": { "schema-name": "testdatabase", "table-name": "testtable" }, "rule-action": "include" }, { "rule-type": "table-settings", "rule-id": "2", "rule-name": "2", "object-locator": { "schema-name": "testdatabase", "table-name": "testtable" }, "parallel-load": { "type": "ranges", "columns": [ "_id", "num" ] "boundaries": [ [ "5f805c97873173399a278d79", // First segment will select documents with _id less-than-or-equal-to 5eae7331a282eff90bf8b060 and num less-than-or-equal-to 2 "2" ], [ "5f805cc5873173399a278d7c", // Second segment will select documents with _id > 5f805c97873173399a278d79 and _id less-than-or-equal-to 5f805cc5873173399a278d7c "5" // and num > 2 and num less-than-or-equal-to 5 ] // Third segment is implied and selects documents with _id > 5f805cc5873173399a278d7c ] } } ] }

该表映射定义将源集合拆分为三个段并并行迁移。以下是分割边界。

Data with _id less-than-or-equal-to "5f805c97873173399a278d79" and num less-than-or-equal-to 2 (2 records) Data with _id > "5f805c97873173399a278d79" and num > 2 and _id less-than-or-equal-to "5f805cc5873173399a278d7c" and num less-than-or-equal-to 5 (3 records) Data with _id > "5f805cc5873173399a278d7c" and num > 5 (2 records)

迁移任务完成后,您可以从任务日志中验证表是否并行加载,如以下示例所示。您还可以验证用于从源表卸载每个分段的 MongoDB find() 子句。

[TASK_MANAGER ] I: Start loading segment #1 of 3 of table 'testdatabase'.'testtable' (Id = 1) by subtask 1. Start load timestamp 0005B191D638FE86 (replicationtask_util.c:752) [SOURCE_UNLOAD ] I: Range Segmentation filter for Segment #0 is initialized. (mongodb_unload.c:157) [SOURCE_UNLOAD ] I: Range Segmentation filter for Segment #0 is: { "_id" : { "$lte" : { "$oid" : "5f805c97873173399a278d79" } }, "num" : { "$lte" : { "$numberInt" : "2" } } } (mongodb_unload.c:328) [SOURCE_UNLOAD ] I: Unload finished for segment #1 of segmented table 'testdatabase'.'testtable' (Id = 1). 2 rows sent. [TASK_MANAGER ] I: Start loading segment #1 of 3 of table 'testdatabase'.'testtable' (Id = 1) by subtask 1. Start load timestamp 0005B191D638FE86 (replicationtask_util.c:752) [SOURCE_UNLOAD ] I: Range Segmentation filter for Segment #0 is initialized. (mongodb_unload.c:157) [SOURCE_UNLOAD ] I: Range Segmentation filter for Segment #0 is: { "_id" : { "$lte" : { "$oid" : "5f805c97873173399a278d79" } }, "num" : { "$lte" : { "$numberInt" : "2" } } } (mongodb_unload.c:328) [SOURCE_UNLOAD ] I: Unload finished for segment #1 of segmented table 'testdatabase'.'testtable' (Id = 1). 2 rows sent. [TARGET_LOAD ] I: Load finished for segment #1 of segmented table 'testdatabase'.'testtable' (Id = 1). 1 rows received. 0 rows skipped. Volume transfered 480. [TASK_MANAGER ] I: Load finished for segment #1 of table 'testdatabase'.'testtable' (Id = 1) by subtask 1. 2 records transferred.

目前,AWS DMS 支持以下 MongoDB 数据类型作为分区键列:

  • Double

  • String

  • ObjectId

  • 32 位整数

  • 64 位整数

将 MongoDB 作为 AWS DMS 源时的限制

将 MongoDB 作为 AWS DMS 源时,存在以下限制:

  • _id 选项设置为单独一列时,ID 字符串不能超过 200 个字符。

  • 在表模式下,对象 ID 和数组类型键将转换为具有 oidarray 前缀的列。

    将使用具有前缀的名称在内部引用这些列。如果您在 AWS DMS 中使用引用了这些列的转换规则,则必须指定具有前缀的列。例如,指定 ${oid__id} 而不是 ${_id},或者指定 ${array__addresses} 而不是 ${_addresses}

  • 集合名称不能包含美元符号 ($)。

  • 表模式和文档模式具有前面讨论的限制。

将 MongoDB 作为 AWS DMS 源时的额外连接属性

在设置 MongoDB 源终端节点时,您可以指定额外的连接属性。通过键值对指定额外的连接属性。如果您具有多个连接属性设置,请用分号将它们彼此分开,并且不需要额外的空格(例如,oneSetting;thenAnother)。

下表介绍了将 MongoDB 数据库作为 AWS DMS 源时可用的额外连接属性。

属性名称 有效值 默认值和描述

authType

"no"

"password"

"password" – 如果指定 "no",则不使用用户名和密码参数,这两个参数可以为空。

authMechanism

"default"

"mongodb_cr"

"scram_sha_1"

对于默认值,在 MongoDB 版本 2.x 中,"default""mongodb_cr"。 对于 MongoDB 版本 3.x 或更高版本,"default""scram_sha_1"。 当 authType 设置为 "no" 时,不使用此设置。

nestingLevel

"none"

"one"

"none" – 指定 "none" 使用文档模式。指定 "one" 使用表模式。

extractDocID

"true"

"false"

"false" – 当 nestingLevel 设为 "none" 时使用此属性。

docsToInvestigate

大于 0 的正整数。

1000 – 当 nestingLevel 设为 "one" 时使用此属性。

authSource

有效的 MongoDB 数据库名称。

"admin" – 当 authType 设为 "no" 时,不使用此属性。

注意

如果目标终端节点为 DocumentDB,请确保为 MongoDB 源设置以下额外连接属性,如下所示:

  • nestingLevel="none"

  • extractDocID="false"

有关更多信息,请参阅将 Amazon DocumentDB 作为 AWS Database Migration Service 的目标

MongoDB 的源数据类型

将 MongoDB 作为 AWS DMS 源的数据迁移支持大多数 MongoDB 数据类型。在下表中,您可以找到使用 MongoDB 时支持的 AWS DMS 源数据类型以及来自 AWS DMS 数据类型的默认映射。有关 MongoDB 数据类型的更多信息,请参阅 文档中的 BSON 类型MongoDB。

有关如何查看目标中映射的数据类型的信息,请参阅有关所使用的目标终端节点的部分。

有关 AWS DMS 数据类型的其他信息,请参阅AWS Database Migration Service 的数据类型

MongoDB 数据类型

AWS DMS 数据类型

布尔型

Bool

二进制

BLOB

Date

Date

时间戳

Date

Int

INT4

长整型

INT8

Double

REAL8

字符串 (UTF-8)

CLOB

数组

CLOB

OID

String

REGEX

CLOB

CODE

CLOB