scp-action/README.zh-cn.md
appleboy 17026f90b8
docs: add comprehensive Chinese documentation and localization support
- Add links to Traditional and Simplified Chinese documentation in the README
- Add a complete README in Simplified Chinese, including setup, configuration, usage examples, best practices, troubleshooting, and FAQ
- Add a complete README in Traditional Chinese, including setup, configuration, usage examples, best practices, troubleshooting, and FAQ

Signed-off-by: appleboy <appleboy.tw@gmail.com>
2025-04-27 11:37:08 +08:00

11 KiB
Raw Blame History

🚀 GitHub Actions 的 SCP

English | 繁體中文

GitHub Action 用于通过 SSH 复制文件和构建产物。

Actions Status

注意: 仅支持 Linux docker 容器。


功能特性

  • 通过 SSH 将文件和产物复制到一台或多台远程服务器
  • 支持 SSH 密钥和密码认证
  • 完全支持 SSH 代理(跳板机)
  • 处理 Linux ↔ Windows 路径转换
  • 集成 GitHub Artifacts 工作流
  • 支持增量与差异文件传输
  • 丰富的高级配置选项

📦 目录


🚀 快速开始

在 GitHub Actions 工作流中通过 SSH 复制文件和产物:

name: scp files
on: [push]
jobs:
  build:
    runs-on: ubuntu-latest
    steps:
      - uses: actions/checkout@v4
      - name: 通过 SSH 复制文件
        uses: appleboy/scp-action@v0.1.7
        with:
          host: ${{ secrets.HOST }}
          username: ${{ secrets.USERNAME }}
          password: ${{ secrets.PASSWORD }}
          port: ${{ secrets.PORT }}
          source: "tests/a.txt,tests/b.txt"
          target: your_server_target_folder_path

⚙️ 配置说明

🔌 连接设置

变量 说明 默认值 必填
host 远程主机(多台用逗号分隔) -
port SSH 端口 22
username SSH 用户名 -
password SSH 密码(建议优先使用密钥认证) -
key SSH 私钥内容 -
key_path SSH 私钥文件路径 -
passphrase SSH 私钥密码 -
fingerprint 主机密钥 SHA256 指纹验证 -
protocol IP 协议:'tcp'、'tcp4' 或 'tcp6' tcp
timeout SSH 连接超时 30s
command_timeout SCP 命令超时 10m

📁 文件传输设置

变量 说明 默认值 安全性说明
source 本地要传输的文件/目录(逗号分隔) - 请使用明确路径
target 远程目标目录(必须为目录) - 避免使用根目录
rm 上传前移除目标目录 - 谨慎使用
strip_components 传输时移除前置路径元素 -
overwrite 使用 tar 覆盖现有文件 -
tar_dereference tar 传输时跟随符号链接 -
tar_tmp_path 目标端 tar 临时文件路径 -
tar_exec 目标端 tar 执行文件路径 tar
debug 启用调试输出 -
curl_insecure curl 使用 --insecure false 不推荐
capture_stdout 将命令 stdout 作为 action 输出 false
version 指定 drone-scp 版本 -

🌐 代理设置

变量 说明 默认值 必填
proxy_host SSH 代理主机 -
proxy_port SSH 代理端口 22
proxy_username SSH 代理用户名 -
proxy_password SSH 代理密码 -
proxy_key SSH 代理私钥内容 -
proxy_key_path SSH 代理私钥文件路径 -
proxy_passphrase SSH 代理私钥密码 -
proxy_fingerprint 代理主机 SHA256 指纹验证 -
proxy_use_insecure_cipher 启用较不安全的代理加密算法 -
proxy_timeout SSH 代理连接超时 30s

🛡️ 最佳实践与安全性

  • 建议优先使用 SSH 密钥认证,提升安全性。
  • 将所有敏感信息host、username、password、key存放于 GitHub Secrets
  • 定期更换部署密钥(建议每 90 天一次)。
  • 限制目标服务器目录的写入权限。
  • 启用主机密钥指纹验证以防止中间人攻击。
  • 避免使用 root 用户登录 SSH。

🖥️ 跨平台注意事项

场景 Linux 服务器 Windows 服务器
路径格式 /path/to/dir /c/path/to/dir
必要设置 tar_dereference: true
权限 保留 可能需手动设置 ACL
Shell bash默认 Git BashOpenSSH

🚩 重要提醒:
复制到 Windows 服务器时:

  • 安装 Git for Windows 并将 OpenSSH 默认 shell 设为 Git Bash
  • 使用类 Unix 目标路径(如 /c/Users/...
  • 启用 tar_dereference 处理符号链接

💡 使用示例

🧩 场景导览


示例 1基本 SSH 密码

- name: 通过 SSH 密码复制文件
  uses: appleboy/scp-action@v0.1.7
  with:
    host: example.com
    username: foo
    password: bar
    port: 22
    source: "tests/a.txt,tests/b.txt"
    target: your_server_target_folder_path

示例 2多台服务器

- name: 复制到多台服务器
  uses: appleboy/scp-action@v0.1.7
  with:
    host: "foo.com,bar.com"
    username: foo
    password: bar
    port: 22
    source: "tests/a.txt,tests/b.txt"
    target: your_server_target_folder_path

示例 3仅传输变更文件

- name: 获取变更文件
  id: changed-files
  uses: tj-actions/changed-files@v35
  with:
    since_last_remote_commit: true
    separator: ","

- name: 复制变更文件到服务器
  uses: appleboy/scp-action@v0.1.7
  with:
    host: ${{ secrets.HOST }}
    username: ${{ secrets.USERNAME }}
    key: ${{ secrets.KEY }}
    port: ${{ secrets.PORT }}
    source: ${{ steps.changed-files.outputs.all_changed_files }}
    target: your_server_target_folder_path

示例 4集成 Artifacts

- uses: actions/upload-artifact@v4
  with:
    name: my-artifact
    path: world.txt

- uses: actions/download-artifact@v4
  with:
    name: my-artifact
    path: distfiles

- name: 复制 artifact 到服务器
  uses: appleboy/scp-action@v0.1.7
  with:
    host: ${{ secrets.HOST }}
    username: ${{ secrets.USERNAME }}
    key: ${{ secrets.KEY }}
    port: ${{ secrets.PORT }}
    source: distfiles/*
    target: your_server_target_folder_path

示例 5Windows 服务器

- name: 复制到 Windows
  uses: appleboy/scp-action@v0.1.7
  with:
    host: ${{ secrets.HOST }}
    username: ${{ secrets.USERNAME }}
    key: ${{ secrets.SSH_PRIVATE_KEY }}
    port: 22
    source: "your_source_path"
    target: "/c/path/to/target/"
    tar_dereference: true
    rm: true

🗝️ SSH 密钥设置

  1. 生成 SSH 密钥(在本地执行):

    # RSA
    ssh-keygen -t rsa -b 4096 -C "your_email@example.com"
    # ED25519
    ssh-keygen -t ed25519 -a 200 -C "your_email@example.com"
    
  2. 将公钥添加到服务器

    cat .ssh/id_rsa.pub | ssh user@host 'cat >> .ssh/authorized_keys'
    # 或 ed25519
    cat .ssh/id_ed25519.pub | ssh user@host 'cat >> .ssh/authorized_keys'
    
  3. 将私钥内容复制到 GitHub Secrets

    clip < ~/.ssh/id_rsa
    # 或
    clip < ~/.ssh/id_ed25519
    

更多细节请参考 SSH 免密登录

OpenSSH 注意事项:
如遇到 ssh: handshake failed: ssh: unable to authenticate, attempted methods [none publickey],请确认密钥算法已被支持。
Ubuntu 20.04+ 可在 /etc/ssh/sshd_config/etc/ssh/sshd_config.d/ 添加:

CASignatureAlgorithms +ssh-rsa

或使用 ed25519 密钥(默认支持)。


🧰 常见错误代码

错误代码 可能原因 解决方法
ECONNREFUSED 端口错误/防火墙阻挡 检查端口和防火墙设置
ENOENT 找不到源文件 使用绝对路径或检查 checkout 步骤
EAUTH 认证失败 检查密钥格式和权限(需 PEM 格式)

🔄 工作流程图

sequenceDiagram
    participant G as GitHub Runner
    participant S as Target Server
    G->>S: 建立 SSH 连接
    S-->>G: 验证凭证
    G->>S: (可选)移除目标目录
    G->>G: 打包源文件
    G->>S: 传输打包文件
    S->>S: 解压和处理文件
    S-->>G: 返回结果

FAQ 与故障排查

  • Q: 为什么认证失败?
    A: 请检查 SSH 密钥格式、权限,以及密钥是否已添加到服务器。

  • Q: 如何只复制变更文件?
    A: 使用 tj-actions/changed-files 获取变更文件并传递给 source

  • Q: 如何部署到多台服务器?
    A: host 参数用逗号分隔多台主机,例如:host: "foo.com,bar.com"

  • Q: 如何复制到 Windows
    A: 设置 Git Bash使用类 Unix 路径,并启用 tar_dereference


📝 许可证

MIT License