1、關於MogileFShtml
2、常見分佈式文件系統前端
3、MogileFS基本原理node
4、MogileFS的實現mysql
1、關於MogileFSlinux
當下咱們處在一個互聯網飛速發展的信息社會,在海量併發鏈接的驅動下天天所產生的數據量必然以幾何方式增加,隨着信息鏈接方式日益多樣化,數據存儲的結構也隨着發生了變化。在這樣的壓力下使得人們不得不從新審視大量數據的存儲所帶來的挑戰,例如:數據採集、數據存儲、數據搜索、數據共享、數據傳輸、數據分析、數據可視化等一系列問題。根據定理,分佈式系統只能知足三項中的兩項而不可能知足所有三項。nginx
對於大型站點,可用性(Availability)與分隔容錯性(Partition Tolerance)的優先級會高於一致性(Consistency),這裏並非指徹底捨棄一致性,而是經過其餘手段實現數據的弱一致性,例如:用戶微博的瀏覽數和評論能夠容忍相對長時間的不一致,幾乎不會影響用戶體驗,而股票價格的數據則異常敏感,即使是10秒鐘的數據不一致也沒法容忍下面列出了"各類一致性".強一致性git
ACID程序員
在單機環境中,強一致性能夠由數據庫的事務來保證github
在多級環境中,強一致性很難作到web
分佈式事務:性能太差,在化聯網的應用中不適合
弱一致性(包括最終一致性)
經過提交處理的半同步、半異步或全異步,取得最終一致性效果
最終一致性使得數據的提交具備延時性,而在必定範圍時的延時性範圍內(好比一秒),應用的可用性時正常的
集羣內一致性算法實施過程案例
基於合法票數(Quorum)和向量時鐘(Vector Clock)
Quorum算法:
N :數據複製的節點量
R :成功讀取所依賴的最少節點數
W :成功寫操做所依賴的最少節點數
W+R>N 表示強一致性 ;W+R<=N 屬於弱一致性(保證最終一致性)
2、常見分佈式存儲文件系統
Google Filesystem | GFS+MapReduce擅長處理單個大文件 |
Hadoop Distributed Filesystem | GFS的山寨版+MapReduce,擅長處理單個大文件 |
ClusterFS | 擅長處理單個大文件 |
Taobao Filesystem | 擅長處理海量小文件 |
MogileFS | 擅長處理海量小文件 |
Ceph | PB級別的分佈式文件系統 |
MooseFS | 通用簡便,適用於研發能力不強的公司 |
Lustre | 一種平行分佈式文件系統 |
▲MogileFS管理的幾個概念:
一、Domain:一個MogileFS能夠有多個Domain,用來存放不一樣文件(大小,類型),同一個Domain內key必須爲一,不一樣Domain內,key能夠相同;
二、每個存儲節點稱爲一個主機,一個主機上能夠有多個存儲設備(單獨的硬盤),每一個設備都有ID號,Domain+Fid用來定位文件。
三、Class:文件屬性管理,定位文件存儲在不一樣設備上的份數;
Client libray、tracker、Database、mogstore的關係圖 |
![]() |
MofileFS工做流程圖 |
![]() |
4、MogileFS的實現
2)Nginx根據反向代理+負載均衡機制隨機代理到後端Tracker(node1)(任意一臺)。
3)Tracker(node1)向mysql服務器發起查詢請求。
4)mysql服務器返回查詢結果給Tracker(node1)。
5)Tracker(node1)將查詢結果返回給Nginx。
6)Nginx將查詢結果根據模塊轉換爲合理的url發送給後端的Storage存儲服務器(node3)。
7)Storage存儲服務器(node3)將文件內容經過http協議返回給Nginx。
8)Nginx將結果返回給應用層的請求。
說明:你們一眼就能夠看出來這個拓撲規劃的缺陷,首先是前端nginx代理服務器單點故障所在處、若是高併發的狀況下一臺根本就支撐不了,此時前端能夠考慮Nginx+keepalived或者是Haproxy+keepalived,其次是後端的mysql,就算前端一臺nginx支撐得了,可是讀寫操做都壓在了一臺mysql上面,很明顯mysql就須要擴展了,構建主從的架構適宜,最後的Tracker和Storage徹底能夠在一臺主機上運行,他們之間沒有任何影響;可是本文的重點在於如何去部署一個MogileFS的應用場景,其餘並未考慮,請各位朋友不要誤解!
2.實驗步驟:
MariaDB [(none)]> use mysql #刪除有安全隱患的帳戶 MariaDB [mysql]> DELETE FROM user WHERE host = '::1'; MariaDB [mysql]> DELETE FROM user WHERE user = ''; #受權root用戶能遠程登陸 MariaDB [mysql]> GRANT ALL ON *.* TO 'root'@'172.16.%.%' IDENTIFIED BY '123.com' #受權moguser用戶 MariaDB [mysql]> GRANT ALL ON mogdb.* TO 'moguser'@'172.16.%.%' IDENTIFIED BY '123.com'; #刷新受權表 MariaDB [mysql]> FLUSH PRIVILEGES;
#→下面三個是Tracker和Storage端必裝的程序包. MogileFS-Server-2.46-2.el6.noarch.rpm MogileFS-Server-mogilefsd-2.46-2.el6.noarch.rpm MogileFS-Server-mogstored-2.46-2.el6.noarch.rpm #→這是在維護MogileFS時使用的工具包 MogileFS-Utils-2.19-1.el6.noarch.rpm #→MogileFS客戶端程序 perl-MogileFS-Client-1.14-1.el6.noarch.rpm #→這個軟件包是在跨網絡或者跨機房是所使用的包 perl-Net-Netmask-1.9015-8.el6.noarch.rpm #→這是用perl所編寫的web程序,它是在mostored上提供webDAV的方式接受客戶web服務請求的. perl-Perlbal-1.78-1.el6.noarch.rpm #這是perl程序所依賴的包 perl-IO-AIO.x86_64 #→說明若是在配置安裝過程中遇依賴關係時,解決就好了. #→而後將幾個軟件包都拷貝至其它兩個節點上. [root@node1 ~]# scp *.rpm 172.16.41.2:/root/ [root@node1 ~]# scp *.rpm 172.16.41.3:/root/
[root@node1 ~]# yum install *.rpm perl-IO-AIO #→其餘兩個節點的安裝過程在node1上面的同樣.
(3)配置node1.example.com
#→安裝好tracker後會在/var/run/下面生成該目錄,改變目錄屬主.屬組 [root@node1 ~]# chown -R mogilefs.mogilefs /var/run/mogilefsd
[root@node1 ~]# mogdbsetup --dbrootuser=root --dbname=mogdb --dbhost=172.16.41.5 --dbport=3306 --dbrootpass=123.com --dbuser=moguser --dbpass=123.com --yes
<3>驗證初始化數據庫結果:
<4>修改tracker配置文件,以下內容:
[root@node1 ~]# vim /etc/mogilefs/mogilefsd.conf #→修改下面4項便可其它參數根據工做環境自定 db_dsn = DBI:mysql:mogdb:host=172.16.41.5 db_user = moguser db_pass = 123.com listen = 172.16.41.1:7001
<5>修改storage配置文件,以下內容:
[root@node1 ~]# vim /etc/mogilefs/mogstored.conf maxconns = 10000 #→存儲系統的最大鏈接數. httplisten = 0.0.0.0:7500 #→這個就是webDAV服務使用的端口,可是這裏咱們不知使用它. mgmtlisten = 0.0.0.0:7501 #→mogilefs的管理端口. docroot = /data/mogdata #→該項決定了數據的在storage上存儲的實際位置,建議使用的是一個單獨掛載使用的磁盤.這裏我就不用演示了. [root@node1 ~]# mkdir -p /data/mydata/dev1 #→這裏必定要改變數據存放目錄的屬主屬組,應爲mogilefs服務程序必須是以普通用戶來運行的,不然服務啓動將失敗! [root@node1 ~]# chown -R mogilefs.mogilefs /data/mogdata/dev1
<6>啓動tracker和storage服務:
[root@node2 ~]# service mogilefsd start Starting mogilefsd [ OK ] [root@node2 ~]# service mogstored start Starting mogstored [ OK ] [root@node2 ~]#
<7>在node1上面將本身添加mogstore存儲主機
[root@node1 ~]# mogadm --trackers=172.16.41.1:7001 host add 172.16.41.1 --ip=172.16.41.1 --status=alive
下面繼續配置:
<8>現將兩個配置文件拷貝至兩個節點中--要保證各個程序包都已經安裝了,不然在拷貝後安裝會覆蓋兩個配置文件.
[root@node1 ~]# scp /etc/mogilefs/* 172.16.41.2:/etc/mogilefs/ mogilefsd.conf 100% 1462 1.4KB/s 00:00 mogstored.conf 100% 93 0.1KB/s 00:00 [root@node1 ~]# scp /etc/mogilefs/* 172.16.41.3:/etc/mogilefs/ mogilefsd.conf 100% 1462 1.4KB/s 00:00 mogstored.conf 100% 93 0.1KB/s 00:00 [root@node1 ~]#
(4)配置node2.example.com
<1>程序包已經安裝
<2>設定數據庫已經完畢,該節點與node3節點無需重複此操做
<3>配置tracker.
#→安裝好tracker後會在/var/run/下面生成該目錄,改變目錄屬主.屬組 [root@node2 ~]# chown -R mogilefs.mogilefs /var/run/mogilefsd
<4>修改tracker配置文件,以下內容:
[root@node2 ~]# vim /etc/mogilefs/mogilefsd.conf #→修改下面4項便可其它參數根據工做環境自定 db_dsn = DBI:mysql:mogdb:host=172.16.41.5 db_user = moguser db_pass = 123.com listen = 172.16.41.2:7001
<5>修改storage配置文件,以下內容:
[root@node2 ~]# vim /etc/mogilefs/mogstored.conf maxconns = 10000 httplisten = 0.0.0.0:7500 mgmtlisten = 0.0.0.0:7501 docroot = /data/mogdata#→該項決定了數據的在storage上存儲的實際位置,建議使用的是一個單獨掛載使用的磁盤.這裏我就不用演示了. [root@node2 ~]# mkdir -p /data/mydata/dev2 #→這裏必定要改變數據存放目錄的屬主屬組,應爲mogilefs服務程序必須是以普通用戶來運行的,不然服務啓動將失敗! [root@node2 ~]# chown -R mogilefs.mogilefs /data/mogdata/dev2
<6>啓動tracker和storage服務:
[root@node2 ~]# service mogilefsd start Starting mogilefsd [ OK ] [root@node2 ~]# service mogstored start Starting mogstored [ OK ] [root@node2 ~]#
<7>在node1上面將本身添加mogstore存儲主機
[root@node2 ~]# mogadm --trackers=172.16.41.2:7001 host add 172.16.41.2 --ip=172.16.41.2 --status=alive
此時兩個節點都加入到了MogileFS系統中,第三個節點配置與第二個同樣,只是配置文件修改一下便可,這裏不在贅述!
下面就能夠在node1節點上控制其餘兩個節點便可!
(5)管理配置MogileFS集羣系統
#→添加的第一個設備,設備號不能重名 [root@node1 ~]# mogadm --trackers=172.16.41.1:7001 device add 172.16.41.1 1 #→添加的第二個設備 [root@node1 ~]# mogadm --trackers=172.16.41.2:7001 device add 172.16.41.2 2 #→添加的第三個設備 [root@node1 ~]# mogadm --trackers=172.16.41.3:7001 device add 172.16.41.3 3 [root@node1 ~]# mogadm --trackers=172.16.41.3:7001 device list
<2>添加域domain-----域用來存儲不一樣應用類型的數據的容器
#→建立的圖片存放域 [root@node1 ~]# mogadm --trackers=172.16.41.1:7001 domain add p_w_picpaths #→建立的html等文件存放域 [root@node1 ~]# mogadm --trackers=172.16.41.1:7001 domain add files [root@node1 ~]# mogadm --trackers=172.16.41.1:7001 domain list
<3>添加類class
[root@node1 ~]# mogadm --trackers=172.16.41.1:7001 class add p_w_picpaths class0 --mindevcount=2 [root@node1 ~]# mogadm --trackers=172.16.41.1:7001 class add p_w_picpaths class1 --mindevcount=2 [root@node1 ~]# mogadm --trackers=172.16.41.1:7001 class add p_w_picpaths class3 --mindevcount=2 [root@node1 ~]# mogadm --trackers=172.16.41.1:7001 class add files class0 --mindevcount=2 [root@node1 ~]# mogadm --trackers=172.16.41.1:7001 class add files class1 --mindevcount=2 [root@node1 ~]# mogadm --trackers=172.16.41.1:7001 class add files class2 --mindevcount=2 [root@node1 ~]# mogadm --trackers=172.16.41.1:7001 class list
這裏再次提一下關於這兩個概念
域(domain)
在一個 MogileFS 中,能夠有多個域,用來存放不一樣的文件,好比,不一樣大小的文件,不一樣類型的文件.在上圖中全部 alive 的"設備"是一個大的總體,造成一個統一的存儲空間,裏面的數據能夠根據 "域" domain 和類 class 來分類管理,屬於同一個 domain,即便是屬於不一樣的class,文件的key也必須是惟一的.不一樣域的 key 才能重複.
類(class)
在一個域中,能夠有多個類,主要是用來控制複製單元的,類是用來作屬性管理的,類是比域 domain 低一個級別,能夠定義一個文件存儲在不一樣 device 中的份數.一個文件必須經過 domain,class 和 key 才能找出來.咱們能夠給不一樣的重要程度的文件,不一樣熱度的文件,來分別用類來控制份數.
使用mogupload工具在這裏是爲了測試,實際環境中上傳是由程序員在代碼中使用mogilefs的API進行交互的。
[root@node1 ~]# mogupload --trackers=172.16.41.1:7001 --domain=p_w_picpaths --key='tux_1.jpg' --file='/root/my_test_data/1.jpg' #→--key='tux_1.jgp' 是我要上傳後的鍵是什麼 #→ --file 指的是我要上傳的文件
經過將它給出的路徑來訪問一下看能不能正常的訪問到?
模擬某個節點故障,看文件是否還在?
看到咱們的文件還有一份保存在另一節點上面的,經過那個路徑也能訪問到該文件,並且在每一個storage節點上都能看到這個文件,以前說過啦,他們用的都是一個數據庫;
OK!此時咱們MogileFS系統基本上部暑基本完畢;
下面介紹Nginx作爲MogileFS的前端客戶端是如何實現的!
Nginx作爲MogileFS的前端客戶端,咱們使用Nginx來吐文件,作前端的查詢代理時,咱們須要使用到mogilefs的這個模塊,能夠下載這個模塊編譯進Nginx就好了,直接使用 ./configure -add-module=這個參數就能夠了,最新的這個模塊的下載地址是:https://github.com/vkholodkov/nginx-mogilefs-module
#這裏須要安裝個pcre-devel包 [root@node4 ~]# yum install -y pcre-devel #解壓獲取到的mogilefs模塊包 [root@node4 ~]# unzip nginx-mogilefs-module-master.zip #解壓、編譯安裝nginx [root@node4 ~]# tar -xf nginx-1.4.7.tar.gz -C /usr/src/ [root@nginx ~]# cd /usr/src/nginx-1.4.7/ [root@nginx nginx-1.4.7]# ./configure \ --prefix=/usr \ --sbin-path=/usr/sbin/nginx \ --conf-path=/etc/nginx/nginx.conf \ --error-log-path=/var/log/nginx/error.log \ --http-log-path=/var/log/nginx/access.log \ --pid-path=/var/run/nginx/nginx.pid \ --lock-path=/var/lock/nginx.lock \ --user=nginx \ --group=nginx \ --with-http_ssl_module \ --with-http_flv_module \ --with-http_stub_status_module \ --with-http_gzip_static_module \ --http-client-body-temp-path=/var/tmp/nginx/client/ \ --http-proxy-temp-path=/var/tmp/nginx/proxy/ \ --http-fastcgi-temp-path=/var/tmp/nginx/fcgi/ \ --http-uwsgi-temp-path=/var/tmp/nginx/uwsgi \ --http-scgi-temp-path=/var/tmp/nginx/scgi \ --with-pcre \ --with-debug \ --add-module=/root/nginx-mogilefs-module-master
2.爲nginx提供SysV init腳本:
[root@nginx ~]# vim /etc/rc.d/init.d/nginx #!/bin/sh # # nginx - this script starts and stops the nginx daemon # # chkconfig: - 85 15 # description: Nginx is an HTTP(S) server, HTTP(S) reverse \ # proxy and IMAP/POP3 proxy server # processname: nginx # config: /etc/nginx/nginx.conf # config: /etc/sysconfig/nginx # pidfile: /var/run/nginx.pid # Source function library. . /etc/rc.d/init.d/functions # Source networking configuration. . /etc/sysconfig/network # Check that networking is up. [ "$NETWORKING" = "no" ] && exit 0 nginx="/usr/sbin/nginx" prog=$(basename $nginx) NGINX_CONF_FILE="/etc/nginx/nginx.conf" [ -f /etc/sysconfig/nginx ] && . /etc/sysconfig/nginx lockfile=/var/lock/subsys/nginx make_dirs() { # make required directories user=`nginx -V 2>&1 | grep "configure arguments:" | sed 's/[^*]*--user=\([^ ]*\).*/\1/g' -` options=`$nginx -V 2>&1 | grep 'configure arguments:'` for opt in $options; do if [ `echo $opt | grep '.*-temp-path'` ]; then value=`echo $opt | cut -d "=" -f 2` if [ ! -d "$value" ]; then # echo "creating" $value mkdir -p $value && chown -R $user $value fi fi done } start() { [ -x $nginx ] || exit 5 [ -f $NGINX_CONF_FILE ] || exit 6 make_dirs echo -n $"Starting $prog: " daemon $nginx -c $NGINX_CONF_FILE retval=$? echo [ $retval -eq 0 ] && touch $lockfile return $retval } stop() { echo -n $"Stopping $prog: " killproc $prog -QUIT retval=$? echo [ $retval -eq 0 ] && rm -f $lockfile return $retval } restart() { configtest || return $? stop sleep 1 start } reload() { configtest || return $? echo -n $"Reloading $prog: " killproc $nginx -HUP RETVAL=$? echo } force_reload() { restart } configtest() { $nginx -t -c $NGINX_CONF_FILE } rh_status() { status $prog } rh_status_q() { rh_status >/dev/null 2>&1 } case "$1" in start) rh_status_q && exit 0 $1 ;; stop) rh_status_q || exit 0 $1 ;; restart|configtest) $1 ;; reload) rh_status_q || exit 7 $1 ;; force-reload) force_reload ;; status) rh_status ;; condrestart|try-restart) rh_status_q || exit 0 ;; *) echo $"Usage: $0 {start|stop|status|restart|condrestart|try-restart|reload|force-reload|configtest}" exit 2 esac [root@nginx ~]# chmod +x /etc/rc.d/init.d/ [root@nginx ~]# chkconfig --add nginx [root@nginx ~]# chkconfig nginx on #啓動nginx [root@nginx ~]# service nginx start Starting nginx: [ OK ] [root@nginx ~]# ss -tnl | grep :80 LISTEN 0 128 *:80 *:* [root@nginx ~]#
3.修改nginx主配置文件:
[root@nginx ~]# vim /etc/nginx/nginx.conf worker_processes 2; events { worker_connections 1024; } http { include mime.types; default_type application/octet-stream; sendfile on; keepalive_timeout 65; gzip on; server { listen 80; server_name www.magelinux.com; location / { root html; index index.html index.htm; } ################About p_w_picpaths############### location /p_w_picpaths/ { mogilefs_tracker 172.16.41.1:7001; mogilefs_domain p_w_picpaths; mogilefs_pass { proxy_pass $mogilefs_path; proxy_hide_header Content-Type; proxy_buffering off; } } ################About files############### location /files/ { mogilefs_tracker 172.16.41.1:7001; mogilefs_domain p_w_picpaths; mogilefs_pass { proxy_pass $mogilefs_path; proxy_hide_header Content-Type; proxy_buffering off; } } error_page 404 /404.html; error_page 500 502 503 504 /50x.html; location = /50x.html { root html; } } }
4.測試:
下面我上傳一個html文檔看可否代理成功?
此時我查看到了在兩個域類有兩個key,注意它們在上傳的時候輸入的類容,以及在去觀察在nginx反代中的書寫方法有是有必定區別的,先測試,稍後說
ok!fiels測試沒有問題,可是咱們能夠將nginx的配置修改一下,讓我在定義鍵的時候也改一下.
nginx中只須要修改 location /files/ 和proxy pass這段內容便可,這種方式定義p_w_picpaths也同樣適用,先看看效果吧.
從新加載nginx、再次訪問測試:
這兩種定義方法可根據實際場景應用!
從新加載nginx、再次訪問測試:
#################################################################### #→顯示當前mogilefs的配置信息(host,domain,class)狀態,若是加上--stats="domains"能夠只顯示domian相關的信息. [root@node1 ~]# mogstats --config=/etc/mogilefs/mogilefsd.conf #################################################################### #→顯示一個具體文件的信息,包括所在域、副本數、文件ID、key、複製到了哪些tracker上面. [root@node1 ~]# mogfileinfo --trackers=172.16.41.1:7001 --domain=p_w_picpaths --key="tux_1.jpg" #################################################################### #→上傳一個本地文件到指定的域內,同時必須指定key. [root@node1 ~]# mogupload --trackers=172.16.41.1:7001 --domain=p_w_picpaths --key='tux_1.jpg' --file='/root/my_test_data/1.jpg' #################################################################### #→刪除指定域內的一個key. [root@node1 ~]# mogdelete --trackers=172.16.41.1:7001 --domain=p_w_picpaths --key='test1.html #################################################################### #→查看指定域內的文件有哪些. [root@node1 ~]# moglistkeys --trackers=172.16.41.1:7001 --domain=files #################################################################### #→檢查整個mogilefs系統. [root@node1 ~]# mogadm --trackers=172.16.41.1:7001 check #################################################################### ................................ ................................ #→以上工具使用較爲方便,其餘工具使用請找"man"!
至此,mogilefs的部署已經完成,後續還有許多地方須要改進;
以上內容如有錯誤,請朋友們指出!
寫博、不易,比不了別人,就作好本身!