脚本如何双向同步本地远程文件

wen 实用脚本 33

本文目录导读:

脚本如何双向同步本地远程文件

  1. 使用 rsync(适用于 Linux/Mac)
  2. 使用 unison(专门的双向同步工具)
  3. 使用 rclone(支持云存储)
  4. 定时执行方案(crontab)
  5. inotify 实时监控(Linux)
  6. 完整的生产级脚本
  7. 注意事项:
  8. 推荐方案:

要实现本地与远程文件的双向同步,有几种成熟的方法,我来帮你梳理一下:

使用 rsync(适用于 Linux/Mac)

这是最常用的方法,但需要两次传输:

#!/bin/bash
# 双向同步脚本
LOCAL_DIR="/path/to/local/"
REMOTE_DIR="user@host:/path/to/remote/"
# 本地到远程
rsync -avz --delete "$LOCAL_DIR" "$REMOTE_DIR"
# 远程到本地
rsync -avz --delete "$REMOTE_DIR" "$LOCAL_DIR"

优化版本(避免循环触发):

#!/bin/bash
LOCAL_DIR="/path/to/local/"
REMOTE_DIR="user@host:/path/to/remote/"
# 创建临时锁文件防止冲突
LOCK_FILE="/tmp/sync.lock"
if [ -f "$LOCK_FILE" ]; then
    exit 1
fi
touch "$LOCK_FILE"
# 同步方向标记(防止双向同时修改同一文件产生冲突)
rsync -avz --update --delete "$LOCAL_DIR" "$REMOTE_DIR"
rsync -avz --update --delete "$REMOTE_DIR" "$LOCAL_DIR"
rm -f "$LOCK_FILE"

使用 unison(专门的双向同步工具)

安装:sudo apt-get install unisonbrew install unison

#!/bin/bash
# unison 双向同步配置
LOCAL_DIR="/path/to/local"
REMOTE_DIR="ssh://user@host//path/to/remote"
unison "$LOCAL_DIR" "$REMOTE_DIR" \
    -batch \
    -auto \
    -times \
    -perms 0 \
    -ignore "Name .git" \
    -ignore "Name *.tmp"

使用 rclone(支持云存储)

安装:sudo apt install rclone

#!/bin/bash
# rclone 双向同步
LOCAL_DIR="/path/to/local"
REMOTE_DIR="remote:path/to/remote"
# --backup-dir 参数备份冲突文件
rclone bisync "$LOCAL_DIR" "$REMOTE_DIR" \
    --verbose \
    --create-empty-dirs \
    --compare-size \
    --resync

定时执行方案(crontab)

# 每5分钟同步一次
*/5 * * * * /path/to/sync_script.sh
# 或者在后台循环执行
while true; do
    /path/to/sync_script.sh
    sleep 300  # 5分钟
done

inotify 实时监控(Linux)

#!/bin/bash
# 基于 inotify 的实时同步
LOCAL_DIR="/path/to/local"
REMOTE_DIR="user@host:/path/to/remote"
inotifywait -m -r -e modify,create,delete,move "$LOCAL_DIR" |
while read path action file; do
    # 延迟一点防止频繁同步
    sleep 2
    rsync -avz --delete "$LOCAL_DIR" "$REMOTE_DIR"
done

完整的生产级脚本

#!/bin/bash
# 配置
LOCAL_DIR="/path/to/local"
REMOTE_USER="username"
REMOTE_HOST="remote.server.com"
REMOTE_DIR="/path/to/remote"
SSH_KEY="/path/to/ssh/key"
LOG_FILE="/var/log/rsync_sync.log"
# 函数:日志记录
log() {
    echo "[$(date '+%Y-%m-%d %H:%M:%S')] $1" >> "$LOG_FILE"
}
# 函数:执行同步
sync_direction() {
    local source="$1"
    local dest="$2"
    local direction="$3"
    rsync -avz \
        --delete \
        --update \
        --exclude='*.tmp' \
        --exclude='.DS_Store' \
        --exclude='node_modules' \
        --progress \
        --log-file="$LOG_FILE" \
        -e "ssh -i $SSH_KEY" \
        "$source" "$dest"
    if [ $? -eq 0 ]; then
        log "成功: $direction 同步完成"
    else
        log "错误: $direction 同步失败"
    fi
}
# 主同步逻辑
main() {
    log "开始双向同步..."
    # 本地 -> 远程
    sync_direction "$LOCAL_DIR" "${REMOTE_USER}@${REMOTE_HOST}:${REMOTE_DIR}" "本地到远程"
    # 远程 -> 本地
    sync_direction "${REMOTE_USER}@${REMOTE_HOST}:${REMOTE_DIR}" "$LOCAL_DIR" "远程到本地"
    log "双向同步完成"
}
# 执行
main "$@"

注意事项:

  1. 冲突处理:双向同步最大问题是文件冲突,建议使用 --update 参数,保留最新版本
  2. 排除项:排除缓存、临时文件、日志等
  3. SSH免密码:配置 SSH 密钥认证
  4. 增量同步:使用 --update--checksum 只同步变更内容
  5. 备份:建议同步前做增量备份,防止数据丢失

推荐方案:

  • 简单场景:rsync 两遍同步
  • 需要冲突处理:unison
  • 跨平台:rclone
  • 实时同步:inotify + rsync
  • 大型项目:考虑使用 Syncthing(开源P2P同步工具)

选择什么方案取决于你的具体需求:数据量、同步频率、冲突处理方式等,如果有更具体的使用场景,我可以提供更针对性的建议。

抱歉,评论功能暂时关闭!