在Windows7环境中构建MongoDB 3.0的副本集

简要概述

我整理了一份在Windows7上创建MongoDB副本集的开发环境和验证步骤。

环境 –

    • Windows7 (64bit)

 

    MongoDB 3.0.2

复制的配置

node nameportroleprioritynode130001primary node2node230002secondary node1node330003secondary node1node430004arbiter1

环境建设

目录结构

本次示例中,在D:\dev文件夹下创建了bin文件夹和每个节点对应的conf、db、log文件夹。

D:\dev\mongodb3.0
            |
            +----- \bin
            |        |
            |        +---- \mongod.exe
            |        +---- \mongo.exe
            |        +---- \shell_node1.bat    (shell_node1.bat~shell_node4.bat)
            |        +---- \startup_node1.bat  (startup_node1.bat~startup_node4.bat)
            |
            +----- \node1
            |        |
            |        +---- \conf\mongod.cfg
            |        +---- \db
            |        +---- \log
            |
            +----- \node2
            |        |
            |        +---- \conf\mongod.cfg
            |        +---- \db
            |        +---- \log
            |
            +----- \node3
            |        |
            |        +---- \conf\mongod.cfg
            |        +---- \db
            |        +---- \log
            |
            +----- \node4
                     |
                     +---- \conf\mongod.cfg
                     +---- \db
                     +---- \log

配置文件

我会为每个节点创建一个conf文件。
然后将创建好的conf文件放置在每个节点目录下的conf文件夹中。

这是一个用于node1的配置文件。

systemLog:
   destination: file
   path: "D:/dev/mongodb3.0/node1/log/mongod.log"
   logAppend: true
   timeStampFormat: iso8601-local
storage:
   dbPath: "D:/dev/mongodb3.0/node1/db"
   directoryPerDB: true
   journal:
      enabled: true
net:
   bindIp: 127.0.0.1
   port: 30001
setParameter:
   enableLocalhostAuthBypass: true
operationProfiling:
   slowOpThresholdMs: 100
   mode: all
replication:
   oplogSizeMB: 128
   replSetName: "myReplica"

其他节点将把以下三个地方的值分别用于每个节点的值。

    • systemLog.path

 

    • storage.dbPath

 

    net.port

准备可执行文件

创建符号链接

创建一个到bin目录的符号链接的exe文件。

> mklink mongod.exe "C:\Program Files\MongoDB\Server\3.0\bin\mongod.exe"
> mklink mongo.exe "C:\Program Files\MongoDB\Server\3.0\bin\mongo.exe"
创建MongoDB启动.bat文件

创建适用于每个节点的MongoDB启动bat文件在bin目录下。

这是用于node1的bat文件。我们将为每个节点创建类似的bat文件。

D:\dev\mongodb3.0\bin\mongod.exe --enableExperimentalIndexStatsCmd --rest --httpinterface --verbose --config D:\dev\mongodb3.0\node1\conf\mongod.cfg
pause

— “httpinterface”是一个选项,可以使浏览器能够查看MongoDB服务器的状态。

将1000添加到MongoDB端口上,并指定该值为端口。
由于node1的端口设为30001,因此httpinterface的端口将为31001。

创建Mongo Shell启动.bat文件

在bin目录下创建用于每个节点的Mongo Shell启动bat文件。
这是用于node1的bat文件。为每个节点创建类似的bat文件。

D:\dev\mongodb3.0\bin\mongo.exe --port 30001 --host localhost --verbose

复制品套装的设置

首先,我們要啟動從node1到node4的MongoDB實例。然後,我們要使用mongo shell登錄到node1作為主要節點。

创建复制套装

在node1上执行以下命令以构建副本集。

> var config = {
  _id: 'myReplica',
  members: [
    {_id:0, host:'localhost:30001', priority:2 },
    {_id:1, host:'localhost:30002', priority:1 },
    {_id:2, host:'localhost:30003', priority:1 },
    {_id:3, host:'localhost:30004', arbiterOnly: true}
  ],
  settings: {
    getLastErrorDefaults: {w:2, wtimeout:0},
    getLastErrorModes: {}
  }
}

> rs.initiate(config)
{ "ok" : 1 }

我会检查复制套装的状态。

> rs.status()
{
        "set" : "myReplica",
        "date" : ISODate("2015-06-06T03:39:33.374Z"),
        "myState" : 1,
        "members" : [
                {
                        "_id" : 0,
                        "name" : "localhost:30001",
                        "health" : 1,
                        "state" : 1,
                        "stateStr" : "PRIMARY",
                        "uptime" : 1399,
                        "optime" : Timestamp(1433553387, 1),
                        "optimeDate" : ISODate("2015-06-06T01:16:27Z"),
                        "electionTime" : Timestamp(1433560639, 1),
                        "electionDate" : ISODate("2015-06-06T03:17:19Z"),
                        "configVersion" : 2,
                        "self" : true
                },
                {
                        "_id" : 1,
                        "name" : "localhost:30002",
                        "health" : 1,
                        "state" : 2,
                        "stateStr" : "SECONDARY",
                        "uptime" : 1336,
                        "optime" : Timestamp(1433553387, 1),
                        "optimeDate" : ISODate("2015-06-06T01:16:27Z"),
                        "lastHeartbeat" : ISODate("2015-06-06T03:39:33.345Z"),
                        "lastHeartbeatRecv" : ISODate("2015-06-06T03:39:33.316Z"),
                        "pingMs" : 0,
                        "lastHeartbeatMessage" : "could not find member to sync from",
                        "configVersion" : 2
                },
                {
                        "_id" : 2,
                        "name" : "localhost:30003",
                        "health" : 1,
                        "state" : 2,
                        "stateStr" : "SECONDARY",
                        "uptime" : 1333,
                        "optime" : Timestamp(1433553387, 1),
                        "optimeDate" : ISODate("2015-06-06T01:16:27Z"),
                        "lastHeartbeat" : ISODate("2015-06-06T03:39:31.898Z"),
                        "lastHeartbeatRecv" : ISODate("2015-06-06T03:39:32.187Z"),
                        "pingMs" : 0,
                        "configVersion" : 2
                },
                {
                        "_id" : 3,
                        "name" : "localhost:30004",
                        "health" : 1,
                        "state" : 7,
                        "stateStr" : "ARBITER",
                        "uptime" : 1330,
                        "lastHeartbeat" : ISODate("2015-06-06T03:39:32.876Z"),
                        "lastHeartbeatRecv" : ISODate("2015-06-06T03:39:31.800Z"),
                        "pingMs" : 0,
                        "configVersion" : 2
                }
        ],
        "ok" : 1
}

MongoDB手册 – 副本集配置

确认数据复制

我們將確認將數據添加到主節點後是否會反映到次要節點。

我将登录主节点并添加测试数据。

> use sample
switched to db sample
> db.test.insert({no:1, desc:"test data"})
WriteResult({ "nInserted" : 1 })

从辅助节点读取数据

如果您想从辅助节点(node2,node3)中引用数据,请执行以下命令进行读取设置。由于这是针对连接的设置,因此每次连接都需要进行设置。

登录到次要节点(node2)。

> db.getMongo().setReadPref('secondaryPreferred')
> use sample
switched to db sample
> show collections
columbo
system.indexes
system.profile
test
> db.test.find()
{ "_id" : ObjectId("5572dcd134829ba85871fcfa"), "no" : 1, "desc" : "test data" }

也可以在每次读取操作时进行设置。

> db.test.find().readPref({mode:'secondaryPreferred'})
{ "_id" : ObjectId("5572dcd134829ba85871fcfa"), "no" : 1, "desc" : "test data" }

在中国,可以使用rs.slaveOk()进行设置,但似乎已经过时了。

设置当前连接的slaveOk属性。已被弃用。使用readPref()和Mongo.setReadPref()来设置读取偏好。

关于阅读设置
Read Preference Modedescriptionprimaryデフォルト.全ての読み取り操作はプライマリーから行うprimaryPreferredプライマリーが利用不能であればセカンダリーから行うsecondary全ての読み取り操作はセカンダリーから行うsecondaryPreferredセカンダリーが利用不能であればプライマリーから行うnearestネットワークレイテンシの小さいメンバーから行う

MongoDB 手册 – 读优先级参考

复制套件的操作方法

methodsdescriptionprimary noders.initiate()レプリカセットを作成します。
rs.reconfig()既存のレプリカセットを再設定します。Only Primary Noders.add()レプリカセットにメンバーを追加します。Only Primary Noders.remove()レプリカセットからメンバーを除外します。除外するメンバーは事前にシャットダウンしておく必要があります。
rs.addArb()レプリカセットにアービターを追加します。
rs.status()レプリカセットのステータスを出力します。
rs.conf()レプリカセットの現在の設定内容を出力します。
rs.help()ヘルプを出力します。
db.isMaster()mongodインスタンスの役割を表示します。
db.getMongo().getReadPrefMode()現在の読み取り設定を出力します。
db.getMongo().setReadPref()読み取り設定を行います。

MongoDB 手册 – 复制方法

复制确认

关于写作保证

optiondescriptionw:0プライマリーにデータが書き込まれたことは保証しません。(書き込み完了の確認を行いません)ネットワークエラーの情報は返します。w:1デフォルトです。プライマリーにデータが書き込まれたことを保証します。 書き込めなかった場合はエラーを返します。w:numbernumberで指定したノードにデータが書き込まれたことを保証します。(プライマリー含む)指定数に書き込めなかった場合はエラーを返します。w:”majority”レプリカセットに参加する過半数のノードにデータが書き込まれたことを保証します。指定数に書き込めなかった場合はエラーを返します。j:trueジャーナルにデータが書き込まれたことを保証します。書き込めなかった場合はエラーを返します。wtimeout書き込み完了のタイムリミットをミリ秒で指定します。0または未指定の場合は無期限にブロックします。wオプションが1以上のときに意味を持ちます。

如果对多个节点进行写操作,即使其中一些节点发生错误,也无法撤消之前已经写入的数据。

设置写入保障(Write concern)的示例

未被认可的

writeConcern: { w: 0 }

已经收到。

writeConcern: { w: 1 }

记录

writeConcern: { w: 1, j:true }

复制品已收到确认

writeConcern: { w: 2 }
writeConcern: { w: "majority" }
验证书写保证的操作功能。

从主节点(node1)和两个辅助节点(node2,node3)的状态开始,我们尝试在去掉辅助节点(node3)的情况下,使用以下写入保证({writeConcern:{w:3, wtimeout:5000}})添加文档。
这个设置的意思是“保证在5000毫秒内完成写入至三个节点”,但在这个例子中,由于可用节点不足而导致发生错误。

var a = {no:1, name:"test"}
> db.test.insert(a, {writeConcern:{w:3, wtimeout:5000}})
WriteResult({
        "nInserted" : 1,
        "writeConcernError" : {
                "code" : 64,
                "errInfo" : {
                        "wtimeout" : true
                },
                "errmsg" : "waiting for replication timed out"
        }
})

可能有节点1和节点2写入数据已经完成。

将写入保证更改为{writeConcern:{w:2, wtimeout:5000}},并将文档添加到node1、node2,这样就可以进行写入操作,不会出现错误。

> db.test.insert(a, {writeConcern:{w:2, wtimeout:5000}})
WriteResult({ "nInserted" : 1 })

MongoDB手册-写关注

关于节点的排除和添加

在构建复制集之后,您仍然可以对节点进行排除和添加的操作。

在排除辅助节点后进行操作验证

我们会暂时将一个次要节点从副本集中移除,并确保在其重新加入副本集后,添加到主节点上的数据会自动同步。

在此示例中,暂时排除节点3。
在排除辅助节点(节点3)之前,关闭MongoDB。

> use admin
switched to db admin
> db.shutdownServer()

在主节点(node1)上检查副本集的状态。

> rs.status()

将第三个节点从复制集中排除。

> rs.remove("localhost:30003")
{ "ok" : 1 }

再次检查复制集的状态,确认节点3已被排除。

> rs.status()

在主节点上添加数据。

> db.test.insert({no:3, desc:"before node3 add"})
WriteResult({ "nInserted" : 1 })

启动node3的MongoDB,并将其加入到副本集。

> rs.add("localhost:30003")
{ "ok" : 1 }

通过查看复制集的状态,确认成员中是否添加了node3。

> rs.status()

确认在node3上登录并确认数据已经更新。

> db.test.find({no:3})
{ "_id" : ObjectId("55729c1834829ba85871fcf6"), "no" : 3, "desc" : "before node3 add" }
在排除主节点后进行操作验证

确认排除主节点(node1),并确保次要节点(node2或node3)升级为主节点。然后确认恢复排除的主节点(node1)并与升级的次要节点交换。

关闭主节点(node1)。

> use admin
switched to db admin
> db.shutdownServer()

登录到次要节点(node2),查看副本集的状态,确认剩余节点中有一个变成了主节点。
在这个例子中,假设node2成为了主节点。

> rs.status()

在升级为主节点的node2上添加数据。

> use sample
switched to db admin
> db.test.insert({no:2, desc:"inset data from node2"})
WriteResult({ "nInserted" : 1 })

启动node1上的MongoDB,并查看复制集的状态以确认node1已经恢复为主节点。

> rs.status()

我们将确认在node2中添加的数据。

> db.test.find()
{ "_id" : ObjectId("5572dcd134829ba85871fcfa"), "no" : 1, "desc" : "test data" }
{ "_id" : ObjectId("5572e07ab6e83d84b2e82956"), "no" : 2, "desc" : "inset data from node2" }

参考网站

我参考了下面的网站。

    • MongoDB manual – replication

 

    • gihyo.jp – 第4回 MongoDBのレプリケーションを構築してみよう

 

    gihyo.jp – 第6回 レプリケーション+シャーディングでMongoDBをもっと使いこなす
广告
将在 10 秒后关闭
bannerAds