【运维实战】企业级SFTP 文件服务 · 一键自动化部署方案 (适配AnolisOS /openEuler /CentOS)

企业 SFTP 服务一键部署:基于 OpenSSH 实现部门隔离与国产化适配

在国产操作系统替代浪潮中,如何快速搭建安全、可控的文件共享服务?本文分享一套自动化部署方案,实现"开箱即用"的 SFTP 服务。

一、业务背景:国产化替代下的文件共享难题

随着信创产业加速落地,越来越多的政府、金融、能源企业将原有 CentOS 迁移至国产 Linux 发行版,如 Anolis OS、openEuler、Rocky Linux、AlmaLinux 等。在这些环境中,常见的商业文件共享软件(如 Serv-U、WS_FTP)要么授权昂贵,要么对国产系统支持不佳。而传统的 FTP 协议明文传输、防火墙配置复杂,已逐渐被企业安全策略淘汰。

SFTP(SSH File Transfer Protocol) 凭借其基于 SSH 的加密通道、简单开放端口(22)、天然支持 Linux 权限模型等优势,成为内部文件共享的首选方案。然而,手工配置 SFTP 的 Chroot 隔离、多部门用户管理、SELinux 策略等步骤繁琐且易错,急需一套自动化工具。

二、需求分析与痛点识别

在与多家企业运维团队沟通后,我们归纳出以下核心需求与痛点:

需求点 具体描述 手工配置痛点
部门隔离 不同部门(行政、市场、设计、研发)的文件互相不可见 需逐一配置 ChrootDirectory,修改 Match Group 块
用户权限精细 同一部门内用户可共享可写目录,且用户仅能 SFTP 不能 SSH 需设置 shell 为 /sbin/nologin,配置家目录与属主
快速批量创建 一次性创建数十个用户并分配密码 手工 useradd + chpasswd 效率极低,密码管理混乱
国产系统兼容 在 Anolis OS、openEuler 等系统上无报错运行 不同发行版的 SELinux 布尔值名称、服务管理存在差异
可重复执行 部署脚本应幂等,支持后续增加用户或重置 缺乏标准化,二次维护成本高

基于以上痛点,我们设计了一套 一键式 SFTP 部署脚本,并已在阜阳云动科技内部及多家客户环境验证。

三、方案设计:打造"一键式"SFTP 服务端部署脚本

3.1 技术选型

  • 底层服务 :OpenSSH 自带的 internal-sftp(无需额外安装 vsftpd 或 proftpd)
  • 隔离机制 :Chroot 目录 + 专用系统组(sftp-*
  • 自动化工具:Bash 脚本,兼容 systemd、firewalld、SELinux
  • 密码策略 :初始明文密码在脚本中定义,首次登录强制修改(生产环境建议结合 chage

3.2 目录结构设计

复制代码
/srv/sftp/                     # SFTP 根目录(所有部门)
├── admin/                     # 行政部
│   └── files/                 # 可写子目录(用户实际家目录)
├── market/                    # 市场部
│   └── files/
├── design/                    # 设计部
│   └── files/
└── develop/                   # 研发部
    └── files/
  • Chroot 原理 :用户登录后,/ 被映射为 /srv/sftp/部门名,因此用户只能看到 /files 目录。
  • 权限设计
    • 部门根目录(如 /srv/sftp/admin)属主 root:root,权限 755 → 用户无法在此创建文件。
    • 可写子目录 /files 属主 root:sftp-admin,权限 775 → 用户可读写,同组用户可共享。

3.3 用户与组映射

脚本内置了 4 个部门、10 个虚拟用户(可根据实际修改):

  • 行政部:admin01, admin02
  • 市场部:market01, market02, market03
  • 设计部:design01, design02
  • 研发部:develop01, develop02, develop03

每个用户属于对应部门组,家目录指向 /部门根目录/files,Shell 禁用。

3.4 核心安全加固

  • 禁止 root 登录(PermitRootLogin no
  • 仅允许密码认证(可后续开启密钥)
  • 禁用 TCP 转发、X11 转发
  • 配置 SELinux 布尔值:ssh_sysadm_loginsftp_enable_homedirssshd_enable_password_auth

四、脚本核心代码节选(完整版见文末)

由于篇幅限制,以下展示脚本中最关键的几个函数:

4.1 部门目录与组创建

bash 复制代码
create_dept_structure() {
    DEPTS=("admin" "market" "design" "develop")
    for dept in "${DEPTS[@]}"; do
        groupadd "sftp-$dept" || true
        DEPT_ROOT="$SFTP_ROOT/$dept"
        mkdir -p "$DEPT_ROOT"
        chown root:root "$DEPT_ROOT"
        chmod 755 "$DEPT_ROOT"
        
        FILES_DIR="$DEPT_ROOT/files"
        mkdir -p "$FILES_DIR"
        chown "root:sftp-$dept" "$FILES_DIR"
        chmod 775 "$FILES_DIR"
    done
}

4.2 批量用户创建

bash 复制代码
declare -A USERS=(
    ["admin01"]="admin01@pwd"
    ["market01"]="market01@pwd"
    # ...
)
declare -A DEPARTMENTS=(
    ["admin01"]="admin"
    ["market01"]="market"
    # ...
)

create_sftp_users() {
    for user in "${!USERS[@]}"; do
        dept="${DEPARTMENTS[$user]}"
        group="sftp-$dept"
        useradd -g "$group" -d "$SFTP_ROOT/$dept/files" -s /sbin/nologin -M "$user"
        echo "$user:${USERS[$user]}" | chpasswd
    done
}

4.3 sshd_config 动态配置

bash 复制代码
cat >> /etc/ssh/sshd_config << EOF
Subsystem sftp internal-sftp

Match Group sftp-admin
    ChrootDirectory /srv/sftp/admin
    ForceCommand internal-sftp -d /files
    AllowTcpForwarding no
    X11Forwarding no
# ... 其他部门类似
EOF

4.4 SELinux 策略适配

bash 复制代码
if [ "$(getenforce)" = "Enforcing" ]; then
    setsebool -P ssh_sysadm_login on
    setsebool -P sftp_enable_homedirs on
    setsebool -P sshd_enable_password_auth on
fi

五、部署效果演示(成功输出摘要)

在一台 Anolis OS 8.9 服务器上执行脚本后,输出摘要如下:

复制代码
[root@MiWiFi-RA70-srv ~]# ./install-sftp.sh
╔══════════════════════════════════════════════════════════════╗
║           企业级 SFTP 一键部署脚本 (Chroot 隔离版)           ║
║               基于 OpenSSH - 支持 RHEL 8/9 及衍生版          ║
╚══════════════════════════════════════════════════════════════╝

[STEP 0] 检查系统权限...
2026-04-16 03:26:10 - 系统权限检查通过
  └─ [✓] root 权限验证成功
[STEP 1] 检测系统类型和版本...
2026-04-16 03:26:10 - 检测到系统: Anolis OS 8.10 (rpm_based)
  └─ [✓] 检测到系统: Anolis OS 8.10
  └─ [✓] 包管理器: dnf
[STEP 2] 安装 OpenSSH 服务器...
  └─ [✓] OpenSSH 服务已就绪
2026-04-16 03:26:13 - OpenSSH 服务安装/检查完成
[STEP 3] 创建部门组和目录结构...
2026-04-16 03:26:13 - 创建组 sftp-admin
2026-04-16 03:26:13 - 部门目录创建: /srv/sftp/admin
2026-04-16 03:26:13 - 创建组 sftp-market
2026-04-16 03:26:13 - 部门目录创建: /srv/sftp/market
2026-04-16 03:26:13 - 创建组 sftp-design
2026-04-16 03:26:13 - 部门目录创建: /srv/sftp/design
2026-04-16 03:26:13 - 创建组 sftp-develop
2026-04-16 03:26:13 - 部门目录创建: /srv/sftp/develop
  └─ [✓] 部门组和目录结构创建完成
[STEP 4] 创建 SFTP 用户并设置密码...
2026-04-16 03:26:13 - 创建用户 admin01 (部门: admin)
2026-04-16 03:26:13 - 设置密码 for admin01
2026-04-16 03:26:14 - 创建用户 admin02 (部门: admin)
2026-04-16 03:26:14 - 设置密码 for admin02
2026-04-16 03:26:14 - 创建用户 market01 (部门: market)
2026-04-16 03:26:14 - 设置密码 for market01
2026-04-16 03:26:14 - 创建用户 market02 (部门: market)
2026-04-16 03:26:14 - 设置密码 for market02
2026-04-16 03:26:14 - 创建用户 market03 (部门: market)
2026-04-16 03:26:14 - 设置密码 for market03
2026-04-16 03:26:14 - 创建用户 develop03 (部门: develop)
2026-04-16 03:26:14 - 设置密码 for develop03
2026-04-16 03:26:14 - 创建用户 develop02 (部门: develop)
2026-04-16 03:26:14 - 设置密码 for develop02
2026-04-16 03:26:14 - 创建用户 develop01 (部门: develop)
2026-04-16 03:26:15 - 设置密码 for develop01
2026-04-16 03:26:15 - 创建用户 design02 (部门: design)
2026-04-16 03:26:15 - 设置密码 for design02
2026-04-16 03:26:15 - 创建用户 design01 (部门: design)
2026-04-16 03:26:15 - 设置密码 for design01
  └─ [✓] SFTP 用户创建完成
[STEP 5] 备份原始 SSH 配置文件...
  └─ [✓] 已备份至 /etc/ssh/sshd_config.bak_20260416
2026-04-16 03:26:15 - SSH 配置文件备份完成
[STEP 6] 配置 SSH 守护进程 (SFTP + Chroot)...
  └─ [✓] sshd_config 语法正确
2026-04-16 03:26:15 - sshd_config 配置完成
[STEP 7] 配置防火墙规则...
  └─ [WARN] firewalld 未运行,请手动确保端口 22 开放
2026-04-16 03:26:15 - 防火墙配置完成
[STEP 8] 配置 SELinux 策略...
  └─ [INFO] SELinux 未处于强制模式,跳过
2026-04-16 03:26:15 - SELinux 配置完成
[STEP 9] 重启 SSH 服务...
  └─ [✓] SSH 服务重启成功
2026-04-16 03:26:17 - SSH 服务重启完成
[STEP 10] 验证 SFTP 服务配置...
  ├─ [✓] SSH 服务状态: active
  ├─ [✓] 端口 22 监听: 是
  └─ [✓] SFTP 子系统可用(internal-sftp)
2026-04-16 03:26:17 - SFTP 服务验证完成

╔══════════════════════════════════════════════════════════════╗
║                    SFTP 服务部署完成信息                     ║
╚══════════════════════════════════════════════════════════════╝

  ● 系统版本: Anolis OS 8.10
  ● SFTP 服务: OpenSSH option
  ● 根目录: /srv/sftp

┌────────────────────────────────────────────────────────────┐
│                    用户账号信息                            │
├────────────────────────────────────────────────────────────┤
用户名    密码          登录后路径
─────────────────────────────────────────────────────────────────
admin01      admin01@pwd     /files (在部门根目录下)
admin02      admin02@pwd     /files (在部门根目录下)
design01     design01@pwd    /files (在部门根目录下)
design02     design02@pwd    /files (在部门根目录下)
develop01    develop01@pwd   /files (在部门根目录下)
develop02    develop02@pwd   /files (在部门根目录下)
develop03    develop03@pwd   /files (在部门根目录下)
market01     market01@pwd    /files (在部门根目录下)
market02     market02@pwd    /files (在部门根目录下)
market03     market03@pwd    /files (在部门根目录下)
└────────────────────────────────────────────────────────────┘

┌────────────────────────────────────────────────────────────┐
│                    网络访问信息                            │
├────────────────────────────────────────────────────────────┤
│ SFTP 地址: sftp://192.168.31.33:22                        │
│ 客户端: FileZilla, WinSCP, 命令行 sftp user@IP                  │
└────────────────────────────────────────────────────────────┘

┌────────────────────────────────────────────────────────────┐
│                    服务管理                                │
├────────────────────────────────────────────────────────────┤
│ systemctl start|stop|restart|status sshd                  │
└────────────────────────────────────────────────────────────┘

┌────────────────────────────────────────────────────────────┐
│                    目录结构                                │
├────────────────────────────────────────────────────────────┤
│ /srv/sftp/admin/files   - 行政部可写区域                  │
│ /srv/sftp/market/files  - 市场部可写区域                  │
│ /srv/sftp/design/files  - 设计部可写区域                  │
│ /srv/sftp/develop/files - 研发部可写区域                  │
└────────────────────────────────────────────────────────────┘

┌────────────────────────────────────────────────────────────┐
│                    安全提醒                                │
├────────────────────────────────────────────────────────────┤
│ 1. 所有用户已禁用 shell,仅允许 SFTP 登录                  │
│ 2. 用户被 chroot 到部门根目录,无法访问系统文件           │
│ 3. 定期修改用户密码:passwd <用户名>                       │
│ 4. 查看登录日志:journalctl -u sshd -f                     │
└────────────────────────────────────────────────────────────┘

✅ 企业级 SFTP 服务部署完成!
安装日志: /var/log/sftp_deploy_20260416_032610.log

验证测试 :使用 sftp market01@服务器IP 登录,执行 pwd 显示 /files,尝试 ls / 只能看到 files 目录,无法访问系统文件,隔离生效。

六、后期维护建议(由阜阳云动科技提供)

脚本部署完成后,日常运维仍需关注以下几点:

6.1 用户增删改

  • 新增用户 :手动编辑脚本中的 USERSDEPARTMENTS 数组,重新执行脚本(已有用户会跳过,新用户被创建)。
  • 删除用户userdel -r 用户名,同时清理 USERS 数组避免误重建。
  • 重置密码passwd 用户名echo "新密码" | chpasswd

6.2 磁盘空间与日志

  • 定期清理 /srv/sftp/*/files 中的过期文件,可配合 tmpwatchcron 任务。
  • SFTP 传输日志:journalctl -u sshd -f | grep "sftp"
  • 审计用户登录:last | grep sftp

6.3 安全加固进阶

  • 禁用密码,改用密钥认证 :修改 /etc/ssh/sshd_configPasswordAuthentication no,并为每个用户配置 AuthorizedKeysFile
  • 限制用户传输速率 :在 Match Group 块中添加 SftpRateLimit(需 OpenSSH 9.0+,或使用 tc 限流)。
  • IP 白名单 :通过 sshd_configAllowUsersMatch Address 实现。

6.4 备份与恢复

  • 备份目录:tar czf sftp_backup.tar.gz /srv/sftp /etc/ssh/sshd_config
  • 恢复时先解压目录,再重启 sshd,注意检查 SELinux 上下文:restorecon -Rv /srv/sftp

6.5 跨部门文件共享

当前设计部门之间天然隔离。若需跨部门读写(如设计部向市场部交付素材),可考虑:

  • 创建公共组 sftp-share,在某个部门下建立子目录,属组改为 sftp-share
  • 或使用软链接(注意 Chroot 环境内软链接不能指向外部,需使用 mount --bind)。

脚本完整版获取 :关注账号,回复 SFTP一键部署 即可下载。
技术支持:如遇国产系统兼容性问题(统信 UOS、麒麟等),欢迎联系我们获取适配版本。

阜阳云动科技有限公司,专注于系统运维、服务器网络、安全及 AI 大模型落地。我们坚信:好的运维工具,应该让复杂变简单

相关推荐
Agent手记18 小时前
供应商资质智能审核自动化、落地方法与合规校验方案:AGI时代下的企业级风控重塑
运维·人工智能·ai·自动化·agi
神奇椰子19 小时前
Linux系统更换软件源说明文档
linux·运维·服务器
ITyunwei098719 小时前
数字化转型与遗留系统:如何为老旧的IT系统“减负“并注入新活力?
运维·网络·数据库
Python私教19 小时前
跨境电商浏览器自动化:Claude Code 集成 AdsPower MCP 实战
运维·自动化
风曦Kisaki20 小时前
#Linux Shell 编程入门 Day05 :awk文本数据处理基础
linux·运维
挨踢学霸20 小时前
MsgHelper 5.0 全新发布:微信群发+微信群发群双引擎,按标签群发/定时群发/多于500人群发,数据本地化守护企业隐私安全
人工智能·安全·微信·自动化
wanhengidc20 小时前
BGP服务器的功能是什么
运维·服务器·安全·web安全·智能手机
剑神一笑20 小时前
Linux tree 命令深度解析:从目录遍历到树形可视化的完整实现
linux·运维·elasticsearch
小小的木头人20 小时前
Docker Compose 镜像检测脚本(支持自动扫描 + 手动输入 YAML)
运维·docker·容器
夏日听雨眠20 小时前
Linux(printf函数输出问题,exit ,主函数参数,fork函数,文件系统调用)
linux·运维·服务器