2016-11-23 202 views
0

當連接到MongoDB副本集時,我可以從輔助節點讀取數據,但事後使用相同連接寫入時,我收到以下錯誤:Pymongo讀取首選項 - ServerSelectionTimeoutError:沒有主要可用於寫入

pymongo.errors.ServerSelectionTimeoutError: No primary available for writes 

的Python 3.4.3 Pymongo 3.2.2

我的連接:

var_host = 'XXX.XXX.XXX.XXX' # Public IP 
var_port = 27017 
var_username = 'username' 
var_password = 'password' 
mongo_uri = 'mongodb://%s:%[email protected]%s:%s' % (username, password, host, port) 
client_db = MongoClient(mongo_uri, 
       replicaSet='rs0', 
       readPreference='secondaryPreferred') 

我重要:當刪除'replicaSet'和'readPrefence'字段時,連接將起作用。

在服務器:

rs0:PRIMARY> rs.status() 
{"set" : "rs0", 
"date" : ISODate("2016-11-23T13:09:55.699Z"), 
"myState" : 1, 
"term" : NumberLong(4), 
"heartbeatIntervalMillis" : NumberLong(2000), 
"members" : [ 
    { 
     "_id" : 0, 
     "name" : "mongodb0:27017", 
     "health" : 1, 
     "state" : 1, 
     "stateStr" : "PRIMARY", 
     "uptime" : 64491, 
     "optime" : { 
      "ts" : Timestamp(1479906595, 21), 
      "t" : NumberLong(4) 
     }, 
     "optimeDate" : ISODate("2016-11-23T13:09:55Z"), 
     "electionTime" : Timestamp(1479844637, 1), 
     "electionDate" : ISODate("2016-11-22T19:57:17Z"), 
     "configVersion" : 424888, 
     "self" : true 
    }, 
    { 
     "_id" : 1, 
     "name" : "mongodb2:27017", 
     "health" : 1, 
     "state" : 2, 
     "stateStr" : "SECONDARY", 
     "uptime" : 61631, 
     "optime" : { 
      "ts" : Timestamp(1479906593, 31), 
      "t" : NumberLong(4) 
     }, 
     "optimeDate" : ISODate("2016-11-23T13:09:53Z"), 
     "lastHeartbeat" : ISODate("2016-11-23T13:09:53.776Z"), 
     "lastHeartbeatRecv" : ISODate("2016-11-23T13:09:53.758Z"), 
     "pingMs" : NumberLong(0), 
     "syncingTo" : "XXXXXXXX:27017", 
     "configVersion" : 424888 
    }, 
    { 
     "_id" : 2, 
     "name" : "mongodb3:27017", 
     "health" : 1, 
     "state" : 2, 
     "stateStr" : "SECONDARY", 
     "uptime" : 61264, 
     "optime" : { 
      "ts" : Timestamp(1479906593, 31), 
      "t" : NumberLong(4) 
     }, 
     "optimeDate" : ISODate("2016-11-23T13:09:53Z"), 
     "lastHeartbeat" : ISODate("2016-11-23T13:09:53.776Z"), 
     "lastHeartbeatRecv" : ISODate("2016-11-23T13:09:55.493Z"), 
     "pingMs" : NumberLong(0), 
     "syncingTo" : "XXX:27017", 
     "configVersion" : 424888 
    } 
    ], 
    "ok" : 1} 

db.isMaster()

mongodb0

rs0:PRIMARY> db.isMaster() 
{ 
"hosts" : [ 
    "mongodb0:27017" 
], 
"passives" : [ 
    "10.150.151.141:27017", 
    "10.150.151.155:27017" 
], 
"setName" : "rs0", 
"setVersion" : 424888, 
"ismaster" : true, 
"secondary" : false, 
"primary" : "mongodb0:27017", 
"me" : "mongodb0:27017", 
"electionId" : ObjectId("7fffffff0000000000000004"), 
"maxBsonObjectSize" : 16777216, 
"maxMessageSizeBytes" : 48000000, 
"maxWriteBatchSize" : 1000, 
"localTime" : ISODate("2016-11-23T15:12:37.988Z"), 
"maxWireVersion" : 4, 
"minWireVersion" : 0, 
"ok" : 1 
} 

mongodb1

rs0:SECONDARY> db.isMaster() 
{ 
"hosts" : [ 
    "mongodb0:27017" 
], 
"passives" : [ 
    "10.150.151.141:27017", 
    "10.150.151.155:27017" 
], 
"setName" : "rs0", 
"setVersion" : 424888, 
"ismaster" : false, 
"secondary" : true, 
"primary" : "mongodb0:27017", 
"passive" : true, 
"me" : "10.150.151.141:27017", 
"maxBsonObjectSize" : 16777216, 
"maxMessageSizeBytes" : 48000000, 
"maxWriteBatchSize" : 1000, 
"localTime" : ISODate("2016-11-23T15:24:32.134Z"), 
"maxWireVersion" : 4, 
"minWireVersion" : 0, 
"ok" : 1 

mongodb2

rs0:SECONDARY> db.isMaster() 
{ 
"hosts" : [ 
    "mongodb0:27017" 
], 
"passives" : [ 
    "10.150.151.141:27017", 
    "10.150.151.155:27017" 
], 
"setName" : "rs0", 
"setVersion" : 424888, 
"ismaster" : false, 
"secondary" : true, 
"primary" : "mongodb0:27017", 
"passive" : true, 
"me" : "10.150.151.155:27017", 
"maxBsonObjectSize" : 16777216, 
"maxMessageSizeBytes" : 48000000, 
"maxWriteBatchSize" : 1000, 
"localTime" : ISODate("2016-11-23T15:21:54.971Z"), 
"maxWireVersion" : 4, 
"minWireVersion" : 0, 
"ok" : 1 
} 
+0

我們可以從連接到每個副本集成員的shell中看到你的'mongo_uri'和'db.isMaster()'的輸出嗎? –

+0

@ A.JesseJiryuDavis檢查上面,編輯! Tks – Nadav

回答

1

我假設:

  1. 驅動程序可以在任10.150.151.141:27017或10.150.151.155:27017或兩者連接到您的輔助的公網IP。
  2. 您的連接字符串指向上述公共IP之一,或連接字符串指向主公共IP。
  3. 副本集中使用在其配置內部IP它們到您的客戶機訪問:它無法連接到「mongodb0」,「mongodb1」,或「mongodb2」。

您需要使用公共IP重新配置副本集。如果你很好奇爲什麼這樣,它在Server Discovery and Monitoring Spec中解釋。但要點是:rs.conf()中列出的成員主機名必須是您的客戶機可以訪問的公共主機名。

+0

真棒!!!!!!!! – Nadav