You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

在GCP中调度任务:将SFTP服务器数据同步至GCS存储桶

方案可行性说明

你的方案完全可以在GCP实现,并且不需要用到Cloud Function——你已有的带白名单静态IP的Compute Engine实例是更合适的执行载体:一方面它不受Cloud Function的9分钟执行时长限制(同步大量文件时更稳定),另一方面无需额外配置网络即可访问SFTP服务器。

实操指导

1. 配置Compute Engine实例的同步环境

1.1 安装必要工具

登录到你的Compute Engine实例,执行以下命令安装同步所需工具(以Debian/Ubuntu系统为例):

sudo apt update && sudo apt install -y openssh-client rsync google-cloud-sdk

1.2 配置SFTP免密登录

为了自动化执行同步,需要设置无需手动输入密码的SFTP登录方式:

  • 生成SSH密钥对(不设密码):
    ssh-keygen -t ed25519 -f ~/.ssh/sftp_sync_key -N ""
    
  • 将生成的公钥~/.ssh/sftp_sync_key.pub内容,添加到SFTP服务器目标用户的~/.ssh/authorized_keys文件中
  • 测试免密登录:
    sftp -i ~/.ssh/sftp_sync_key sftp-user@sftp-server-ip
    
    确认能成功登录且无需输入密码。

1.3 编写同步脚本

创建同步脚本/home/your-user/sync_sftp_to_gcs.sh,替换脚本中的参数为你的实际信息:

#!/bin/bash

# 配置参数
SFTP_USER="你的SFTP用户名"
SFTP_SERVER="SFTP服务器IP/域名"
SFTP_KEY="/home/your-user/.ssh/sftp_sync_key"
SFTP_BASE_DIR="SFTP上要同步的根文件夹路径"
GCS_BUCKET="gs://sftp-data"
LOCAL_TEMP_DIR="/tmp/sftp_sync_temp"

# 创建临时目录
mkdir -p $LOCAL_TEMP_DIR

# 从SFTP同步到本地(只同步新增/修改文件,保持文件夹结构)
rsync -avz -e "ssh -i $SFTP_KEY" --delete $SFTP_USER@$SFTP_SERVER:$SFTP_BASE_DIR/ $LOCAL_TEMP_DIR/

# 从本地同步到Cloud Storage,保持结构一致
gsutil rsync -r $LOCAL_TEMP_DIR/ $GCS_BUCKET/

# 清理临时目录(可选,避免占用磁盘空间)
rm -rf $LOCAL_TEMP_DIR/*

给脚本添加执行权限:

chmod +x /home/your-user/sync_sftp_to_gcs.sh

手动运行脚本测试,确认文件能同步到Cloud Storage且结构一致。

2. 配置Cloud Scheduler定时触发

我们用Cloud Scheduler + Pub/Sub的组合来触发同步任务,避免直接SSH调用的权限复杂度:

2.1 创建Pub/Sub主题

在GCP控制台打开Pub/Sub服务,创建一个主题,名称设为sftp-gcs-sync-trigger。

2.2 在Compute Engine上配置Pub/Sub监听脚本

  • 安装Pub/Sub Python客户端:
    sudo apt install -y python3-pip && pip3 install google-cloud-pubsub
    
  • 创建监听脚本/home/your-user/pubsub_listener.py,替换your-gcp-project-id为你的项目ID:
    import os
    from google.cloud import pubsub_v1
    
    def sync_sftp_to_gcs():
        os.system("/home/your-user/sync_sftp_to_gcs.sh")
    
    def callback(message):
        print("收到同步触发消息,开始执行同步")
        sync_sftp_to_gcs()
        message.ack()
    
    if __name__ == "__main__":
        project_id = "your-gcp-project-id"
        subscription_name = "sftp-sync-subscription"
        subscriber = pubsub_v1.SubscriberClient()
        subscription_path = subscriber.subscription_path(project_id, subscription_name)
        
        # 创建订阅(若已存在则忽略)
        try:
            subscriber.create_subscription(name=subscription_path, topic=f"projects/{project_id}/topics/sftp-gcs-sync-trigger")
        except Exception as e:
            print(f"订阅已存在: {e}")
        
        future = subscriber.subscribe(subscription_path, callback=callback)
        print("正在监听同步触发消息...")
        try:
            future.result()
        except KeyboardInterrupt:
            future.cancel()
    
  • 设置脚本开机自启(用systemd):
    创建/etc/systemd/system/sftp-sync-listener.service文件:
    [Unit]
    Description=SFTP到GCS同步的Pub/Sub监听服务
    After=network.target
    
    [Service]
    User=your-user
    ExecStart=/usr/bin/python3 /home/your-user/pubsub_listener.py
    Restart=always
    
    [Install]
    WantedBy=multi-user.target
    
    启用并启动服务:
    sudo systemctl daemon-reload
    sudo systemctl enable sftp-sync-listener.service
    sudo systemctl start sftp-sync-listener.service
    

2.3 创建Cloud Scheduler定时任务

在GCP控制台打开Cloud Scheduler服务,点击「创建任务」:

  • 任务名称:sftp-gcs-sync-hourly
  • 频率:0 * * * *(每小时整点执行)
  • 时区:选择你的实际时区(如Asia/Shanghai)
  • 目标:选择「Pub/Sub」
  • 主题:选择之前创建的sftp-gcs-sync-trigger
  • 消息正文:可留空或填写"sync"
  • 点击「创建」完成配置

可选优化

  • 给同步脚本添加日志记录,比如在脚本中加入>> /var/log/sftp_sync.log 2>&1,方便排查问题
  • 若只需同步.csv文件,可在rsync命令中添加--include="*.csv" --exclude="*"过滤文件类型
  • 使用gsutil rsync -c选项校验文件完整性,确保同步的文件无损坏

内容的提问来源于stack exchange,提问作者Berra

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.10 21:30:14