目录
复制文件
方式1:通过内置包文件操作实现
方式2:通过exec包实现
移动文件
方式1:通过内置包文件操作实现
方式2:通过exec包实现
提示
func CopyFile(src, dst string) (size int64, err error) {
fmt.Printf("ready copy '%s' to '%s'\n", src, dst)
srcFile, err := os.OpenFile(src, os.O_RDONLY, 0644)
if err != nil {
err = fmt.Errorf("failed to open source file: %v", err)
return
}
defer srcFile.Close()
info, err := srcFile.Stat()
if err != nil {
err = fmt.Errorf("failed to get file info: %v\n", err)
return
}
size = info.Size()
if info.IsDir() {
err = fmt.Errorf("source is a directory, does not support copying directories recursively.")
return
}
dstFile, err := createFile(dst, info)
if err != nil {
err = errors.New(fmt.Sprintf("failed to create destination file: %v", err))
return
}
defer dstFile.Close()
_, err = io.Copy(dstFile, srcFile)
if err != nil {
err = fmt.Errorf(fmt.Sprintf("failed to copy file: %v\n", err))
return
}
fmt.Printf("successfully copied '%s' to '%s'\n", src, dst)
return
}
func createFile(dst string, info os.FileInfo) (*os.File, error) {
dir := filepath.Dir(dst)
err := os.MkdirAll(dir, os.ModePerm)
if err != nil {
return nil, fmt.Errorf("failed to create destination directory: %w", err)
}
dstFile, err := os.Create(dst)
if err != nil {
return nil, fmt.Errorf("failed to create destination file: %w", err)
}
err = dstFile.Chmod(info.Mode())
if err != nil {
dstFile.Close()
return nil, fmt.Errorf("failed to set destination file permissions: %w", err)
}
return dstFile, nil
}
封装执行简单命令的函数:
func Exec(name string, args ...string) (outString string, err error) {
var out bytes.Buffer
var stderr bytes.Buffer
cmd := exec.Command(name, args...)
cmd.Stdout = &out
cmd.Stderr = &stderr
err = cmd.Run()
outString = out.String()
if err != nil {
err = fmt.Errorf("exec failed: %v, stderr=%s. name=%s, args=%v.", err, stderr.String(), name, args)
}
return
}
使用:
_, err = Exec("cp", src, dst)
即可完成文件复制。
func Move(src, dst string) error {
return os.Rename(src, dst)
}
_, err = Exec("mv", src, dst)
目标目录不存在时,通过exec.Command的方式执行cp、mv会报错,因此需要提前准备好目的目录。