本文介绍如何在 go 中绕过 shell 命令拼接,直接通过 os.open 读取本地公钥文件并以标准输入(stdin)方式传输至远程服务器的 authorized_keys,避免 shell 注入、路径错误与跨平台兼容性问题。 本文介绍如何在 go 中绕过 shell 命令拼接,直接通过 os.open 读取本地公钥文件并以标准输入(stdin)方式传输至远程服务器的 authorized_keys,避免 shell 注入、路径错误与跨平台兼容性问题。在自动化部署或基础设施管理场景中,经常需要通过 Go 程序将本地生成的 SSH 公钥安全地追加到远程 Linux/macOS 服务器的 ~/.ssh/authorized_keys 文件中。许多开发者最初尝试用 exec.Command 模拟终端管道命令(如 cat key.pub | ssh user@host 'cat >> ~/.ssh/authorized_keys'),但这种方式存在严重缺陷:不仅因字符串拼接易引发 shell 注入和路径解析错误(如示例中误写为 ~/.shh/authorized_keys),更因 exec.Command 的参数传递机制不支持 Unix 管道符 | ------ 它只会把整个字符串当作单一命令名执行,导致运行失败。正确的做法是解耦「读取」与「传输」逻辑:由 Go 直接打开公钥文件,再将其作为 stdin 注入 ssh 子进程。这样既规避了 shell 解析依赖,又确保了二进制安全传输(无换行截断、编码失真风险),且天然兼容 macOS、Linux 等不同系统。以下为推荐实现方案:import ( "log" "os" "os/exec" "path/filepath")func copySSHPubKeyToServer(pubKeyPath, userAtHost string) error { // 1. 安全读取公钥文件(自动处理路径) absPath, err := filepath.Abs(pubKeyPath) if err != nil { return err } file, err := os.Open(absPath) if err != nil { return err } defer file.Close() // 2. 构建 ssh 命令:注意目标路径应为 ~/.ssh/authorized_keys(非 .shh!) cmd := exec.Command("ssh", userAtHost, "mkdir -p ~/.ssh && cat >> ~/.ssh/authorized_keys") cmd.Stdin = file // 3. 执行并捕获输出(便于调试) output, err := cmd.CombinedOutput() if err != nil { log.Printf("SSH command failed: %s", string(output)) return err } return nil}// 使用示例func main() { homeDir := fileUtil.FindUserHomeDir() // 假设该工具函数已定义 pubKeyPath := filepath.Join(homeDir, ".ssh", "foobar.pub") userAtHost := "alice@example.com" if err := copySSHPubKeyToServer(pubKeyPath, userAtHost); err != nil { log.Fatal("Failed to install SSH key:", err) } log.Println("SSH public key successfully installed.")}? 关键优势说明: 幻导航网 发现优质实用网站,开启网络探索之旅!
相关推荐
东北小狐狸-Hellxz35 分钟前
Redis 哨兵搭建+ACL权限控制测试秃头怪44 分钟前
如何评估自动化测试脚本的编写时间和维护工作量?姚青&1 小时前
测试左移体系技术民工之路1 小时前
Python Socket编程零基础实战教程(TCP/UDP通信完整版)EW Frontier1 小时前
三级跳突破864维动作空间——QMIX-Hierarchical多无人机协同通信方法全解析【附python代码】研究员子楚2 小时前
GEO行业发展标准体系白皮书V2.0-第09卷 · 适配篇:硅基主权伦理宪章与行业适配宣言中微极客2 小时前
TensorFlow模型量化实战:从精度到延迟的优化指南老毛肚3 小时前
juc线程通信l134062082353 小时前
鸿蒙实战:RDB 数据库设计与 DatabaseService