摘要:容器訪問(wèn)以為例,在原始的文件中,如下上面的配置,本地主機(jī)是無(wú)法訪問(wèn)容器的,我們至少需要暴露出一個(gè)端口。查看,的默認(rèn)端口其實(shí)是,而這里寫(xiě)成也是有原因的。
任何事情的成功都需要掐準(zhǔn)時(shí)間
上一節(jié)mongo EOF中,關(guān)于容器的配置,只是粗略的使用了Docker-Compose-MongoDB-Replica-Set項(xiàng)目提供好的docker-compose.yml文件。在使用過(guò)程中,我發(fā)現(xiàn)這個(gè)文件本身一些不如意的地方。首先,services中的creator服務(wù),entrypoint指令太長(zhǎng)了,不美;其次,所有的service都沒(méi)有給容器外部暴露端口,導(dǎo)致外部無(wú)法訪問(wèn)容器;再次,直接使用mongo repliSet的連接串進(jìn)行訪問(wèn),無(wú)法正常訪問(wèn)mongo服務(wù)。
在上一篇文章的基礎(chǔ)上,這篇文章對(duì)docker-compse.yml做了一些調(diào)整,并且也包含了docker使用的入門(mén)介紹。更新后的docker-compose.yml請(qǐng)?jiān)L問(wèn)githubsi。
depends_onHowever, for startup Compose does not wait until a container is “ready” (whatever that means for your particular application) - only until it’s running. There’s a good reason for this.
在creator service中使用了該指令, 但是,實(shí)際中creator不會(huì)等到mongo1、mongo2、mongo3容器ready后再啟動(dòng),而是等到它們啟動(dòng)就開(kāi)始啟動(dòng)。這也是我在setup腳本中執(zhí)行sleep操作的原因。
creator: build: context: . dockerfile: dockerfile entrypoint: ["/data/conf/setup.sh"] depends_on: - mongo1 - mongo2 - mongo3entrypoint
Entrypoint sets the command and parameters that will be executed first when a container is run.
entrypoint設(shè)置了容器啟動(dòng)時(shí)執(zhí)行的命令和參數(shù),傳遞給docker run
命令的語(yǔ)法格式:
ENTRYPOINT ["executable" "param1" "param2"]
在修改后的docker-compose.yml中,entrypoint指令用于執(zhí)行shell腳本。按照規(guī)范來(lái)說(shuō),可執(zhí)行文件名稱(chēng)中需要包含entrypoint字段,也就是將下列指令中的setup.sh重命名為setup-entrypoint.sh。但是,重命名之后的文件,容器執(zhí)行會(huì)報(bào)錯(cuò),所以,這里也并沒(méi)有使用這個(gè)規(guī)范。
entrypoint: ["/data/conf/setup.sh"]調(diào)整creator中的entrypoint指令
原始的文件如下所示,entrypoint指令的參數(shù)非常難看:
creator: build: creator entrypoint: ["mongo","--host","mongo1","--port","27017","--eval", "rs.initiate( { _id : "rs0",members: [{ _id: 0, host: "mongo1:27017" },{ _id: 1, host: "mongo2:27017" },{ _id: 2, host: "mongo3:27017" } ]})"] depends_on: - mongo1 - mongo2 - mongo3
如果將entrypoint的執(zhí)行命令提取到一個(gè)多帶帶的的腳本中,會(huì)讓整個(gè)頁(yè)面看起來(lái)更加簡(jiǎn)潔。所以,新建一個(gè)setup.sh文件。其中的replicaSet.js用于執(zhí)行rs.initiate操作,詳情可以查看github項(xiàng)目。其中的sleep指令只是為了保證:在執(zhí)行initiate時(shí)mongo的3個(gè)服務(wù)都啟動(dòng)了。
#! /bin/bash echo "******************************" echo Start the replica set echo `date` echo "******************************" sleep 20 | echo Sleeping echo `date` mongo mongodb://mongo1:37017 replicaSet.js
相應(yīng)的,我們需要調(diào)整creator的dockerfile文件,因?yàn)榇藭r(shí)的容器內(nèi),并沒(méi)有我們需要的相關(guān)文件。我們需要在創(chuàng)建鏡像的時(shí)候,拷貝本地文件到容器。調(diào)整后的文件如下:
FROM mongo:4.0.4 MAINTAINER Yowko TsaiWORKDIR /data/conf COPY ./setup.sh /data/conf/setup.sh COPY ./replicaSet.js /data/conf/replicaSet.js CMD ["./setup.sh"]
在項(xiàng)目的目錄下,我們多帶帶編譯creator的dockerfile文件,已保證調(diào)整是有效的。
docker build . docker run容器訪問(wèn)
以mongo1為例,在原始的文件中,docker-compose.yml如下:
mongo1: container_name: mongo1 image: mongo:4-xenial expose: - 27017 restart: always entrypoint: [ "mongod", "--bind_ip_all", "--replSet", "rs0" ]
上面的配置,本地主機(jī)是無(wú)法訪問(wèn)容器的,我們至少需要暴露出一個(gè)端口。下面通過(guò)添加ports來(lái)指定容器外到容器內(nèi)的端口映射。在上一篇中已經(jīng)介紹過(guò)ports和expose的相關(guān)內(nèi)容,感興趣的可以去查看。之后,我們就可以通過(guò)37017端口來(lái)訪問(wèn)容器內(nèi)的mongo1服務(wù)了。
mongo1: container_name: mongo1 image: mongo:4.0.4 expose: - 37017 ports: - "37017:37017" restart: always entrypoint: [ "mongod", "--port", "37017", "--bind_ip_all", "--replSet", "rs0" ]
查看Default MongoDB Port,mongod的默認(rèn)端口其實(shí)是27017,而這里寫(xiě)成37017也是有原因的。未修改之前mongod的端口映射,如下所示。每個(gè)容器中的mongo服務(wù)都使用默認(rèn)的27017端口,通過(guò)暴露不通的宿主主機(jī)端口來(lái)達(dá)到區(qū)分容器服務(wù)的目的。
mongo1: container_name: mongo1 image: mongo:4.0.4 expose: - 27017 ports: - "27017:27017" restart: always entrypoint: [ "mongod", "--bind_ip_all", "--replSet", "rs0" ] mongo2: container_name: mongo2 image: mongo:4.0.4 expose: - 27017 ports: - "27018:27017" restart: always entrypoint: [ "mongod", "--bind_ip_all", "--replSet", "rs0" ] mongo3: container_name: mongo3 image: mongo:4.0.4 expose: - 27017 ports: - "27019:27017" restart: always entrypoint: [ "mongod", "--bind_ip_all", "--replSet", "rs0" ]
在多帶帶連接mongo服務(wù)的時(shí)候,這樣的配置是沒(méi)有任何問(wèn)題的。我們?cè)诿钚休斎?b>mongo,也會(huì)連接到其中任意一個(gè)mongo服務(wù)。如果恰好連接的不是PRIMARY節(jié)點(diǎn),可以執(zhí)行rs.slaveOk()來(lái)執(zhí)行查詢(xún)。
但當(dāng)使用replicaSet連接串來(lái)訪問(wèn)mongo服務(wù)時(shí),連接卻會(huì)失敗??纯催@個(gè)連接串,感覺(jué)不出任何問(wèn)題。
mongo mongodb://127.0.0.1:27017,127.0.0.1:27018,127.0.0.1:27019/admin?replicaSet=rs0
看了報(bào)錯(cuò)信息,才明白:當(dāng)執(zhí)行連接的時(shí)候,mongo會(huì)拉取replica set 的配置信息,而通過(guò)host去訪問(wèn)的時(shí)候失敗了。很明顯:docker-compose容器內(nèi)可以將server name當(dāng)作host來(lái)相互訪問(wèn),但在容器外通過(guò)server name是訪問(wèn)不通的。
changing hosts to rs0/mongo1:27017,mongo2:27017,mongo3:27017 from rs0/127.0.0.1:27017,127.0.0.1:27018,127.0.0.1:27019
另外,你還可以在容器內(nèi)部打開(kāi)/etc/hosts文件,查看容器內(nèi)映射的ip地址,容器外也是ping不通的。我們可以通過(guò)下面的指令進(jìn)入容器查看:
docker exec -itbash less /etc/hosts
解決的辦法是,我們?cè)诒镜刂鳈C(jī)上追加host。但這樣的話,rs0其實(shí)只有一個(gè)節(jié)點(diǎn),因?yàn)槎加成涞搅?b>127.0.0.1:27017這個(gè)容器上。
# file: /etc/hosts 127.0.0.1 mongo1, mongo2, mongo3
基于這個(gè)原因,我們修改了容器內(nèi)外暴露的端口。同時(shí),修改各個(gè)服務(wù)mongod啟動(dòng)時(shí)的默認(rèn)端口以及replica set的配置信息:
mongo1: container_name: mongo1 image: mongo:4.0.4 expose: - 37017 ports: - "37017:37017" restart: always entrypoint: [ "mongod", "--port", "37017", "--bind_ip_all", "--replSet", "rs0" ] mongo2: container_name: mongo2 image: mongo:4.0.4 expose: - 37018 ports: - "37018:37018" restart: always entrypoint: [ "mongod", "--port", "37018", "--bind_ip_all", "--replSet", "rs0" ] mongo3: container_name: mongo3 image: mongo:4.0.4 expose: - 37019 ports: - "37019:37019" restart: always entrypoint: [ "mongod", "--port", "37019", "--bind_ip_all", "--replSet", "rs0" ]
// file :replicaSet.js rsconf = { _id: "rs0", members: [ {_id: 0, host: "mongo1:37017"}, {_id: 1, host: "mongo2:37018"}, {_id: 2, host: "mongo3:37019"} ] } rs.initiate(rsconf); rs.conf();
做了這些修改,我們就可以正常訪問(wèn)mongo服務(wù)了:
mongo mongodb://mongo1:37017,mongo2:37018,mongo3:37019/admin?replicaSet=rs0啟動(dòng)服務(wù)
首先,我們看看鏡像能不能順利編譯過(guò)去:
docker-compose -f docker-compose.yml build
其次,我們啟動(dòng)容器服務(wù):
docker-compose -f docker-compose.yml up
最后,關(guān)閉容器服務(wù)。這個(gè)命令相當(dāng)于依次執(zhí)行docker container stop、docker-compose down,很方便。
docker-compose -f docker-compose.yml down總結(jié)
執(zhí)行上一篇的測(cè)試用例,然后中途關(guān)閉一個(gè)節(jié)點(diǎn),來(lái)查看執(zhí)行效果。
啟動(dòng)容器:
docker-compose -f docker-compose.yml down
查看容器的運(yùn)行情況:
docker ps
關(guān)閉其中一個(gè)容器:
docker container stop
服務(wù)短暫的輸出.no reachable servers錯(cuò)誤信息后,由恢復(fù)正常了!
備注看到這里的人,必須關(guān)注公眾號(hào)了
文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請(qǐng)注明本文地址:http://specialneedsforspecialkids.com/yun/27842.html
摘要:所以在掃描次后,率先到達(dá)狀態(tài),那么此刻將停止掃描,進(jìn)入到算分的階段。除了這條引發(fā)故障的之外,其他的字段命中索引數(shù)量都非常小,有的甚至只有一條。那這里很明顯在中只去根據(jù)中執(zhí)行計(jì)劃的相關(guān)索引來(lái)進(jìn)行判斷是不合理的。 前段時(shí)間筆者遇到一個(gè)MongoBD Plan Cache的bug,于是深究了下MongoDB優(yōu)化器相關(guān)源碼。在這里分享給大家,一方面讓大家知道MongoDB優(yōu)化器工作原理,一方面...
摘要:負(fù)責(zé)讀取和記錄當(dāng)前代碼的位置,并把讀取到的代碼交給處理,其意義在于,當(dāng)傳遞給的代碼需要進(jìn)行判讀猜測(cè)時(shí),能夠記錄當(dāng)前讀取的位置,并在接下來(lái)的操作匯總回滾到之前的讀取位置,也能在發(fā)生語(yǔ)法錯(cuò)誤時(shí),準(zhǔn)確指出錯(cuò)誤發(fā)生在代碼段的第幾行第幾個(gè)字符。 上一篇(《如何編寫(xiě)簡(jiǎn)單的parser(基礎(chǔ)篇)》)中介紹了編寫(xiě)一個(gè)parser所需具備的基礎(chǔ)知識(shí),接下來(lái),我們要?jiǎng)邮謱?shí)踐一個(gè)簡(jiǎn)單的parser,既然是簡(jiǎn)...
摘要:為此我首先需要?jiǎng)?chuàng)建一個(gè)針對(duì)的配置文件。的作用是指定基準(zhǔn)鏡像。該以后面指定的鏡像為基礎(chǔ),在其上進(jìn)行定制。存在一個(gè)特殊的鏡像,名為。它是一個(gè)虛擬的概念,表示一個(gè)空白的鏡像。直接使用會(huì)讓鏡像體積更加小巧。 什么是dockerfile?簡(jiǎn)單的說(shuō)就是一個(gè)文本格式的腳本文件,其內(nèi)包含了一條條的指令(Instruction),每一條指令負(fù)責(zé)描述鏡像的當(dāng)前層(Layer)如何構(gòu)建。 下面通過(guò)一個(gè)具體的...
摘要:本文將介紹如何在中使用。如果你是一名的初學(xué)者,那么你入門(mén)的第一件事就是安裝,但是安裝又不是一件簡(jiǎn)單的事情,還需要自己配置一些服務(wù)。這時(shí)候,就能幫上大忙,它能夠讓你不需要本地安裝就能使用。下面讓我們來(lái)看看這是怎么實(shí)現(xiàn)的。 ??本文將介紹如何在docker中使用MongoDB。??如果你是一名MongoDB的初學(xué)者,那么你入門(mén)MongoDB的第一件事就是安裝MongoDB,但是安裝Mong...
閱讀 1659·2021-11-23 10:07
閱讀 2652·2019-08-30 11:10
閱讀 2834·2019-08-29 17:08
閱讀 1778·2019-08-29 15:42
閱讀 3163·2019-08-29 12:57
閱讀 2396·2019-08-28 18:06
閱讀 3544·2019-08-27 10:56
閱讀 382·2019-08-26 11:33