溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊(cè)×
其他方式登錄
點(diǎn)擊 登錄注冊(cè) 即表示同意《億速云用戶服務(wù)條款》

【技術(shù)解析】如何用Docker實(shí)現(xiàn)SequoiaDB集群的快速部署

發(fā)布時(shí)間:2020-06-30 17:19:02 來(lái)源:網(wǎng)絡(luò) 閱讀:257 作者:OliverFinn 欄目:數(shù)據(jù)庫(kù)
  1. 背景
    以Docker和Rocket為代表的容器技術(shù)現(xiàn)在正變得越來(lái)越流行,它改變著公司和用戶創(chuàng)建、發(fā)布、運(yùn)行分布式應(yīng)用的方式,在未來(lái)5年將給云計(jì)算行業(yè)帶來(lái)它應(yīng)有的價(jià)值。它的誘人之處在于:
    1)資源獨(dú)立、隔離
    資源隔離是云計(jì)算平臺(tái)的最基本需求。Docker通過Linux namespace, cgroup限制了硬件資源與軟件運(yùn)行環(huán)境,與宿主機(jī)上的其他應(yīng)用實(shí)現(xiàn)了隔離,做到了互不影響。不同應(yīng)用或服務(wù)以“集裝箱”(container)為單位裝“船”或卸“船”,“集裝箱船”(運(yùn)行container的宿主機(jī)或集群 )上,數(shù)千數(shù)萬(wàn)個(gè)“集裝箱”排列整齊,不同公司、不同種類的“貨物”(運(yùn)行應(yīng)用所需的程序、組件、運(yùn)行環(huán)境、依賴)保持獨(dú)立。
    2)環(huán)境的一致性
    開發(fā)工程師完成應(yīng)用開發(fā)后build一個(gè)docker image,基于這個(gè)image創(chuàng)建的container像是一個(gè)集裝箱,里面打包了各種“散件貨物”(運(yùn)行應(yīng)用所需的程序、組件、運(yùn)行環(huán)境、依賴)。無(wú)論這個(gè)集裝箱在哪里:開發(fā)環(huán)境、測(cè)試環(huán)境、生產(chǎn)環(huán)境,都可以確保集裝箱里面的“貨物”種類與個(gè)數(shù)完全相同,軟件包不會(huì)在測(cè)試環(huán)境缺失,環(huán)境變量不會(huì)在生產(chǎn)環(huán)境忘記配置,開發(fā)環(huán)境與生產(chǎn)環(huán)境不會(huì)因?yàn)榘惭b了不同版本的依賴導(dǎo)致應(yīng)用運(yùn)行異常。這樣的一致性得益于“發(fā)貨”(build docker image)時(shí)已經(jīng)密封到“集裝箱”中,而每一個(gè)環(huán)節(jié)都是在運(yùn)輸這個(gè)完整的、不需要拆分合并的“集裝箱”。
    3)輕量化
    相比傳統(tǒng)的虛擬化技術(shù)(VM),使用docker在cpu, memory, disk IO, network IO上的性能損耗都有同樣水平甚至更優(yōu)的表現(xiàn)。Container的快速創(chuàng)建、啟動(dòng)、銷毀受到很多贊譽(yù)。
    4)Build Once, Run Everywhere
    這個(gè)特性著實(shí)吸引了很多人,“貨物”(應(yīng)用)在“汽車”、“火車”、“輪船”(私有云、公有云等服務(wù))之間遷移交換時(shí),只需要遷移符合標(biāo)準(zhǔn)規(guī)格和裝卸方式的“集裝箱”(docker container),削減了耗時(shí)費(fèi)力的人工“裝卸”(上線、下線應(yīng)用),帶來(lái)的是巨大的時(shí)間人力成本節(jié)約。這使未來(lái)僅有少數(shù)幾個(gè)運(yùn)維人員運(yùn)維超大規(guī)模裝載線上應(yīng)用的容器集群成為可能,如同60年代后少數(shù)幾個(gè)機(jī)器操作員即可在幾小時(shí)內(nèi)連裝帶卸完一艘萬(wàn)級(jí)集裝箱船。
    容器技術(shù)現(xiàn)在也被廣泛應(yīng)用于數(shù)據(jù)庫(kù)領(lǐng)域。它的“Build Once, Run Everywhere”的特性大大減少了花在安裝配置數(shù)據(jù)庫(kù)環(huán)境上的時(shí)間,因?yàn)榧词箤?duì)于從事數(shù)據(jù)庫(kù)多年的DBA而言,安裝配置數(shù)據(jù)庫(kù)環(huán)境依舊是一項(xiàng)看似簡(jiǎn)單但卻經(jīng)常不順利的工作。當(dāng)然,容器技術(shù)的其他優(yōu)勢(shì)也被很好的應(yīng)用在數(shù)據(jù)庫(kù)的使用中。
    SequoiaDB作為一款優(yōu)秀的國(guó)產(chǎn)分布式NewSQL數(shù)據(jù)庫(kù),已經(jīng)得到了越來(lái)越多用戶的認(rèn)可。本文以Docker為例,著重介紹如何用Dockerfile快速構(gòu)建SequoiaDB鏡像,以及如何利用容器快速搭建和啟動(dòng)SequoiaDB集群供應(yīng)用系統(tǒng)使用。

  2. 構(gòu)建SequoiaDB鏡像
    如何安裝docker以及配置鏡像倉(cāng)庫(kù)不是本文的重點(diǎn),網(wǎng)上有很多相關(guān)的技術(shù)文章。需要指出的是本文采用阿里云鏡像倉(cāng)庫(kù),因?yàn)閷㈢R像上傳到Docker官方倉(cāng)庫(kù)的速度實(shí)在不敢恭維。如何注冊(cè)和使用阿里云鏡像倉(cāng)庫(kù),可以參考文章(http://www.jb51.net/article/123101.htm)。

STEP 1:創(chuàng)建Dockerfile,內(nèi)容如下,只需要幾行簡(jiǎn)單的指令即可

*# Sequoiadb DOCKERFILES PROJECT
--------------------------
This is the Dockerfile for Sequoiadb 2.8.4

REQUIRED FILES TO BUILD THIS IMAGE
----------------------------------
(1) sequoiadb-2.8.4-linuxx8664-enterprise-installer.run
(2) installSDB.sh

HOW TO BUILD THIS IMAGE
-----------------------
Put all downloaded files in the same directory as this Dockerfile
Run: 
$ sudo docker build -t sequoiadb:2.8.4 . 

Pull base image
FROM ubuntu

Environment variables required for this build
ENV INSTALLBINFILE="sequoiadb-2.8.4-linuxx8664-enterprise-installer.run" \
INSTALLSDBSCRIPT="installSDB.sh" \
INSTALLDIR="/opt/sequoiadb"

Copy binaries
ADD $INSTALLBINFILE $INSTALLSDBSCRIPT $INSTALLDIR/

Install SDB software binaries
RUN chmod 755 $INSTALLDIR/$INSTALLSDBSCRIPT \
&& $INSTALLDIR/$INSTALLSDBSCRIPT \
&& rm $INSTALLDIR/$INSTALLSDBSCRIPT**

其中installSDB.sh腳本內(nèi)容如下:

chmod 755 $INSTALL_DIR/$INSTALL_BIN_FILE
$INSTALL_DIR/$INSTALL_BIN_FILE --mode unattended 
rm $INSTALL_DIR/$INSTALL_BIN_FILE
echo 'service sdbcm start' >> /root/.bashrc

需要注意的是本例采用Sequoiadb企業(yè)版2.8.4,您也可以從巨杉官網(wǎng)下載社區(qū)版(選擇tar包,下載然后解壓),替換本例中的介質(zhì)名稱。
巨杉官網(wǎng)下載地址:http://download.sequoiadb.com/cn/

STEP 2:創(chuàng)建鏡像
root用戶執(zhí)行:
docker build -t sequoiadb:2.8.4 .
如果是普通用戶,需要使用sudo:
sudo docker build -t sequoiadb:2.8.4 .

STEP3:登陸阿里云鏡像倉(cāng)庫(kù)
docker login --username=xxx registry.cn-hangzhou.aliyuncs.com
其中xxx為您在阿里云注冊(cè)的賬號(hào)。

STEP4:查看本地sequoiadb鏡像id
docker images

STEP5:標(biāo)記本地鏡像,將其歸入阿里云倉(cāng)庫(kù)
docker tag 04dc528f2a6f registry.cn-hangzhou.aliyuncs.com/508mars/sequoiadb:latest
其中04dc528f2a6f是筆者本地sequoiadb鏡像id,新的標(biāo)記格式有一定要求,registry.cn-hangzhou.aliyuncs.com為阿里云倉(cāng)庫(kù)地址,508mars是筆者在阿里云的用戶名,sequoiadb是鏡像名,latest是tag。

STEP6:提交sequoiadb鏡像到鏡像庫(kù)
docker push registry.cn-hangzhou.aliyuncs.com/508mars/sequoiadb:latest

  1. 利用容器啟動(dòng)SequoiaDB集群
    Docker的網(wǎng)絡(luò)默認(rèn)采用bridge模式,采用bridge模式的容器有如下特點(diǎn):
    1)同一宿主機(jī)的容器之間可以互相ping通
    2)不同宿主機(jī)的容器之間互相ping不同
    但是SequoiaDB集群要求所有節(jié)點(diǎn)之間是可以互通的,所以如果運(yùn)行SequoiaDB的容器跑在不同宿主機(jī)上,docker的默認(rèn)網(wǎng)絡(luò)模式顯然不合適。有很多種方法可以解決不同宿主機(jī)容器之間的連通性問題,本文只介紹weave虛擬網(wǎng)絡(luò)這個(gè)解決方案,因?yàn)閣eave同時(shí)提供了一個(gè)DNS server的功能,有了該功能,在利用容器部署SequoiaDB集群時(shí)不再需要修改各個(gè)容器內(nèi)部的/etc/hosts,大大簡(jiǎn)化了自動(dòng)化部署的步驟。

STEP1:安裝weave網(wǎng)絡(luò)

curl -s -L git.io/weave -o /usr/local/bin/weave
chmod a+x /usr/local/bin/weave

需要在所有宿主機(jī)安裝,筆者采用了三臺(tái)虛擬機(jī)作為宿主機(jī):sdb1, sdb2和sdb3。

STEP2:?jiǎn)?dòng)weave網(wǎng)絡(luò)
weave launch
第一次啟動(dòng)時(shí)會(huì)下載weave鏡像。

STEP3:從阿里云倉(cāng)庫(kù)下載sequoiadb鏡像
docker pull registry.cn-hangzhou.aliyuncs.com/508mars/sequoiadb

STEP4:在所有宿主機(jī)創(chuàng)建docker的掛載卷

cd /home/sdbadmin
mkdir -p data/disk1 data/disk2 data/disk3
mkdir -p conf/local
chmod -R 777 data
chmod -R 777 conf

掛載卷的位置可以自定義,但總的來(lái)說需要?jiǎng)?chuàng)建兩大類掛載卷,一類用來(lái)存放集合數(shù)據(jù),如本例中的data/disk1, data/disk2, data/disk3,一類用來(lái)存放節(jié)點(diǎn)配置信息,如本例中的conf/local。這樣即使容器被誤刪了,依舊可以啟動(dòng)一個(gè)新容器來(lái)扮演被誤刪的容器的角色。

STEP5:?jiǎn)?dòng)容器
sdb1:

weave stop
weave launch
eval $(weave env)
docker run -dit --name sdbserver1 -p 11810:11810 -v /home/sdbadmin/data:/data -v /home/sdbadmin/conf/local:/opt/sequoiadb/conf/local registry.cn-hangzhou.aliyuncs.com/508mars/sequoiadb

sdb2:

weave stop
weave launch 192.168.17.132
eval $(weave env)
docker run -dit --name sdbserver2 -p 11810:11810 -v /home/sdbadmin/data:/data -v /home/sdbadmin/conf/local:/opt/sequoiadb/conf/local registry.cn-hangzhou.aliyuncs.com/508mars/sequoiadb

sdb3:

weave stop
weave launch 192.168.17.132
eval $(weave env)
docker run -dit --name sdbserver3 -p 11810:11810 -v /home/sdbadmin/data:/data -v /home/sdbadmin/conf/local:/opt/sequoiadb/conf/local registry.cn-hangzhou.aliyuncs.com/508mars/sequoiadb

其中192.168.17.132是sdb1的IP地址,11810是對(duì)外暴露的集群訪問端口。宿主機(jī)存放節(jié)點(diǎn)配置信息的卷必須掛到容器的/opt/sequoiadb/conf/local目錄,存放表數(shù)據(jù)的卷可以掛載到用戶自定義的目錄,但是集群一旦創(chuàng)建后,不可更改。啟動(dòng)容器的時(shí)候必須指定機(jī)器名,因?yàn)樵跇?gòu)建完集群后,機(jī)器名會(huì)被保存在SequoiaDB的系統(tǒng)表中,節(jié)點(diǎn)的機(jī)器名與系統(tǒng)表中不一致會(huì)導(dǎo)致無(wú)法加入到集群。在使用weave的場(chǎng)景下,建議使用--name選項(xiàng),不要使用--hostname設(shè)置機(jī)器名。后者會(huì)阻止weave將機(jī)器名添加到DNS服務(wù)器,weave會(huì)自動(dòng)根據(jù)--name的值來(lái)設(shè)置機(jī)器名,同時(shí)在機(jī)器名后增加weave.local域名,并添加到的DNS服務(wù)器。

STEP6:將創(chuàng)建SequoiaDB集群的腳本拷貝到容器中
docker cp create_cluster.js sdbserver1:/data

create_cluster.js內(nèi)容如下:

var array_hosts = ["sdbserver1.weave.local", "sdbserver2.weave.local", "sdbserver3.weave.local"];
var array_dbroot = ["/data/disk1/sequoiadb/database","/data/disk2/sequoiadb/database","/data/disk3/sequoiadb/database"];
var port_sdbcm = "11790";
var port_temp_coord = "18888";
var cataloggroup = {gname:"SYSCatalogGroup", gport:"11820", ghosts:["sdbserver1.weave.local", "sdbserver2.weave.local", "sdbserver3.weave.local"]};
var array_coordgroups = [
        {gname:"SYSCoord", gport:"11810", ghosts:["sdbserver1.weave.local", "sdbserver2.weave.local", "sdbserver3.weave.local"]}
];
var array_datagroups = [
        {gname:"dg1", gport:"11830", ghosts:["sdbserver1.weave.local", "sdbserver2.weave.local", "sdbserver3.weave.local"], goptions:{transactionon:true}}
       ,{gname:"dg2", gport:"11840", ghosts:["sdbserver1.weave.local", "sdbserver2.weave.local", "sdbserver3.weave.local"], goptions:{transactionon:true}}
       ,{gname:"dg3", gport:"11850", ghosts:["sdbserver1.weave.local", "sdbserver2.weave.local", "sdbserver3.weave.local"], goptions:{transactionon:true}}
];
var array_domains = [
        {dname:"allgroups", dgroups:["dg1", "dg2", "dg3"], doptions:{AutoSplit:true}}
];

println("啟動(dòng)臨時(shí)協(xié)調(diào)節(jié)點(diǎn)");
var oma = new Oma(array_coordgroups[0].ghosts[0], port_sdbcm);
oma.createCoord(port_temp_coord, array_dbroot[0]+"/coord/"+port_temp_coord);
oma.startNode(port_temp_coord);

println("創(chuàng)建編目節(jié)點(diǎn)組:"+cataloggroup.ghosts[0]+"   "+cataloggroup.gport+"    "+array_dbroot[0]+"/cata/"+cataloggroup.gport);
var db = new Sdb(array_coordgroups[0].ghosts[0], port_temp_coord);
db.createCataRG(cataloggroup.ghosts[0], cataloggroup.gport, array_dbroot[0]+"/cata/"+cataloggroup.gport);
var cataRG = db.getRG("SYSCatalogGroup");
for (var i in cataloggroup.ghosts) {
        if (i==0) {continue;}
    println("創(chuàng)建編目節(jié)點(diǎn): "+cataloggroup.ghosts[i]+"  "+cataloggroup.gport+"    "+array_dbroot[0]+"/cata/"+cataloggroup.gport);
        var catanode = cataRG.createNode(cataloggroup.ghosts[i], cataloggroup.gport, array_dbroot[0]+"/cata/"+cataloggroup.gport);
        catanode.start();
}

println("創(chuàng)建協(xié)調(diào)節(jié)點(diǎn)組");
var db = new Sdb(array_coordgroups[0].ghosts[0], port_temp_coord);
var coordRG = db.createCoordRG();
for (var i in array_coordgroups) {
        for (var j in array_coordgroups[i].ghosts) {
                println("創(chuàng)建協(xié)調(diào)節(jié)點(diǎn)組:"+array_coordgroups[i].ghosts[j]+"    "+array_coordgroups[i].gport+"    "+array_dbroot[0]+"/coord/"+array_coordgroups[i].gport);
                coordRG.createNode(array_coordgroups[i].ghosts[j], array_coordgroups[i].gport, array_dbroot[0]+"/coord/"+array_coordgroups[i].gport);
        }
}
coordRG.start();

println("刪除臨時(shí)協(xié)調(diào)節(jié)點(diǎn)")
var oma = new Oma(array_coordgroups[0].ghosts[0], port_sdbcm);
oma.removeCoord(port_temp_coord);

println("創(chuàng)建數(shù)據(jù)節(jié)點(diǎn)組")
var db = new Sdb(array_coordgroups[0].ghosts[0], array_coordgroups[0].gport);
var k=0;
for (var i in array_datagroups) {
        var dataRG = db.createRG(array_datagroups[i].gname);
        for (var j in array_datagroups[i].ghosts) {
                println("創(chuàng)建數(shù)據(jù)節(jié)點(diǎn):"+array_datagroups[i].gname+"    "+array_datagroups[i].ghosts[j]+"   "+array_datagroups[i].gport+"    "+array_dbroot[k]+"/data/"+array_datagroups[i].gport+"    "+array_datagroups[i].goptions)
                dataRG.createNode(array_datagroups[i].ghosts[j], array_datagroups[i].gport, array_dbroot[k]+"/data/"+array_datagroups[i].gport, array_datagroups[i].goptions);
        }
        dataRG.start();
        k++;
}

println("創(chuàng)建域");
var db = new Sdb(array_coordgroups[0].ghosts[0], array_coordgroups[0].gport);
for (var i in array_domains) {
        println("創(chuàng)建域:"+array_domains[i].dname+"   "+array_domains[i].dgroups+"    "+array_domains[i].doptions)
        db.createDomain(array_domains[i].dname, array_domains[i].dgroups, array_domains[i].doptions );
}

STEP7:創(chuàng)建SequoiaDB集群
docker exec sdbserver1 su - sdbadmin -c "sdb -f /data/create_cluster.js"

至此SequoiaDB集群創(chuàng)建并啟動(dòng)完成,后面再啟動(dòng)容器的時(shí)候集群會(huì)自動(dòng)啟動(dòng)。

  1. 結(jié)論
    SequoiaDB利用容器技術(shù)很好的實(shí)現(xiàn)了集群快速部署,大大簡(jiǎn)化了初學(xué)者安裝部署的難度。后期筆者還會(huì)在SequoiaDB鏡像制作上做一些優(yōu)化,因?yàn)槟壳白龀鰜?lái)的鏡像有點(diǎn)大,主要根源是采用ADD或COPY命令將安裝介質(zhì)拷貝到Docker容器中會(huì)生成一個(gè)新的鏡像image1,最終生成的鏡像image2中雖然刪除了安裝介質(zhì),但是它在image1之上,所以image2的大小依舊包含安裝介質(zhì)。最好采用ADD拷貝tar包(ADD會(huì)自動(dòng)解壓)或者采用類似如下的方式:
    RUN mkdir -p /usr/src/things \
    && curl -SL http://example.com/big.tar.xz \
    | tar -xJC /usr/src/things \
    && make -C /usr/src/things all

<END>

向AI問一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI