• mongodb副本集自动切换修复节点解决方案


    副本集部署
    1.启动mongod
    在每台运行mongod服务的机器上增加配置文件/etc/mongodb-rs.conf,内容为:
    [root@MongodbF-A etc]# vi /etc/mongodb-rs.conf
    port = 27017
    dbpath = /data/db
    logpath = /log/log.log
    fork = true
    replSet = test
    通过下面命令启动mongod:
    [root@MongodbF-A etc]# /App/mongo/bin/mongod -f /etc/mongodb-rs.conf
    about to fork child process, waiting until server is ready for connections.
    all output going to: /log/log.log
    log file [/log/log.log] exists; copied to temporary file [/log/log.log.2013-07-18T10-00-56]
    forked process: 8513
    child process started successfully, parent exiting
    [root@MongodbF-A etc]# 
    [root@MongodbF-B App]# /App/mongo/bin/mongod -f /etc/mongodb-rs.conf 
    about to fork child process, waiting until server is ready for connections.
    all output going to: /log/log.log
    log file [/log/log.log] exists; copied to temporary file [/log/log.log.2013-07-18T10-00-06]
    forked process: 8314
    child process started successfully, parent exiting
    [root@MongodbF-B App]# 
    [root@MongodbF-C App]#  /App/mongo/bin/mongod -f /etc/mongodb-rs.conf 
    about to fork child process, waiting until server is ready for connections.
    all output going to: /log/log.log
    log file [/log/log.log] exists; copied to temporary file [/log/log.log.2013-07-18T10-06-38]
    forked process: 8083
    [Achild process started successfully, parent exiting
    [root@MongodbF-C App]# 
    2. 修改每个机器的/etc/hosts
    [root@MongodbF-A etc]# vim /etc/hosts
    # Do not remove the following line, or various programs
    # that require network functionality will fail.
    127.0.0.1               MongodbF-A localhost.localdomain localhost
    ::1             localhost6.localdomain6 localhost6
    192.168.155.224 mongodb1.example.net
    192.168.155.225 mongodb2.example.net
    192.168.155.226 mongodb3.example.net
    ~
    2. 使用mongo shell连接mongod,进行配置:
    [root@MongodbF-A etc]# /App/mongo/bin/mongo  192.168.155.224
    MongoDB shell version: 2.4.5
    connecting to: 192.168.155.224/test
    Welcome to the MongoDB shell.
    For interactive help, type "help".
    For more comprehensive documentation, see
            http://docs.mongodb.org/
    Questions? Try the support group
            http://groups.google.com/group/mongodb-user
    > config = {_id:'test',members:[
    ... _id:0,host:'mongodb1.example.net'},
    ... _id:1,host:'mongodb2.example.net'},
    Thu Jul 18 18:10:52.802 JavaScript execution failed: SyntaxError: Unexpected token :
    > config = {_id:'test',members:[ _id:0,host:'mongodb1.example.net'}, _id:1,host:'mongodb2.example.net'},{_id:2,host:'mongodb3.example.net'}]}
    Thu Jul 18 18:11:54.575 JavaScript execution failed: SyntaxError: Unexpected token :
    > config_test={"_id":"test",members:[    --------------定义配置信息
    ... {_id:0,host:"mongodb1.example.net"},
    ... {_id:1,host:"mongodb2.example.net"},
    ... {_id:2,host:"mongodb3.example.net"}]
    ... }
    {
            "_id" : "test",
            "members" : [
                    {
                            "_id" : 0,
                            "host" : "mongodb1.example.net"
                    },
                    {
                            "_id" : 1,
                            "host" : "mongodb2.example.net"
                    },
                    {
                            "_id" : 2,
                            "host" : "mongodb3.example.net"
                    }
            ]
    }
    >
    > rs.initiate(config_test)    -----启动副本集


    {
            "info" : "Config now saved locally.  Should come online in about a minute.",
            "ok" : 1
    }
    test:STARTUP2> 
    test:STARTUP2> 
    test:SECONDARY> 
    test:SECONDARY> 
    test:SECONDARY> 
    test:SECONDARY> 
    test:SECONDARY> 
    test:SECONDARY> 
    test:SECONDARY> 
    test:SECONDARY> 
    test:SECONDARY> 
    test:SECONDARY> 
    test:SECONDARY> 
    test:SECONDARY> 
    test:SECONDARY> rs.status()
    {
            "set" : "test",
            "date" : ISODate("2013-07-18T10:19:03Z"),
            "myState" : 2,
            "members" : [
                    {
                            "_id" : 0,
                            "name" : "mongodb1.example.net:27017",
                            "health" : 1,
                            "state" : 2,
                            "stateStr" : "SECONDARY",
                            "uptime" : 1087,
                            "optime" : Timestamp(1374142698, 1),
                            "optimeDate" : ISODate("2013-07-18T10:18:18Z"),
                            "self" : true
                    },
                    {
                            "_id" : 1,
                            "name" : "mongodb2.example.net:27017",
                            "health" : 1,
                            "state" : 5,
                            "stateStr" : "STARTUP2",
                            "uptime" : 44,
                            "optime" : Timestamp(0, 0),
                            "optimeDate" : ISODate("1970-01-01T00:00:00Z"),
                            "lastHeartbeat" : ISODate("2013-07-18T10:18:56Z"),
                            "lastHeartbeatRecv" : ISODate("2013-07-18T10:18:54Z"),
                            "pingMs" : 273
                    },
                    {
                            "_id" : 2,
                            "name" : "mongodb3.example.net:27017",
                            "health" : 1,
                            "state" : 5,
                            "stateStr" : "STARTUP2",
                            "uptime" : 44,
                            "optime" : Timestamp(0, 0),
                            "optimeDate" : ISODate("1970-01-01T00:00:00Z"),
                            "lastHeartbeat" : ISODate("2013-07-18T10:18:45Z"),
                            "lastHeartbeatRecv" : ISODate("2013-07-18T10:18:56Z"),
                            "pingMs" : 62
                    }
            ],
            "ok" : 1
    }
    test:SECONDARY>
    新成员初始状态为"stateStr" : "(not reachable/healthy)",然后变成"stateStr" : "STARTUP2",然后变成"stateStr" : "RECOVERING",最后当数据同步成功后,状态变为"stateStr" : "SECONDARY"。
    test:SECONDARY> rs.status()
    {
            "set" : "test",
            "date" : ISODate("2013-07-18T10:28:57Z"),
            "myState" : 1,
            "members" : [
                    {
                            "_id" : 0,
                            "name" : "mongodb1.example.net:27017",
                            "health" : 1,
                            "state" : 1,
                            "stateStr" : "PRIMARY",
                            "uptime" : 1681,
                            "optime" : Timestamp(1374142698, 1),
                            "optimeDate" : ISODate("2013-07-18T10:18:18Z"),
                            "self" : true
                    },
                    {
                            "_id" : 1,
                            "name" : "mongodb2.example.net:27017",
                            "health" : 1,
                            "state" : 2,
                            "stateStr" : "SECONDARY",
                            "uptime" : 638,
                            "optime" : Timestamp(1374142698, 1),
                            "optimeDate" : ISODate("2013-07-18T10:18:18Z"),
                            "lastHeartbeat" : ISODate("2013-07-18T10:28:55Z"),
                            "lastHeartbeatRecv" : ISODate("2013-07-18T10:28:55Z"),
                            "pingMs" : 0,
                            "syncingTo" : "mongodb1.example.net:27017"
                    },
                    {
                            "_id" : 2,
                            "name" : "mongodb3.example.net:27017",
                            "health" : 1,
                            "state" : 2,
                            "stateStr" : "SECONDARY",
                            "uptime" : 638,
                            "optime" : Timestamp(1374142698, 1),
                            "optimeDate" : ISODate("2013-07-18T10:18:18Z"),
                            "lastHeartbeat" : ISODate("2013-07-18T10:28:56Z"),
                            "lastHeartbeatRecv" : ISODate("2013-07-18T10:28:56Z"),
                            "pingMs" : 0,
                            "syncingTo" : "mongodb1.example.net:27017"
                    }
            ],
            "ok" : 1
    }
    test:PRIMARY> 
    3. 故障切换
    假设224为Primary,其它为Secondary,则可以使用mongo shell连接224,看到下面结果
    [root@MongodbF-B App]# /App/mongo/bin/mongo 192.168.155.224
    MongoDB shell version: 2.4.5
    connecting to: 192.168.155.224/test
    Welcome to the MongoDB shell.
    For interactive help, type "help".
    For more comprehensive documentation, see
            http://docs.mongodb.org/
    Questions? Try the support group
            http://groups.google.com/group/mongodb-user
    test:PRIMARY> rs.isMaster()
    {
            "setName" : "test",
            "ismaster" : true,
            "secondary" : false,
            "hosts" : [
                    "mongodb1.example.net:27017",
                    "mongodb3.example.net:27017",
                    "mongodb2.example.net:27017"
            ],
            "primary" : "mongodb1.example.net:27017",
            "me" : "mongodb1.example.net:27017",
            "maxBsonObjectSize" : 16777216,
            "maxMessageSizeBytes" : 48000000,
            "localTime" : ISODate("2013-07-18T10:30:33.734Z"),
            "ok" : 1
    }
    test:PRIMARY>
    同时可以连接225查看状态;
    [root@MongodbF-C App]# /App/mongo/bin/mongo 192.168.155.225
    MongoDB shell version: 2.4.5
    connecting to: 192.168.155.225/test
    Welcome to the MongoDB shell.
    For interactive help, type "help".
    For more comprehensive documentation, see
            http://docs.mongodb.org/
    Questions? Try the support group
            http://groups.google.com/group/mongodb-user
    test:SECONDARY> rs.isMaster()
    {
            "setName" : "test",
            "ismaster" : false,
            "secondary" : true,
            "hosts" : [
                    "mongodb2.example.net:27017",
                    "mongodb3.example.net:27017",
                    "mongodb1.example.net:27017"
            ],
            "primary" : "mongodb1.example.net:27017",
            "me" : "mongodb2.example.net:27017",
            "maxBsonObjectSize" : 16777216,
            "maxMessageSizeBytes" : 48000000,
            "localTime" : ISODate("2013-07-18T10:32:03.170Z"),
            "ok" : 1
    }
    test:SECONDARY>
    我们停止224的mongod,然后发现已经mongo shell连接不上,而通过另外两个成员可以看到副本集的状态:
    [root@MongodbF-A etc]# kill 8513
    [root@MongodbF-A etc]# /App/mongo/bin/mongo  192.168.155.224
    MongoDB shell version: 2.4.5
    connecting to: 192.168.155.224/test
    Thu Jul 18 18:38:08.920 JavaScript execution failed: Error: couldn't connect to server 192.168.155.224:27017 at src/mongo/shell/mongo.js:L114
    exception: connect failed
    [root@MongodbF-A etc]# 
    停掉了;
    然后查看225,226状态;
    [root@MongodbF-C App]# /App/mongo/bin/mongo 192.168.155.226
    MongoDB shell version: 2.4.5
    connecting to: 192.168.155.226/test
    test:PRIMARY> rs.status()
    {
            "set" : "test",
            "date" : ISODate("2013-07-18T10:39:19Z"),
            "myState" : 1,
            "members" : [
                    {
                            "_id" : 0,
                            "name" : "mongodb1.example.net:27017",
                            "health" : 0,
                            "state" : 8,
                            "stateStr" : "(not reachable/healthy)",
                            "uptime" : 0,
                            "optime" : Timestamp(1374142698, 1),
                            "optimeDate" : ISODate("2013-07-18T10:18:18Z"),
                            "lastHeartbeat" : ISODate("2013-07-18T10:39:17Z"),
                            "lastHeartbeatRecv" : ISODate("2013-07-18T10:38:35Z"),
                            "pingMs" : 0
                    },
                    {
                            "_id" : 1,
                            "name" : "mongodb2.example.net:27017",
                            "health" : 1,
                            "state" : 2,
                            "stateStr" : "SECONDARY",
                            "uptime" : 1222,
                            "optime" : Timestamp(1374142698, 1),
                            "optimeDate" : ISODate("2013-07-18T10:18:18Z"),
                            "lastHeartbeat" : ISODate("2013-07-18T10:39:18Z"),
                            "lastHeartbeatRecv" : ISODate("2013-07-18T10:39:19Z"),
                            "pingMs" : 0,
                            "lastHeartbeatMessage" : "syncing to: mongodb3.example.net:27017",
                            "syncingTo" : "mongodb3.example.net:27017"
                    },
                    {
                            "_id" : 2,
                            "name" : "mongodb3.example.net:27017",
                            "health" : 1,
                            "state" : 1,
                            "stateStr" : "PRIMARY",
                            "uptime" : 1961,
                            "optime" : Timestamp(1374142698, 1),
                            "optimeDate" : ISODate("2013-07-18T10:18:18Z"),
                            "self" : true
                    }
            ],
            "ok" : 1
    }
    test:PRIMARY> 
    225中:
    test:SECONDARY> rs.isMaster()
    {
            "setName" : "test",
            "ismaster" : false,
            "secondary" : true,
            "hosts" : [
                    "mongodb2.example.net:27017",
                    "mongodb3.example.net:27017",
                    "mongodb1.example.net:27017"
            ],
            "primary" : "mongodb3.example.net:27017",
            "me" : "mongodb2.example.net:27017",
            "maxBsonObjectSize" : 16777216,
            "maxMessageSizeBytes" : 48000000,
            "localTime" : ISODate("2013-07-18T10:38:59.686Z"),
            "ok" : 1
    }
    test:SECONDARY> 
    看到故障切换成功;
    故障修复后,重启查看状态;
    [root@MongodbF-A etc]# /App/mongo/bin/mongod -f /etc/mongodb-rs.conf
    about to fork child process, waiting until server is ready for connections.
    all output going to: /log/log.log
    forked process: 8891
    log file [/log/log.log] exists; copied to temporary file [/log/log.log.2013-07-18T10-40-36]
    child process started successfully, parent exiting
    [root@MongodbF-A etc]# /App/mongo/bin/mongo  192.168.155.224
    MongoDB shell version: 2.4.5
    connecting to: 192.168.155.224/test
    test:SECONDARY> rs.status()
    {
            "set" : "test",
            "date" : ISODate("2013-07-18T10:40:48Z"),
            "myState" : 2,
            "syncingTo" : "mongodb3.example.net:27017",
            "members" : [
                    {
                            "_id" : 0,
                            "name" : "mongodb1.example.net:27017",
                            "health" : 1,
                            "state" : 2,
                            "stateStr" : "SECONDARY",
                            "uptime" : 12,
                            "optime" : Timestamp(1374142698, 1),
                            "optimeDate" : ISODate("2013-07-18T10:18:18Z"),
                            "errmsg" : "syncing to: mongodb3.example.net:27017",
                            "self" : true
                    },
                    {
                            "_id" : 1,
                            "name" : "mongodb2.example.net:27017",
                            "health" : 1,
                            "state" : 2,
                            "stateStr" : "SECONDARY",
                            "uptime" : 12,
                            "optime" : Timestamp(1374142698, 1),
                            "optimeDate" : ISODate("2013-07-18T10:18:18Z"),
                            "lastHeartbeat" : ISODate("2013-07-18T10:40:48Z"),
                            "lastHeartbeatRecv" : ISODate("2013-07-18T10:40:47Z"),
                            "pingMs" : 0,
                            "syncingTo" : "mongodb3.example.net:27017"
                    },
                    {
                            "_id" : 2,
                            "name" : "mongodb3.example.net:27017",
                            "health" : 1,
                            "state" : 1,
                            "stateStr" : "PRIMARY",
                            "uptime" : 12,
                            "optime" : Timestamp(1374142698, 1),
                            "optimeDate" : ISODate("2013-07-18T10:18:18Z"),
                            "lastHeartbeat" : ISODate("2013-07-18T10:40:48Z"),
                            "lastHeartbeatRecv" : ISODate("2013-07-18T10:40:48Z"),
                            "pingMs" : 1
                    }
            ],
            "ok" : 1
    }
    test:SECONDARY> 
    启动成功成为了secondary了
    至此,副本集的故障切换完成;
    test:SECONDARY> rs.config()
    {
            "_id" : "test",
            "version" : 1,
            "members" : [
                    {
                            "_id" : 0,
                            "host" : "mongodb1.example.net:27017"
                    },
                    {
                            "_id" : 1,
                            "host" : "mongodb2.example.net:27017"
                    },
                    {
                            "_id" : 2,
                            "host" : "mongodb3.example.net:27017"
                    }
            ]
    }
    test:SECONDARY>
    4、尝试在SECONDARY上插入数据;
    test:SECONDARY> db.song.insert({"name":"xixi"})
    not master
    test:SECONDARY> 
    返回not master。所以必须使用驱动连接到PRIMARY上进行操作,必须在应用上对这种故障切换做进一步控制,保证是对PRIMARY进行操作。
    test:PRIMARY> db.song.insert({"name":"xixi"})
    test:PRIMARY> db.song.find()
    { "_id" : ObjectId("51e7c776ec806afa1810aeff"), "name" : "xixi" }
    test:SECONDARY> show tables;
    Thu Jul 18 18:46:24.018 JavaScript execution failed: error: { "$err" : "not master and slaveOk=false", "code" : 13435 } at src/mongo/shell/query.js:L128
    test:SECONDARY> 
    可以通过rs.slaveOk()命令使该SECONDARY可以进行读操作:
    test:SECONDARY> show tables;
    Thu Jul 18 18:46:24.018 JavaScript execution failed: error: { "$err" : "not master and slaveOk=false", "code" : 13435 } at src/mongo/shell/query.js:L128
    test:SECONDARY> rs.slaveOk()
    test:SECONDARY> show tables;
    song
    system.indexes
    test:SECONDARY> db.song.find()
    { "_id" : ObjectId("51e7c776ec806afa1810aeff"), "name" : "xixi" }
    test:SECONDARY> db.song.insert({"name":"xixi"})   -----只读,不能写的类型;
    not master
    test:SECONDARY> 



  • 相关阅读:
    redis--列表
    redis ——字符串
    redis 第一节 redis安装、PHP扩展 、主从
    Python--day7
    Python--day6
    Python爬虫
    JSON基础
    Python--day5
    Python—day3
    Windows10 安装QT问题
  • 原文地址:https://www.cnblogs.com/javawebsoa/p/3201229.html
Copyright © 2020-2023  润新知