简介
文件实时同步对于运维是个很常见的需求.
如集群的机器, 需要上传个文件, 之前的步骤是每台服务器分别上传.
做文件同步以后, 只上传一台, 其他机器自动同步.
目前实现实时同步的主流方案有 rsync+inotify,sersync,lsyncd.
rsync + inotify
rsync + inotify 是最常见的方案.
Inotify 是一个 Linux 内核特性, 它监控文件系统, 并且及时向专门的应用程序发出相关的事件警告, 比如删除, 读, 写和卸载操作等
本准备试验一下, 在网上看到如下评价:
当向监控目录下拷贝复杂层次目录(多层次目录中包含文件), 或者向其中拷贝大量文件时, inotify 经常会随机性地遗漏某些文件. 这些遗漏掉的文件由于未被监控到, 所有监控的后续操作都不会执行, 例如不会被 rsync 同步.
sersync
这是国人开发的实时同步工具. 优点如下:
1.sersync 是使用 c++ 编写, 而且对 Linux 系统文件系统产生的临时文件和重复的文件操作进行过滤, 所以在结合 rsync 同步的时候, 节省了运行时耗和网络资源. 因此更快.
2. 配置简单, 其中 bin 目录下已经有基本上静态编译的 2 进制文件, 配合 bin 目录下的 xml 配置文件直接使用即可.
3. 使用多线程进行同步, 尤其在同步较大文件时, 能够保证多个服务器实时保持同步状态.
4. 有出错处理机制, 通过失败队列对出错的文件重新同步, 如果仍旧失败, 则按设定时长对同步失败的文件重新同步.
5. 自带 crontab 功能, 只需在 xml 配置文件中开启, 即可按您的要求, 隔一段时间整体同步一次. 无需再额外配置 crontab 功能.
实战
ip | 目录 | 角色 |
---|---|---|
192.168.1.2 | /home/work | 同步机 |
192.168.1.3 | /home/work | 被同步机 |
基于 Centos6 , 使用 sersync + rsync 将 192.168.1.2 的 /home/work 目录实时同步到 192.168.1.3 的 /home/work 目录下.
192.168.1.3 被同步机操作
- yum install rsync -y
- VIM /etc/rsyncd.conf
- log file = /var/log/rsyncd.log #日志文件
- pidfile = /var/run/rsyncd.pid #pid 文件
- lock file = /var/run/rsync.lock #锁文件
- secrets file = /etc/rsync.pass #认证文件
- max connections = 0 # 连接数限制, 0 即不限制
- [dubbo] # 模块名
- path = /home/work # 同步目录
- comment = dubbo # 注释, 要与模块名一致
- uid = root #设置 rsync 运行权限
- gid = root
- port = 873
- use chroot = no
- read only = no
- list = no
- timeout = 600
- auth users = xx # 认证用户
- hosts allow =192.168.1.2 # 允许同步的机器
- hosts deny = 0.0.0.0/32
- VIM /etc/rsync.pass
- xx:abc123 #对应 rsyncd.conf 的 auth users
设置文件权限
- chmod 600 /etc/rsyncd.conf
- chmod 600 /etc/rsync.pass
启动
rsync --daemon
192.168.1.2 同步端操作
- yum install rsync -y
- rsync --daemon
- echo "abc123"> /etc/passwd.txt
- chmod 600 /etc/passwd.txt
- sersync
以下解释下配置文件
- <?xml version="1.0" encoding="ISO-8859-1"?>
- <head version="2.5">
- <host hostip="localhost" port="8008"></host>
- <debug start="false"/> #是否开启 debug 模式, 默认未开启
- <fileSystem xfs="false"/> # 文件系统是 xfs 的要开启才能正常工作
- <filter start="true"> #是否开启文件过滤, 如下几种类型可以根据自己需要进行修改.
- <exclude expression="(.*)\.out"></exclude> #过滤. out 文件, 如 tomcat 的 catalina.out, 微服务的 nohup.out
- <exclude expression="(.*)\.gz"></exclude> #过滤. gz 文件
- <exclude expression="^logs/*"></exclude> #过滤 logs 目录, 如 tomcat 的 logs 目录
- <exclude expression="^static/*"></exclude> #同上解释
- </filter>
- <inotify> # inotify 的选项, 默认即可
- <delete start="true"/>
- <createFolder start="true"/>
- <createFile start="false"/>
- <closeWrite start="true"/>
- <moveFrom start="true"/>
- <moveTo start="true"/>
- <attrib start="false"/>
- <modify start="false"/>
- </inotify>
- <sersync>
- <localpath watch="/home/work/"> # 要同步的目录
- <remote ip="192.168.1.3" name="dubbo"/> # 要同步的服务器, 及 rsyncd.conf 模块名
- <!--<remote ip="192.168.8.39" name="tongbu"/>-->
- <!--<remote ip="192.168.8.40" name="tongbu"/>-->
- </localpath>
- <rsync> # 这里使用的是 rsync daemon 去同步, 而不是 SSH, 所以要指定 passwordfile 文件
- <commonParams params="-artuz"/>
- <auth start="true" users="xx" passwordfile="/etc/passwd.txt"/>
- <userDefinedPort start="false" port="874"/><!-- port=874 -->
- <timeout start="false" time="100"/><!-- timeout=100 -->
- <SSH start="false"/>
- </rsync>
- <failLog path="/tmp/rsync_fail_log.log" timeToExecute="60"/><!--default every 60mins execute once--> # 同步错误日志
- <crontab start="true" schedule="600"><!--600mins--> #是否开启全盘同步.
- <crontabfilter start="false"> #如果开启了全盘同步, 这里也要开启, 并设置与上面一致的过滤类型.
- <exclude expression="*(.*)\.out"></exclude>
- <exclude expression="^logs/*"></exclude>
- </crontabfilter>
- </crontab>
- <plugin start="false" name="command"/>
- </sersync>
- <plugin name="command">
- <param prefix="/bin/sh" suffix=""ignoreError="true"/> <!--prefix /opt/tongbu/mmm.sh suffix-->
- <filter start="false">
- <include expression="(.*)\.php"/>
- <include expression="(.*)\.sh"/>
- </filter>
- </plugin>
- <plugin name="socket">
- <localpath watch="/opt/tongbu">
- <deshost ip="192.168.138.20" port="8009"/>
- </localpath>
- </plugin>
- <plugin name="refreshCDN">
- <localpath watch="/data0/htdocs/cms.xoyo.com/site/">
- <cdninfo domainname="ccms.chinacache.com" port="80" username="xxxx" passwd="xxxx"/>
- <sendurl base="http://pic.xoyo.com/cms"/>
- <regexurl regex="false" match="cms.xoyo.com/site([/a-zA-Z0-9]*).xoyo.com/images"/>
- </localpath>
- </plugin>
- </head>
执行同步
/usr/local/sersync/sersync2 -d -r -o /usr/local/sersync/confxml.xml
监控脚本
- VIM /home/check_sersync.sh
- #!/bin/bash
- sersync="/usr/local/sersync/sersync2"
- confxml="/usr/local/sersync/confxml.xml"
- status=$(ps aux|grep 'sersync2'|grep -v grep|wc -l)
- if [[ $status -eq 0 ]]; then
- $sersync -d -r -o $confxml &
- else
- exit 0;
- fi
添加执行权限
chmod +x /home/check_sersync.sh
设置定时任务
crontab -e
每隔两分钟执行一次
- */2 * * * */bin/bash /home/check_sersync.sh> /dev/null 2>&1
- lsyncd
Lysncd 实际上是 lua 语言封装了 inotify 和 rsync 工具, 采用了 Linux 内核 (2.6.13 及以后) 里的 inotify 触发机制, 然后通过 rsync 去差异同步, 达到实时的效果. 我认为它最令人称道的特性是, 完美解决了 inotify + rsync 海量文件同步带来的文件频繁发送文件列表的问题 -- 通过时间延迟或累计触发事件次数实现. 另外, 它的配置方式很简单, lua 本身就是一种配置语言, 可读性非常强. lsyncd 也有多种工作模式可以选择, 本地目录 cp, 本地目录 rsync, 远程目录 rsynCSSh.
这个比 sersync 设置简单些.
实战
被控制端与如上一致.
同步机设置如下:
- yum install lsyncd -y
- VIM /etc/lsyncd.conf
- settings {
- logfile = "/tmp/lsyncd.log", #日志
- statusFile = "/tmp/lsyncd.status", #记录同步的文件和目录
- pidfile = "/var/run/lsyncd.pid",
- statusInterval = 1, #将 lsyncd 的状态写入上面的 statusFile 的间隔, 默认 10 秒
- nodaemon = false,
- inotifyMode = "CloseWrite", #指定 inotify 监控的事件, 默认是 CloseWrite, 还可以是 Modify 或 CloseWrite or Modify
- maxProcesses = 1, #同步进程的最大个数
- maxDelays = 1, #累计到多少所监控的事件激活一次同步, 即使后面的 delay 延迟时间还未到
- }
- sync {
- default.rsync,
- source = "/home/work/",
- delete = true,
- target = "xx@192.168.1.3::dubbo", # 认证用户, 被同步的服务器, 同步的模块名
- -- excludeFrom = "/etc/rsyncd.d/rsync_exclude.lst", #要同步的文件或目录列表, 我测试 lsyncd 过滤并不好用, 不清楚是哪里的问题.
- rsync = {
- binary = "/usr/bin/rsync",
- archive = true,
- compress = false,
- owner = true,
- perms = true,
- whole_file = false,
- password_file = "/etc/passwd.txt"
- }
- }
启动即同步
/etc/init.d/lsyncd start
总结
我个人测试
sersync 文件多时同步较快
lsyncd 同步大文件时速度较快
sersync 过滤功能比较好用, lsyncd 过滤我测试失败, 暂未解决.
来源: http://www.bubuko.com/infodetail-2921522.html