1. 程式人生 > >分布式進階 十二 Docker固定Container IP

分布式進階 十二 Docker固定Container IP

targe 完成 xxx eth0 times 實現 trac 私有 智能

使用pipework工具。

前提:每個Container所做的工作現在還很少,可以不用savecommit

為了便於通信,自定義一個網橋(192.168.1.180/24),使之IP與宿主主機IP在同一網段內。

bridge模式

bridge模式是Docker默認的網絡設置,此模式會為每一個容器分配Network Namespace、設置IP等,並將一個主機上的Docker容器連接到一個虛擬網橋上。下面著重介紹一下此模式。

bridge模式的拓撲

Docker server啟動時,會在主機上創建一個名為docker0的虛擬網橋,此主機上啟動的Docker容器會連接到這個虛擬網橋上。虛擬網橋的工作方式和物理交換機類似,這樣主機上的所有容器就通過交換機連在了一個二層網絡中。

接下來就要為容器分配IP了,Docker會從RFC1918所定義的私有IP網段中,選擇一個和宿主機不同的IP地址和子網分配給docker0,連接到docker0的容器就從這個子網中選擇一個未占用的IP使用。

如一般Docker會使用172.17.0.0/16這個網段,並將172.17.42.1/16分配給docker0網橋(在主機上使用ifconfig命令是可以看到docker0的,可以認為它是網橋的管理接口,在宿主機上作為一塊虛擬網卡使用)。

單機環境下的網絡拓撲如下,主機地址為10.10.101.105/24

技術分享圖片

為了使本地網絡中的機器和Docker容器更方便的通信,我們經常會有將Docker容器配置到和主機同一網段的需求。這個需求其實很容易實現,我們只要將

Docker容器和主機的網卡橋接起來,再給Docker容器配上IP就可以了。

#安裝pipework

wget https://github.com/jpetazzo/pipework/archive/master.zip #下載 pipework

unzip master.zip #解壓

cp pipework-master/pipework /usr/bin/ #拷貝pipework/usr/bin/

chmod +x /usr/bin/pipework #賦予該命令執行權限

自定義一個網橋:

brctl addbr br0

ifconfig br0 192.168.1.188 netmask 255.255.255.0

編輯/etc/defautl/docker.io文件,追加以下內容,指定使用的網橋:

DOCKER_OPTS="-b=br0"

再次啟動docker

service docker.io start

Contianer未綁定IP之前,其IP地址果然會改變。

註:veth設備是成雙成對出現的,一端是容器內部命名eth0,一端是加入到網橋並命名的veth17f560a(通常命名為veth*),他們組成了一個數據傳輸通道,一端進一端出,veth設備連接了兩個網絡設備並實現了數據通信。

Pipework有個缺點就是給容器指定完固定IP,如果容器重啟,那麽固定IP會消失,還需要重新指定,容器量大時可寫個腳本來完成。

思路:利用jsvc創建服務,在linux啟動時自動創建指定IP的網橋br0,然後利用pipework工具為容器c1-c4添加新的網卡(前提:容器c1-c4均已處以啟動態),將其連接到新創建的br0網橋上,以此創建指定IP的容器。

Jsvc方式見博客“分布式進階(五)之JSVC配置

其中的一個問題是:如何在Ubuntujava代碼中調用shell腳本。

/**

* 運行shell腳本

* @param shell 需要運行的shell腳本

*/

public static void execShell(String shell){

try {

Runtime rt = Runtime.getRuntime();

rt.exec(shell);

} catch (Exception e) {

e.printStackTrace();

}

}

還有一個方法就是在linux啟動時直接運行shell腳本:

只需編輯/etc/init.d/rc.local文件,在最後加上你的腳本即可。

比如:我已經編寫了一個腳本shell.sh,存放在/home/mars704/Desktop/ 下面

在終端輸入 gedit /etc/init.d/rc.local編輯文件,在結尾出加入:

/home/mars704/Desktop/sh.sh 即可開機自動加載腳本

原理:

首先,linux隨機啟動的服務程序都在/etc/init.d這個文件夾裏,裏面的文件全部都是腳本文件(腳本程序簡單的說就是把要運行的程序寫到一個文件裏讓系統能夠按順序執行,類似windows下的autorun.dat文件),

另外在/etc這個文件夾裏還有諸如名為rc1.d, rc2.d一直到rc6.d的文件夾,這些都是linux不同的runlevel,我們一般進入的X windows多用戶的運行級別是第5級,也就是rc5.d

在這個文件夾下的腳本文件就是運行第5級時要隨機啟動的服務程序。需要註意的是,在每個rc (1-6).d文件夾下的文件其實都是/etc/init.d文件夾下的文件的一個軟連接(類似windows中的快捷方式)

,也就是說,在 /etc/init.d文件夾下是全部的服務程序,而每個rc(1-6).d只鏈接它自己啟動需要的相應的服務程序!

要啟動scim(某一程序),我們首先要知道scim程序在哪裏,用locate命令可以找到,scim/usr/bin/scim這裏,其中usr表示是屬於用戶的,binlinux裏表示可以執行的程序。

這樣,我就可以編寫一個腳本程序,把它放到/etc/init.d裏,然後在rc5.d裏做一個相應的軟鏈接就可以了。

ln -s a b 中的 a 就是源文件,b是鏈接文件名,其作用是當進入b目錄,實際上是鏈接進入了a目錄

這個腳本其實很簡單,就兩行:

#!/bin/bash

/usr/bin/scim

第一行是聲明用什麽終端運行這個腳本,第二行就是要運行的命令。

還需要註意的一點是,在rc5.d裏,每個鏈接的名字都是以S或者K開頭的,S開頭的表示是系統啟動是要隨機啟動的,K開頭的是不隨機啟動的。這樣,你就可以知道,如果我要哪個服務隨機啟動,

就把它名字第一個字母K改成S就可以了,當然,把S改成K後,這個服務就不能隨機啟動了。因此,我這個鏈接 還要起名為SXXX,這樣系統才能讓它隨機啟動。

RH下,rc.local是默認啟動的最後一個腳本文件,所以,

如果你想要隨機啟動,還有一種方法就是在rc.local的尾部加入/usr/bin/scim,這樣就可以了。

四個節點配置好了固定IP,節點間的架構圖如下:

技術分享圖片

技術分享圖片

圖一

註:Docker啟動時會在主機上自動創建一個docker0虛擬網橋,實際上是一個linux網橋,可以理解為一個軟件交換機。它會在掛在其上的接口之間進行轉發。

同時,Docker會隨機分配一個本地未占用的私有網段(在RFC1918中定義)中的一個地址給docker0接口。此後啟動的容器內的網口也會自動分配一個同一網段的地址。

技術分享圖片

圖二

註:圖二是自己所寫有關配置自定義網橋,給container添加固定IPshell腳本

技術分享圖片

圖三

註:圖三是Linux重啟後所起到的效果。

疑惑:配置腳本中明明定制了四個啟動容器,結果卻只啟動了三個。經檢查,啟動的三個容器其IP地址均已固定。

技術分享圖片

圖四

註:在Ubuntu命令行輸入以上命令時提示如上信息。錯誤原因及解決措施見博客"分布式進階(十一) 常見錯誤匯總"

技術分享圖片

圖五

註:抱著試試看的心態,自己又運行了一個容器,結果奇跡了,前面的915容器啟動了,而新啟動的容器aef卻沒能啟動,難道啟動的容器總會比自己定義所啟動的容器少一個,這個問題有待於進一步解決。

再分享一下我老師大神的人工智能教程吧。零基礎!通俗易懂!風趣幽默!希望你也加入到我們人工智能的隊伍中來!http://www.captainbed.net

分布式進階 十二 Docker固定Container IP