基于 rsyncd + inotify-tools + sersync 的文件实时同步

方案:接收端配置 rsync 守护进程,发送端通过 inotify 监控文件变化,借助 sersync 调用 rsync 实时同步到接收端(10.40.0.2)

整个方案的核心是利用 inotify 实时监控文件变化,sersync 替代传统的 inotify+rsync 脚本,更稳定且支持失败重传,适合生产环境的文件实时同步需求。

一、整体架构说明

  • 接收端:运行 rsyncd 守护进程,开放指定模块(data_oafile/data_erp_uploadfile),仅允许 10.40.0.0/24 网段访问,需密码认证;
  • 发送端:安装 inotify-tools(监控文件变化)+ sersync(解析监控事件并调用 rsync 同步),监控 /data/erp_uploadfile 目录,实时同步到接收端的 data_erp_uploadfile 模块。

二、接收端(10.40.0.2)完整配置步骤

1、配置 rsyncd.conf

cat >/etc/rsyncd.conf <<EOF
uid = root
gid = root
use chroot = no
log file = /var/log/rsyncd.log  # 日志文件(自动创建)
pid file = /var/run/rsyncd.pid  # PID文件
lock file = /var/run/rsync.lock # 补充锁文件(防止进程冲突)
max connections = 36000        # 最大连接数(根据服务器性能调整)
ignore errors = yes             # 忽略同步中的小错误
read only = no                  # 允许写入(接收端需要可写)
dont compress = *.gz *.tgz *.zip *.z *.Z *.rpm *.deb *.bz2  # 已压缩文件不重复压缩
timeout = 1440                  # 超时时间(分钟)
exclude = lost+found/           # 排除目录
hosts allow = 10.40.0.0/24      # 仅允许该网段访问(安全)
hosts deny = *                  # 拒绝其他所有网段
auth users = rsync              # 认证用户(非系统用户)
secrets file = /etc/rsyncd.secrets  # 密码文件路径

# 同步模块1:data_oafile
[data_oafile]
comment = oafile sync module
path = /data/oafile            # 同步目录(需提前创建)
list = no                      # 不允许列出模块内容(安全)
auth users = rsync             # 该模块使用的认证用户

# 同步模块2:data_erp_uploadfile
[data_erp_uploadfile]
comment = erp upload file sync module
path = /data/erp_uploadfile    # 同步目录(需提前创建)
list = no
auth users = rsync
EOF

2、创建密码文件并设置权限

# 创建密码文件(rsync为认证用户,密码自定义,如123456)
echo "rsync:123456" >/etc/rsyncd.secrets

# 设置权限(关键!必须600,否则rsyncd会报错)
chmod 600 /etc/rsyncd.secrets

3、创建同步目录并设置权限

# 创建模块对应的目录
mkdir -p /data/oafile /data/erp_uploadfile

# 设置权限(root/root,与rsyncd.conf的uid/gid一致)
chown -R root:root /data/oafile /data/erp_uploadfile
chmod -R 755 /data/oafile /data/erp_uploadfile

4、启动rsyncd并设置开机自启

# 启动rsyncd(CentOS 7)
systemctl start rsyncd
# 设置开机自启
systemctl enable rsyncd
# 验证是否启动成功(监听873端口)
netstat -tnlp | grep rsync

5、关闭防火墙、SELinux(或开放873端口)

# 临时关闭防火墙(测试用)
systemctl stop firewalld
systemctl disable firewalld

# 临时关闭SELinux(测试用)
setenforce 0
sed -i 's/^SELINUX=enforcing/SELINUX=disabled/' /etc/selinux/config

# 生产环境推荐开放873端口(不关闭防火墙)
firewall-cmd --add-port=873/tcp --permanent
firewall-cmd --reload

三、发送端完整配置步骤

1、安装依赖(编译 inotify-tools 需要)

yum install -y gcc gcc-c++ make libtool

2、安装 inotify-tools(监控文件变化)

# 创建安装目录
mkdir -p /app/local
cd /app/local

# 下载 inotify-tools(替换为国内镜像)
wget https://nchc.dl.sourceforge.net/project/inotify-tools/inotify-tools/3.14/inotify-tools-3.14.tar.gz

# 解压编译安装
tar zxf inotify-tools-3.14.tar.gz
cd inotify-tools-3.14
./configure --prefix=/app/local/inotify
make && make install

# 添加环境变量(让系统识别inotify命令)
echo "export PATH=/app/local/inotify/bin:\$PATH" >> /etc/profile
source /etc/profile

# 验证安装
inotifywait -V  # 输出版本号则成功

3、安装 sersync(解析监控事件并同步)

cd /app/local

# 下载 sersync(64位)
wget https://github.com/wsgzao/sersync/raw/master/sersync2.5.4_64bit_binary_stable_final.tar.gz

# 解压并移动目录
tar zxf sersync2.5.4_64bit_binary_stable_final.tar.gz
mv GNU-Linux-x86/ /app/local/sersync

# 验证安装
/app/local/sersync/sersync2 -h  # 输出帮助信息则成功

4、配置 sersync(confxml.xml)

cat >/app/local/sersync/confxml.xml <<EOF
<?xml version="1.0" encoding="ISO-8859-1"?>
<head version="2.5">
    <host hostip="localhost" port="8008"></host>
    <debug start="false"/>  <!-- 调试模式:false关闭,true开启(测试用) -->
    <fileSystem xfs="false"/>
    <filter start="false">  <!-- 过滤规则:false关闭,true开启 -->
        <exclude expression="(.*)\.svn"></exclude>
        <exclude expression="(.*)\.gz"></exclude>
        <exclude expression="^info/*"></exclude>
        <exclude expression="^static/*"></exclude>
    </filter>
    <inotify>  <!-- 监控的文件事件(全部开启) -->
        <delete start="false"/>  <!-- 注意:关闭删除同步(防止误删接收端文件),根据需求调整 -->
        <createFolder start="true"/>  <!-- 监控创建目录 -->
        <createFile start="true"/>    <!-- 监控创建文件 -->
        <closeWrite start="true"/>    <!-- 监控文件写入完成 -->
        <moveFrom start="true"/>      <!-- 监控文件移动出目录 -->
        <moveTo start="true"/>        <!-- 监控文件移动进目录 -->
        <attrib start="true"/>        <!-- 监控文件属性变化(权限/时间等) -->
        <modify start="true"/>        <!-- 监控文件内容修改 -->
    </inotify>

    <sersync>
        <!-- 监控的本地目录:与接收端模块对应 -->
        <localpath watch="/data/erp_uploadfile">
            <!-- 接收端配置:ip=接收端IP,name=接收端rsync模块名 -->
            <remote ip="10.40.0.2" name="data_erp_uploadfile"/>
        </localpath>
        <rsync>
            <!-- rsync同步参数:-artuz 包含归档/递归/保持权限/压缩/传输进度 -->
            <commonParams params="-artuz"/>
            <!-- 认证配置:start=true开启认证,users=接收端的auth users,passwordfile=发送端密码文件 -->
            <auth start="true" users="rsync" passwordfile="/etc/rsync.secrets"/>
            <!-- 自定义端口:false使用默认873,true则指定端口(需接收端也改) -->
            <userDefinedPort start="false" port="874"/>
            <!-- 超时时间:false关闭,true指定时间 -->
            <timeout start="false" time="100"/>
            <!-- SSH同步:false使用rsyncd,true使用ssh(需免密) -->
            <ssh start="false"/>
        </rsync>
        <!-- 失败重传:尝试3次,间隔10秒 -->
        <failLog path="/app/local/sersync/rsync_fail.log" timeToExecute="10" start="true"/>
        <!-- 定时全量同步:false关闭,true则每600秒同步一次(防止增量同步遗漏) -->
        <crontab start="false" schedule="600">
            <crontabfilter start="false">
                <exclude expression="*.php"></exclude>
            </crontabfilter>
        </crontab>
        <!-- 远程shell同步:关闭 -->
        <plugin start="false" name="command"/>
    </sersync>

    <plugin name="command">
        <param prefix="/bin/sh" suffix="" ignoreError="true"/>
        <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.xoyo.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>
EOF

5、创建发送端密码文件

# 密码与接收端rsyncd.secrets中的密码一致(如123456)
echo "123456" >/etc/rsync.secrets

# 设置权限
chmod 600 /etc/rsync.secrets

6、创建本地监控目录

mkdir -p /data/erp_uploadfile
chown -R root:root /data/erp_uploadfile
chmod -R 755 /data/erp_uploadfile

7、启动sersync并设置开机自启

# 启动sersync(后台运行,记录日志)
nohup /app/local/sersync/sersync2 -r -d -o /app/local/sersync/confxml.xml >/app/local/sersync/rsync.log 2>&1 &

# 参数说明:
# -r:启动时先全量同步一次(确保初始目录一致)
# -d:守护进程模式
# -o:指定配置文件
# -n:指定线程数(默认10,如-n 20)

# 验证是否启动成功
ps aux | grep sersync2 | grep -v grep

Categories: 系统运维