分布式系统:

            1、系统的各组件分布于网络上多个计算机;

            2、各组件彼此之间仅仅通过消息传递来通信并协调行动;


    分布式系统存在意义:

            1、向上扩展的性价比越来越低;

            2、单机扩展存在性能上升临界点;

            3、出于稳定性及可用性考虑,单机会存在多方面的问题;

        

    计算机组成:CPU、内存、IO

            多CPU:

                    多线程编程,(线程间共享进程的资源)

                            互不通信的线程模型

                            基于共享容器协同工作的模型

                            通过事件协调的多线程模型 

                    多进程模型


            网络IO:

                    多进程:每个进程响应一个请求;

                    多线程、多进程:每进程生成多个线程,每线程响应一个用户请求

                    多线程:每线程直接响应多个请求


                    基于socket实现网络通信开发,其实现方式:

                            BIO:Blocking IO:一个进程或一个线程处理一个请求;

                            NIO:Nonblocking IO:基于事件驱动(epoll)思想,采用Reactor模式

                            AIO:基于事件驱动思想,采用Proactor模式



        如何把应用从单机扩展至多机?

                    输入设备的变化?

                    输出设备的变化?


        控制器的变化?

                    实现的模式:

                            透明代理

                                    lvs的nat

                                    haproxy, nginx

                            旁路代理

                                    lvs的dr、tun

                            名称服务

                            规则服务

                            Master/slave机制


        运算器的变化:

        

        存储器的变化?

        

        分布式系统实现的难点:

                缺乏全局时钟?

                面对故障时的独立性

                处理单点故障

                事务处理

                ACID

        

2PC、BASE、CAP、Paxos


大型网站站点的架构演进方式:

LAMT, LNMT


应用从资源占用的角度分两类:

CPU Bound

IO Bound: IO密集型


session sticky

ip based

cookie based

session replication

session server


引用MySQL主从面临的问题:

1、数据复制的问题

2、应用选择数据源的问题


引入缓存:

1、页面缓存

varnish, squid

2、数据缓存

key-value store: memcached


主库写操作压力:数据库拆分

垂直拆分:把数据库中不同的业务的数据拆分到不同的数据库服务器中

水平拆分:把一个单独的表中的数据拆分到多个不同的数据库服务器上


NoSQL: 非关系数据

文档数据库

列式数据库

... ...


应用拆分:

根据业务特性拆分

根据用户拆分:

用户注册

用户登录

用户信息维护

根据对底层应用的调用进行拆分


异步:解耦

消息中间件:在分布式系统中,完成消息发送和接收的基础性软件;

MOM:Message-oriented middleware


RabbitMQ, ActiveMQ, ZMQ



分布式存储:

    数据类型:

            结构化数据:SQL,TPS,MYSQL(主从复制、分库分表);

            半结构化数据:json,xml(document store,mongodb、elasticsearch)

            非结构化数据:k-v

    

    CAP:一致性、可用性、网络分区容错性;


    通用分布式存储:分布式存储,不可直接挂载,需通过api:mogilefs,fastdfs 等等

    专用分布式存储:分布式文件系统,可直接挂载:moosefs,ceph等等


常见的分布式文件系统:

GlusterFS:适用于存储少量大文件

MogileFS:适用存储海量小文件

使用MySQL存储元数据

FastDFS

MooseFS:

Ceph:内核级别,支持PB级别存储的分布式文件系统;

HDFS:Lucene, MapReduce + HDFS = Hadoop (平台),  HBase(NoSQL)

GFS:Google FS

MapReduce 

Bigtable

TFS: 适用于存储海量小文件

Lustre: Oracle的开源的分布式文件


MogileFS:

开源的分布式存储,由LiveJournal旗下的Danga Interactive;

memcached, MogileFS, Perlbal


MogileFS的特性:

1、应用层:运行于用户空间;

2、无单点失败:

        mogstored:存储多个数据副本;

        tracker:多节点;

        database:mysql等等

3、自动文件复制

4、不需要RAID;

5、传输中立,无特殊协议(HTTP或NFS)

6、简单的名称空间:

        domain,class,fid(key);

7、不用共享任何数据:

        元数据:db;

        数据:mogstored,副本;


MogileFS的角色:

        Tracker:Mogilefsd进程;其实现的功能包括Replication,Deletion, Query, Monitor等等;

        Storage Nodes: mogstored进程;文件实际存储的位置,其实质上是一个http服务器,基于WebDAV模式工作,能完成文件创建、删除、重命名等操作;

        MySQL节点:用于为tracker存储元数据信息;mogilefs的名称空间及文件名;

服务进程有两个:

    tracker: mogilefsd

    storage nodes: mogstored


perl模块的安装方式:

        线上安装:自动解决依赖关系

                cpan> install module_name::name

        离线安装:

                编译:

                # perl Makefile.PL

                # make

                # make install

                rpm包:

                # yum install

安装tracker:

1、安装相关的包:

MogileFS-Server-2.46-2.el6.noarch.rpm  MogileFS-Server-mogilefsd-2.46-2.el6.noarch.rpm  perl-Net-Netmask-1.9015-8.el6.noarch.rpm MogileFS-Server-mogstored-2.46-2.el6.noarch.rpm  perl-Perlbal-1.78-1.el6.noarch.rpm

2、授权数据库用户,并初始mysql数据库

mysql> CREATE DATABASE mogdb CHARSET ‘utf8';

mysql> GRANT ALL ON mogdb.* TO 'moguser'@'127.0.0.1' IDENTIFIED BY 'mogpass';

mysql> GRANT ALL ON mogdb.* TO 'moguser'@'localhost' IDENTIFIED BY 'mogpass';

mysql> flush privileges;

# mogdbsetup --dbname=mogdb --dbuser=moguser --dbpass=mogpass

3、修改配置文件mogilefsd.conf

db_dsn = DBI:mysql:DBNAME:host=172.16.100.7

4、启动mogilefsd进程

# service mogilefsd start


安装mogstored:

1、安装相关的包

MogileFS-Server-2.46-2.el6.noarch.rpm  MogileFS-Server-mogilefsd-2.46-2.el6.noarch.rpm  perl-Net-Netmask-1.9015-8.el6.noarch.rpm MogileFS-Server-mogstored-2.46-2.el6.noarch.rpm  perl-Perlbal-1.78-1.el6.noarch.rpm  perl-IO-AIO

2、准备存储设备

挂载至某路径下,确认此路径下存在文件devN

此路径的属主和属组为mogilefs.mogilefs

3、修改配置文件/etc/mogilefs/mogstored.conf

docRoot=

前面的挂载路径;

4、启动mogstored进程

# service mogtored start


配置mogielfs:mogadm --help查看帮助信息

1、向tracker添加各mogstored主机

mogadm --trackers=TRACKER_NODE host add 


2、向tracker添加各设备

mogadm --trackers=TRACKER_NODE device add 


3、为tracker定义名称空间domain

mogadm --trackers=TRACKER_NODE domain add 


4、为domain添加一个或多个class

mogadm --trackers=TRACKER_NODE class add

可同时副本的最少个数;


上传文件:mogupload


下载文件:mogfeatch


查看文件信息:mogfileinfo 


mogilefs与nginx结合:nginx_mogilefs_module

        编译安装nginx时加上--add-module=模块的的解压路径即可

        配置文件nginx.conf示例:

            将trackers定义为upstream示例:

                    upstream mogtrackers {

                            server 172.20.120.22:7001;

                            server 172.20.120.23:7001;

                    }

                并且在server段内添加

                location /images {

                        mogilefs_tracker  mogtrackers;

                        mogilefs_domain imgs;

                        mogilefs_pass {

                                proxy_pass $mogilefs_path;

                                proxy_hide_header Content-type;

                                proxy_buffering off;

                        }

                }

                测试验证手动验证:

                        1、通过mogupload --trackers=172.20.120.22 --domain=imgs --key='dune.jpg' --file=/usr/share/backgrounds/nature/Dune.jpg

                        2、手动查看mogfileinfo --trackers=172.20.120.22 --domain=imgs --key='dune.jpg'

                        3、通过浏览器url验证   http://nginx-ip/images/dune.jpg


            开启status示例:

                    location /status {

                            stub_status on;

                            access_log off;

                            allow 172.20.120.0/24;

                            deny all;

                    }

            


FastDFS:开源的轻量级分布式文件系统,c++

    三个角色:tracker、storage、client

    tacker server:跟踪服务器,调度;在内存中记录所有储存组和储存服务器的状态信息;

    storage server:存储服务器,文件(data)和文件属性(metadata);

    client:客户端,业务请求发起方,通过专用接口基于tcp协议与tracker以及storage server进行交互;


    扩展示例:如何根据源码制作rpm包       

    # git clone https://github.com/happyfish100/libfastcommon.git

    # less INSTALL

    # less libfastcommon-1.0.40/libfastcommon.spec   查看该软件版本号

    # mv libfastcommon libfastcommon-1.0.40

    # tar zcf libfastcommon-1.0.40.tar.gz libfastcommon-1.0.40/*    打包

    # mkdir -pv rpmbuild/{SOURCES,SPECS}

    # cp libfastcommon-1.0.40.tar.gz rpmbuild/SOURCES/

    # cp libfastcommon-1.0.40/libfastcommon.spec rpmbuild/SPECS/

    # cd rpmbuild/SPECS/

    # rpmbuild -ba libfastcommon.spec


    fastdfs托管在github:https://github.com/happyfish100/fastdfs

    # yum groupinstall "Development Tools" "Server Platform Development" -y

    # yum install git -y 

    # git clone https://github.com/happyfish100/libfastcommon.git

    # less INSTALL

    #  ./make.sh

    # ./make.sh install

    # git clone https://github.com/happyfish100/fastdfs.git

    # less INSTALL   

    #  ./make.sh

    # ./make.sh install


    fastdfs配置文件和测试        

            # group -r fastdfs

            # groupadd -r fastdfs

            # useradd -g fastdfs -r -s /sbin/nologin fastdfs

            # mkdir -pv /data/fdfs/{tracker,storage,client}

            # cd /etc/fdfs/

            # cp tracker.conf.sample tracker.conf

            # vim tracker.conf

                    base_path=/data/fdfs/tracker

                    run_by_group=fastdfs

                    run_by_user=fastdfs

            # service fdfs_trackerd restart

            # cp storage.conf.sample storage.conf

            # vim /etc/fdfs/storage.conf

                    base_path=/data/fdfs/storage

                    store_path0=/data/fdfs/storage

                    tracker_server=192.168.71.41:22122

                    run_by_group=fastdfs

                    run_by_user=fastdfs

            # service fdfs_storaged restart

            # cp client.conf.sample client.conf

            # vim client.conf

                    base_path=/data/fdfs/client

                    tracker_server=192.168.71.41:22122

            # fdfs_test client.conf upload /usr/share/backgrounds/night.jpg     测试


    fastdfs与nginx结合:借用fastdfs-nginx-module模块,前提需手动编译安装nginx

            # wget http://nginx.org/download/nginx-1.16.0.tar.gz

            # yum install pcre-devel openssl-devel -y

            # git clone https://github.com/happyfish100/fastdfs-nginx-module.git

            # tar xvf nginx-1.16.0.tar.gz

            # cd nginx-1.16.0

            # groupadd -r nginx

            # useradd -g nginx -r -s /sbin/nologin nginx

            # ./configure --prefix=/usr/local/nginx --conf-path=/etc/nginx/nginx.conf --pid-path=/var/run/nginx/nginx.pid --lock

-path=/var/lock/nginx.lock --error-log-path=/var/log/nginx/error.log --http-log-path=/var/log/nginx/access.log --user=nginx --group=nginx --with-http_ssl_module --with-http_stub_status_module --with-pcre --add-module=/root/fastdfs-nginx-module/src

            # ln -sv /data/fdfs/storage/data/ /data/fdfs/storage/data/M00

            # cp /etc/nginx/nginx.conf{,.bak}

            # vim /etc/nginx/nginx.conf        

                    location /M00 {

                        root /data/fdfs/storage/data;

                        ngx_fastdfs_module;

                    }

            # cp fastdfs-nginx-module/src/mod_fastdfs.conf /etc/fdfs/

            # vim /etc/fdfs/mod_fastdfs.conf

                    base_path=/data/fdfs/storage

                    store_path0=/data/fdfs/storage

                    tracker_server=192.168.71.41:22122

                    url_have_group_name = true

            # mkdir -pv /var/run/nginx

            # cp fastdfs/conf/{http.conf,mime.types} /etc/fdfs/

            # /usr/local/nginx/sbin/nginx -t

            # vim /etc/profile.d/nginx.sh

                    export PATH=/usr/local/nginx/sbin:$PATH

            # source /etc/profile.d/nginx.sh

            # nginx

            访问URL,测试验证