X-Git-Url: http://www.git.cypherpunks.ru/?a=blobdiff_plain;f=fileutils.go;fp=fileutils.go;h=70d3f1123840718924d05f4817cdabdcf6034aa6;hb=b036ee436eb9bd8889734232a22d3f24be5c9ee2;hp=0000000000000000000000000000000000000000;hpb=11d218004e3a2668985a6d9b2628cb4b3fdc0051;p=gocheese.git diff --git a/fileutils.go b/fileutils.go new file mode 100644 index 0000000..70d3f11 --- /dev/null +++ b/fileutils.go @@ -0,0 +1,67 @@ +/* +GoCheese -- Python private package repository and caching proxy +Copyright (C) 2019 Sergey Matveev + +This program is free software: you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation, version 3 of the License. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program. If not, see . +*/ + +package main + +import ( + "os" + "path/filepath" + "strconv" + "time" +) + +func TempFile(dir string) (*os.File, error) { + // Assume that probability of suffix collision is negligible + suffix := strconv.FormatInt(time.Now().UnixNano()+int64(os.Getpid()), 16) + name := filepath.Join(dir, "nncp"+suffix) + return os.OpenFile(name, os.O_RDWR|os.O_CREATE|os.O_EXCL, os.FileMode(0666)) +} + +func DirSync(dirPath string) error { + fd, err := os.Open(dirPath) + if err != nil { + return err + } + err = fd.Sync() + if err != nil { + fd.Close() + return err + } + return fd.Close() +} + +func WriteFileSync(dirPath, filePath string, data []byte) error { + dst, err := TempFile(dirPath) + if err != nil { + return err + } + if _, err = dst.Write(data); err != nil { + os.Remove(dst.Name()) + dst.Close() + return err + } + if err = dst.Sync(); err != nil { + os.Remove(dst.Name()) + dst.Close() + return err + } + dst.Close() + if err = os.Rename(dst.Name(), filePath); err != nil { + return err + } + return DirSync(dirPath) +}