package main import ( "flag" "fmt" "net/rpc" "os" "path/filepath" "scalib/util" "strings" "go.uber.org/zap" ) // FileInfo 包含文件的元信息 type FileInfo struct { FileName string FileSize int64 } // 客户端 type UpFileClient struct { rpcClient *rpc.Client } // todo 后续增加安全验证 // 使用方法 eg: ./scalib -h 192.168.66.92:9098 -f /www/gfs/sync_zips/BIU_20251009_153640.zip /www/afs/logs/ // 主入口 func main() { // 启用日志 logger := util.NewProductionLogger() defer logger.Sync() // 使用flag解析命令行参数 remote := flag.String("h", "", "The remote server address (ip:port)") curPath := flag.String("f", "", "The local file path to upload") uploadPath := flag.String("u", "", "The remote upload path") flag.Parse() // 将服务器的信息拆分为ip和端口 harr := strings.Split(*remote, ":") dstip := harr[0] dport := harr[1] // 连接到RPC服务器 service := fmt.Sprintf("%v:%v", dstip, dport) client, err := NewUpFileClient(service) if err != nil { logger.Error("NewUpFileClient failed", zap.Error(err)) } defer client.rpcClient.Close() // 调用 transferFile err = transferFile(client, *curPath, *uploadPath) if err != nil { logger.Error("TransferFile failed", zap.Error(err)) fmt.Printf("TransferFile failed: %v\n", err) } fmt.Printf("TransferFile success\n") } // 创建新的客户端 func NewUpFileClient(addr string) (*UpFileClient, error) { client, err := rpc.Dial("tcp", addr) if err != nil { return nil, err } return &UpFileClient{rpcClient: client}, nil } // 传输文件 func transferFile(c *UpFileClient, curPath string, uploadPath string) error { // 发送文件信息 fmt.Printf("TransferFile filePath: %s, uploadPath: %s\n", curPath, uploadPath) // 获取文件信息 fileInfo, err := os.Stat(curPath) if err != nil { // panic(err) fmt.Printf("获取文件信息失败: %v\n", err) return err } // 提取文件名 // 远程的文件名 fileName := filepath.Base(uploadPath) fmt.Printf("fileName: %s\n", fileName) // 远程服务器的路径 dirpath := filepath.Dir(uploadPath) fmt.Printf("remote dirpath: %s\n", dirpath) fmt.Printf("file size: %d\n", fileInfo.Size()) // 异步 go func() { // 发送文件信息 var reply string c.rpcClient.Call("UpFileService.SendFileInfo", FileInfo{ FileName: uploadPath, FileSize: fileInfo.Size(), }, &reply) // 输出执行的结果 fmt.Printf("SendFileInfo result: %v\n", reply) }() return nil }