diff options
| author | Mitja Felicijan <mitja.felicijan@gmail.com> | 2024-10-25 00:47:47 +0200 |
|---|---|---|
| committer | Mitja Felicijan <mitja.felicijan@gmail.com> | 2024-10-25 00:47:47 +0200 |
| commit | c6cc0108ca7738023b45e0eeac0fa2390532dd93 (patch) | |
| tree | 36890e6cd3091bbab8efbe686cc56f467f645bfd /vendor/github.com/otiai10/copy | |
| parent | 0130404a1dc663d4aa68d780c9bcb23a4243e68d (diff) | |
| download | jbmafp-master.tar.gz | |
Diffstat (limited to 'vendor/github.com/otiai10/copy')
24 files changed, 907 insertions, 0 deletions
diff --git a/vendor/github.com/otiai10/copy/.gitignore b/vendor/github.com/otiai10/copy/.gitignore new file mode 100644 index 0000000..a793485 --- /dev/null +++ b/vendor/github.com/otiai10/copy/.gitignore @@ -0,0 +1,9 @@ +test/data.copy +test/owned-by-root +coverage.txt +vendor +.vagrant +.idea/ + +# Test Specific +test/data/case16/large.file diff --git a/vendor/github.com/otiai10/copy/LICENSE b/vendor/github.com/otiai10/copy/LICENSE new file mode 100644 index 0000000..1f0cc5d --- /dev/null +++ b/vendor/github.com/otiai10/copy/LICENSE @@ -0,0 +1,21 @@ +The MIT License (MIT) + +Copyright (c) 2018 otiai10 + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/vendor/github.com/otiai10/copy/README.md b/vendor/github.com/otiai10/copy/README.md new file mode 100644 index 0000000..1cc8fc8 --- /dev/null +++ b/vendor/github.com/otiai10/copy/README.md @@ -0,0 +1,108 @@ +# copy + +[](https://pkg.go.dev/github.com/otiai10/copy) +[](https://github.com/otiai10/copy/actions) +[](https://codecov.io/gh/otiai10/copy) +[](https://github.com/otiai10/copy/blob/main/LICENSE) +[](https://app.fossa.com/projects/git%2Bgithub.com%2Fotiai10%2Fcopy?ref=badge_shield) +[](https://github.com/otiai10/copy/actions/workflows/codeql-analysis.yml) +[](https://goreportcard.com/report/github.com/otiai10/copy) +[](https://pkg.go.dev/github.com/otiai10/copy) +[](https://github.com/otiai10/copy/actions/workflows/docker-test.yml) +[](https://github.com/otiai10/copy/actions/workflows/vagrant-test.yml) + +`copy` copies directories recursively. + +# Example Usage + +```go +package main + +import ( + "fmt" + cp "github.com/otiai10/copy" +) + +func main() { + err := cp.Copy("your/src", "your/dest") + fmt.Println(err) // nil +} +``` + +# Advanced Usage + +```go +// Options specifies optional actions on copying. +type Options struct { + + // OnSymlink can specify what to do on symlink + OnSymlink func(src string) SymlinkAction + + // OnDirExists can specify what to do when there is a directory already existing in destination. + OnDirExists func(src, dest string) DirExistsAction + + // OnError can let users decide how to handle errors (e.g., you can suppress specific error). + OnError func(src, dest, string, err error) error + + // Skip can specify which files should be skipped + Skip func(srcinfo os.FileInfo, src, dest string) (bool, error) + + // PermissionControl can control permission of + // every entry. + // When you want to add permission 0222, do like + // + // PermissionControl = AddPermission(0222) + // + // or if you even don't want to touch permission, + // + // PermissionControl = DoNothing + // + // By default, PermissionControl = PreservePermission + PermissionControl PermissionControlFunc + + // Sync file after copy. + // Useful in case when file must be on the disk + // (in case crash happens, for example), + // at the expense of some performance penalty + Sync bool + + // Preserve the atime and the mtime of the entries + // On linux we can preserve only up to 1 millisecond accuracy + PreserveTimes bool + + // Preserve the uid and the gid of all entries. + PreserveOwner bool + + // The byte size of the buffer to use for copying files. + // If zero, the internal default buffer of 32KB is used. + // See https://golang.org/pkg/io/#CopyBuffer for more information. + CopyBufferSize uint + + // If you want to add some limitation on reading src file, + // you can wrap the src and provide new reader, + // such as `RateLimitReader` in the test case. + WrapReader func(src io.Reader) io.Reader + + // If given, copy.Copy refers to this fs.FS instead of the OS filesystem. + // e.g., You can use embed.FS to copy files from embedded filesystem. + FS fs.FS +} +``` + +```go +// For example... +opt := Options{ + Skip: func(info os.FileInfo, src, dest string) (bool, error) { + return strings.HasSuffix(src, ".git"), nil + }, +} +err := Copy("your/directory", "your/directory.copy", opt) +``` + +# Issues + +- https://github.com/otiai10/copy/issues + + +## License +[](https://app.fossa.com/projects/git%2Bgithub.com%2Fotiai10%2Fcopy?ref=badge_large)
\ No newline at end of file diff --git a/vendor/github.com/otiai10/copy/copy.go b/vendor/github.com/otiai10/copy/copy.go new file mode 100644 index 0000000..085db78 --- /dev/null +++ b/vendor/github.com/otiai10/copy/copy.go @@ -0,0 +1,284 @@ +package copy + +import ( + "io" + "io/fs" + "io/ioutil" + "os" + "path/filepath" + "time" +) + +type timespec struct { + Mtime time.Time + Atime time.Time + Ctime time.Time +} + +// Copy copies src to dest, doesn't matter if src is a directory or a file. +func Copy(src, dest string, opts ...Options) error { + opt := assureOptions(src, dest, opts...) + if opt.FS != nil { + info, err := fs.Stat(opt.FS, src) + if err != nil { + return onError(src, dest, err, opt) + } + return switchboard(src, dest, info, opt) + } + info, err := os.Lstat(src) + if err != nil { + return onError(src, dest, err, opt) + } + return switchboard(src, dest, info, opt) +} + +// switchboard switches proper copy functions regarding file type, etc... +// If there would be anything else here, add a case to this switchboard. +func switchboard(src, dest string, info os.FileInfo, opt Options) (err error) { + if info.Mode()&os.ModeDevice != 0 && !opt.Specials { + return onError(src, dest, err, opt) + } + + switch { + case info.Mode()&os.ModeSymlink != 0: + err = onsymlink(src, dest, opt) + case info.IsDir(): + err = dcopy(src, dest, info, opt) + case info.Mode()&os.ModeNamedPipe != 0: + err = pcopy(dest, info) + default: + err = fcopy(src, dest, info, opt) + } + + return onError(src, dest, err, opt) +} + +// copyNextOrSkip decide if this src should be copied or not. +// Because this "copy" could be called recursively, +// "info" MUST be given here, NOT nil. +func copyNextOrSkip(src, dest string, info os.FileInfo, opt Options) error { + if opt.Skip != nil { + skip, err := opt.Skip(info, src, dest) + if err != nil { + return err + } + if skip { + return nil + } + } + return switchboard(src, dest, info, opt) +} + +// fcopy is for just a file, +// with considering existence of parent directory +// and file permission. +func fcopy(src, dest string, info os.FileInfo, opt Options) (err error) { + + var readcloser io.ReadCloser + if opt.FS != nil { + readcloser, err = opt.FS.Open(src) + } else { + readcloser, err = os.Open(src) + } + if err != nil { + if os.IsNotExist(err) { + return nil + } + return + } + defer fclose(readcloser, &err) + + if err = os.MkdirAll(filepath.Dir(dest), os.ModePerm); err != nil { + return + } + + f, err := os.Create(dest) + if err != nil { + return + } + defer fclose(f, &err) + + chmodfunc, err := opt.PermissionControl(info, dest) + if err != nil { + return err + } + chmodfunc(&err) + + var buf []byte = nil + var w io.Writer = f + var r io.Reader = readcloser + + if opt.WrapReader != nil { + r = opt.WrapReader(r) + } + + if opt.CopyBufferSize != 0 { + buf = make([]byte, opt.CopyBufferSize) + // Disable using `ReadFrom` by io.CopyBuffer. + // See https://github.com/otiai10/copy/pull/60#discussion_r627320811 for more details. + w = struct{ io.Writer }{f} + // r = struct{ io.Reader }{s} + } + + if _, err = io.CopyBuffer(w, r, buf); err != nil { + return err + } + + if opt.Sync { + err = f.Sync() + } + + if opt.PreserveOwner { + if err := preserveOwner(src, dest, info); err != nil { + return err + } + } + if opt.PreserveTimes { + if err := preserveTimes(info, dest); err != nil { + return err + } + } + + return +} + +// dcopy is for a directory, +// with scanning contents inside the directory +// and pass everything to "copy" recursively. +func dcopy(srcdir, destdir string, info os.FileInfo, opt Options) (err error) { + if skip, err := onDirExists(opt, srcdir, destdir); err != nil { + return err + } else if skip { + return nil + } + + // Make dest dir with 0755 so that everything writable. + chmodfunc, err := opt.PermissionControl(info, destdir) + if err != nil { + return err + } + defer chmodfunc(&err) + + var contents []os.FileInfo + if opt.FS != nil { + entries, err := fs.ReadDir(opt.FS, srcdir) + if err != nil { + return err + } + for _, e := range entries { + info, err := e.Info() + if err != nil { + return err + } + contents = append(contents, info) + } + } else { + contents, err = ioutil.ReadDir(srcdir) + } + + if err != nil { + if os.IsNotExist(err) { + return nil + } + return + } + + for _, content := range contents { + cs, cd := filepath.Join(srcdir, content.Name()), filepath.Join(destdir, content.Name()) + + if err = copyNextOrSkip(cs, cd, content, opt); err != nil { + // If any error, exit immediately + return + } + } + + if opt.PreserveTimes { + if err := preserveTimes(info, destdir); err != nil { + return err + } + } + + if opt.PreserveOwner { + if err := preserveOwner(srcdir, destdir, info); err != nil { + return err + } + } + + return +} + +func onDirExists(opt Options, srcdir, destdir string) (bool, error) { + _, err := os.Stat(destdir) + if err == nil && opt.OnDirExists != nil && destdir != opt.intent.dest { + switch opt.OnDirExists(srcdir, destdir) { + case Replace: + if err := os.RemoveAll(destdir); err != nil { + return false, err + } + case Untouchable: + return true, nil + } // case "Merge" is default behaviour. Go through. + } else if err != nil && !os.IsNotExist(err) { + return true, err // Unwelcome error type...! + } + return false, nil +} + +func onsymlink(src, dest string, opt Options) error { + switch opt.OnSymlink(src) { + case Shallow: + if err := lcopy(src, dest); err != nil { + return err + } + if opt.PreserveTimes { + return preserveLtimes(src, dest) + } + return nil + case Deep: + orig, err := os.Readlink(src) + if err != nil { + return err + } + info, err := os.Lstat(orig) + if err != nil { + return err + } + return copyNextOrSkip(orig, dest, info, opt) + case Skip: + fallthrough + default: + return nil // do nothing + } +} + +// lcopy is for a symlink, +// with just creating a new symlink by replicating src symlink. +func lcopy(src, dest string) error { + src, err := os.Readlink(src) + if err != nil { + if os.IsNotExist(err) { + return nil + } + return err + } + return os.Symlink(src, dest) +} + +// fclose ANYHOW closes file, +// with asiging error raised during Close, +// BUT respecting the error already reported. +func fclose(f io.Closer, reported *error) { + if err := f.Close(); *reported == nil { + *reported = err + } +} + +// onError lets caller to handle errors +// occured when copying a file. +func onError(src, dest string, err error, opt Options) error { + if opt.OnError == nil { + return err + } + + return opt.OnError(src, dest, err) +} diff --git a/vendor/github.com/otiai10/copy/copy_namedpipes.go b/vendor/github.com/otiai10/copy/copy_namedpipes.go new file mode 100644 index 0000000..615ddcd --- /dev/null +++ b/vendor/github.com/otiai10/copy/copy_namedpipes.go @@ -0,0 +1,18 @@ +//go:build !windows && !plan9 && !netbsd && !aix && !illumos && !solaris && !js +// +build !windows,!plan9,!netbsd,!aix,!illumos,!solaris,!js + +package copy + +import ( + "os" + "path/filepath" + "syscall" +) + +// pcopy is for just named pipes +func pcopy(dest string, info os.FileInfo) error { + if err := os.MkdirAll(filepath.Dir(dest), os.ModePerm); err != nil { + return err + } + return syscall.Mkfifo(dest, uint32(info.Mode())) +} diff --git a/vendor/github.com/otiai10/copy/copy_namedpipes_x.go b/vendor/github.com/otiai10/copy/copy_namedpipes_x.go new file mode 100644 index 0000000..38dd9dc --- /dev/null +++ b/vendor/github.com/otiai10/copy/copy_namedpipes_x.go @@ -0,0 +1,15 @@ +//go:build windows || plan9 || netbsd || aix || illumos || solaris || js +// +build windows plan9 netbsd aix illumos solaris js + +package copy + +import ( + "os" +) + +// TODO: check plan9 netbsd aix illumos solaris in future + +// pcopy is for just named pipes. Windows doesn't support them +func pcopy(dest string, info os.FileInfo) error { + return nil +} diff --git a/vendor/github.com/otiai10/copy/fileinfo_go1.15.go b/vendor/github.com/otiai10/copy/fileinfo_go1.15.go new file mode 100644 index 0000000..c0708ea --- /dev/null +++ b/vendor/github.com/otiai10/copy/fileinfo_go1.15.go @@ -0,0 +1,17 @@ +//go:build !go1.16 +// +build !go1.16 + +package copy + +import "os" + +// This is a cloned definition of os.FileInfo (go1.15) or fs.FileInfo (go1.16~) +// A FileInfo describes a file and is returned by Stat. +type fileInfo interface { + // Name() string // base name of the file + // Size() int64 // length in bytes for regular files; system-dependent for others + Mode() os.FileMode // file mode bits + // ModTime() time.Time // modification time + IsDir() bool // abbreviation for Mode().IsDir() + Sys() interface{} // underlying data source (can return nil) +} diff --git a/vendor/github.com/otiai10/copy/fileinfo_go1.16.go b/vendor/github.com/otiai10/copy/fileinfo_go1.16.go new file mode 100644 index 0000000..01b3fd2 --- /dev/null +++ b/vendor/github.com/otiai10/copy/fileinfo_go1.16.go @@ -0,0 +1,17 @@ +//go:build go1.16 +// +build go1.16 + +package copy + +import "io/fs" + +// This is a cloned definition of os.FileInfo (go1.15) or fs.FileInfo (go1.16~) +// A FileInfo describes a file and is returned by Stat. +type fileInfo interface { + // Name() string // base name of the file + // Size() int64 // length in bytes for regular files; system-dependent for others + Mode() fs.FileMode // file mode bits + // ModTime() time.Time // modification time + IsDir() bool // abbreviation for Mode().IsDir() + Sys() interface{} // underlying data source (can return nil) +} diff --git a/vendor/github.com/otiai10/copy/options.go b/vendor/github.com/otiai10/copy/options.go new file mode 100644 index 0000000..1b4e508 --- /dev/null +++ b/vendor/github.com/otiai10/copy/options.go @@ -0,0 +1,143 @@ +package copy + +import ( + "io" + "io/fs" + "os" +) + +// Options specifies optional actions on copying. +type Options struct { + + // OnSymlink can specify what to do on symlink + OnSymlink func(src string) SymlinkAction + + // OnDirExists can specify what to do when there is a directory already existing in destination. + OnDirExists func(src, dest string) DirExistsAction + + // OnErr lets called decide whether or not to continue on particular copy error. + OnError func(src, dest string, err error) error + + // Skip can specify which files should be skipped + Skip func(srcinfo os.FileInfo, src, dest string) (bool, error) + + // Specials includes special files to be copied. default false. + Specials bool + + // AddPermission to every entities, + // NO MORE THAN 0777 + // @OBSOLETE + // Use `PermissionControl = AddPermission(perm)` instead + AddPermission os.FileMode + + // PermissionControl can preserve or even add permission to + // every entries, for example + // + // opt.PermissionControl = AddPermission(0222) + // + // See permission_control.go for more detail. + PermissionControl PermissionControlFunc + + // Sync file after copy. + // Useful in case when file must be on the disk + // (in case crash happens, for example), + // at the expense of some performance penalty + Sync bool + + // Preserve the atime and the mtime of the entries. + // On linux we can preserve only up to 1 millisecond accuracy. + PreserveTimes bool + + // Preserve the uid and the gid of all entries. + PreserveOwner bool + + // The byte size of the buffer to use for copying files. + // If zero, the internal default buffer of 32KB is used. + // See https://golang.org/pkg/io/#CopyBuffer for more information. + CopyBufferSize uint + + // If you want to add some limitation on reading src file, + // you can wrap the src and provide new reader, + // such as `RateLimitReader` in the test case. + WrapReader func(src io.Reader) io.Reader + + // If given, copy.Copy refers to this fs.FS instead of the OS filesystem. + // e.g., You can use embed.FS to copy files from embedded filesystem. + FS fs.FS + + intent struct { + src string + dest string + } +} + +// SymlinkAction represents what to do on symlink. +type SymlinkAction int + +const ( + // Deep creates hard-copy of contents. + Deep SymlinkAction = iota + // Shallow creates new symlink to the dest of symlink. + Shallow + // Skip does nothing with symlink. + Skip +) + +// DirExistsAction represents what to do on dest dir. +type DirExistsAction int + +const ( + // Merge preserves or overwrites existing files under the dir (default behavior). + Merge DirExistsAction = iota + // Replace deletes all contents under the dir and copy src files. + Replace + // Untouchable does nothing for the dir, and leaves it as it is. + Untouchable +) + +// getDefaultOptions provides default options, +// which would be modified by usage-side. +func getDefaultOptions(src, dest string) Options { + return Options{ + OnSymlink: func(string) SymlinkAction { + return Shallow // Do shallow copy + }, + OnDirExists: nil, // Default behavior is "Merge". + OnError: nil, // Default is "accept error" + Skip: nil, // Do not skip anything + AddPermission: 0, // Add nothing + PermissionControl: PerservePermission, // Just preserve permission + Sync: false, // Do not sync + Specials: false, // Do not copy special files + PreserveTimes: false, // Do not preserve the modification time + CopyBufferSize: 0, // Do not specify, use default bufsize (32*1024) + WrapReader: nil, // Do not wrap src files, use them as they are. + intent: struct { + src string + dest string + }{src, dest}, + } +} + +// assureOptions struct, should be called only once. +// All optional values MUST NOT BE nil/zero after assured. +func assureOptions(src, dest string, opts ...Options) Options { + defopt := getDefaultOptions(src, dest) + if len(opts) == 0 { + return defopt + } + if opts[0].OnSymlink == nil { + opts[0].OnSymlink = defopt.OnSymlink + } + if opts[0].Skip == nil { + opts[0].Skip = defopt.Skip + } + if opts[0].AddPermission > 0 { + opts[0].PermissionControl = AddPermission(opts[0].AddPermission) + } else if opts[0].PermissionControl == nil { + opts[0].PermissionControl = PerservePermission + } + opts[0].intent.src = defopt.intent.src + opts[0].intent.dest = defopt.intent.dest + return opts[0] +} diff --git a/vendor/github.com/otiai10/copy/permission_control.go b/vendor/github.com/otiai10/copy/permission_control.go new file mode 100644 index 0000000..97ae12d --- /dev/null +++ b/vendor/github.com/otiai10/copy/permission_control.go @@ -0,0 +1,48 @@ +package copy + +import ( + "os" +) + +const ( + // tmpPermissionForDirectory makes the destination directory writable, + // so that stuff can be copied recursively even if any original directory is NOT writable. + // See https://github.com/otiai10/copy/pull/9 for more information. + tmpPermissionForDirectory = os.FileMode(0755) +) + +type PermissionControlFunc func(srcinfo fileInfo, dest string) (chmodfunc func(*error), err error) + +var ( + AddPermission = func(perm os.FileMode) PermissionControlFunc { + return func(srcinfo fileInfo, dest string) (func(*error), error) { + orig := srcinfo.Mode() + if srcinfo.IsDir() { + if err := os.MkdirAll(dest, tmpPermissionForDirectory); err != nil { + return func(*error) {}, err + } + } + return func(err *error) { + chmod(dest, orig|perm, err) + }, nil + } + } + PerservePermission PermissionControlFunc = AddPermission(0) + DoNothing PermissionControlFunc = func(srcinfo fileInfo, dest string) (func(*error), error) { + if srcinfo.IsDir() { + if err := os.MkdirAll(dest, srcinfo.Mode()); err != nil { + return func(*error) {}, err + } + } + return func(*error) {}, nil + } +) + +// chmod ANYHOW changes file mode, +// with asiging error raised during Chmod, +// BUT respecting the error already reported. +func chmod(dir string, mode os.FileMode, reported *error) { + if err := os.Chmod(dir, mode); *reported == nil { + *reported = err + } +} diff --git a/vendor/github.com/otiai10/copy/preserve_ltimes.go b/vendor/github.com/otiai10/copy/preserve_ltimes.go new file mode 100644 index 0000000..cc006d3 --- /dev/null +++ b/vendor/github.com/otiai10/copy/preserve_ltimes.go @@ -0,0 +1,20 @@ +//go:build !windows && !plan9 && !js +// +build !windows,!plan9,!js + +package copy + +import ( + "golang.org/x/sys/unix" +) + +func preserveLtimes(src, dest string) error { + info := new(unix.Stat_t) + if err := unix.Lstat(src, info); err != nil { + return err + } + + return unix.Lutimes(dest, []unix.Timeval{ + unix.NsecToTimeval(info.Atim.Nano()), + unix.NsecToTimeval(info.Mtim.Nano()), + }) +} diff --git a/vendor/github.com/otiai10/copy/preserve_ltimes_x.go b/vendor/github.com/otiai10/copy/preserve_ltimes_x.go new file mode 100644 index 0000000..02aec40 --- /dev/null +++ b/vendor/github.com/otiai10/copy/preserve_ltimes_x.go @@ -0,0 +1,8 @@ +//go:build windows || js || plan9 +// +build windows js plan9 + +package copy + +func preserveLtimes(src, dest string) error { + return nil // Unsupported +} diff --git a/vendor/github.com/otiai10/copy/preserve_owner.go b/vendor/github.com/otiai10/copy/preserve_owner.go new file mode 100644 index 0000000..13ec4f5 --- /dev/null +++ b/vendor/github.com/otiai10/copy/preserve_owner.go @@ -0,0 +1,23 @@ +//go:build !windows && !plan9 +// +build !windows,!plan9 + +package copy + +import ( + "os" + "syscall" +) + +func preserveOwner(src, dest string, info fileInfo) (err error) { + if info == nil { + if info, err = os.Stat(src); err != nil { + return err + } + } + if stat, ok := info.Sys().(*syscall.Stat_t); ok { + if err := os.Chown(dest, int(stat.Uid), int(stat.Gid)); err != nil { + return err + } + } + return nil +} diff --git a/vendor/github.com/otiai10/copy/preserve_owner_x.go b/vendor/github.com/otiai10/copy/preserve_owner_x.go new file mode 100644 index 0000000..9d82574 --- /dev/null +++ b/vendor/github.com/otiai10/copy/preserve_owner_x.go @@ -0,0 +1,8 @@ +//go:build windows || plan9 +// +build windows plan9 + +package copy + +func preserveOwner(src, dest string, info fileInfo) (err error) { + return nil +} diff --git a/vendor/github.com/otiai10/copy/preserve_times.go b/vendor/github.com/otiai10/copy/preserve_times.go new file mode 100644 index 0000000..d89b128 --- /dev/null +++ b/vendor/github.com/otiai10/copy/preserve_times.go @@ -0,0 +1,11 @@ +package copy + +import "os" + +func preserveTimes(srcinfo os.FileInfo, dest string) error { + spec := getTimeSpec(srcinfo) + if err := os.Chtimes(dest, spec.Atime, spec.Mtime); err != nil { + return err + } + return nil +} diff --git a/vendor/github.com/otiai10/copy/stat_times.go b/vendor/github.com/otiai10/copy/stat_times.go new file mode 100644 index 0000000..75f45f6 --- /dev/null +++ b/vendor/github.com/otiai10/copy/stat_times.go @@ -0,0 +1,22 @@ +//go:build !windows && !darwin && !freebsd && !plan9 && !netbsd && !js +// +build !windows,!darwin,!freebsd,!plan9,!netbsd,!js + +// TODO: add more runtimes + +package copy + +import ( + "os" + "syscall" + "time" +) + +func getTimeSpec(info os.FileInfo) timespec { + stat := info.Sys().(*syscall.Stat_t) + times := timespec{ + Mtime: info.ModTime(), + Atime: time.Unix(int64(stat.Atim.Sec), int64(stat.Atim.Nsec)), + Ctime: time.Unix(int64(stat.Ctim.Sec), int64(stat.Ctim.Nsec)), + } + return times +} diff --git a/vendor/github.com/otiai10/copy/stat_times_darwin.go b/vendor/github.com/otiai10/copy/stat_times_darwin.go new file mode 100644 index 0000000..d4c23d8 --- /dev/null +++ b/vendor/github.com/otiai10/copy/stat_times_darwin.go @@ -0,0 +1,20 @@ +//go:build darwin +// +build darwin + +package copy + +import ( + "os" + "syscall" + "time" +) + +func getTimeSpec(info os.FileInfo) timespec { + stat := info.Sys().(*syscall.Stat_t) + times := timespec{ + Mtime: info.ModTime(), + Atime: time.Unix(stat.Atimespec.Sec, stat.Atimespec.Nsec), + Ctime: time.Unix(stat.Ctimespec.Sec, stat.Ctimespec.Nsec), + } + return times +} diff --git a/vendor/github.com/otiai10/copy/stat_times_freebsd.go b/vendor/github.com/otiai10/copy/stat_times_freebsd.go new file mode 100644 index 0000000..5309334 --- /dev/null +++ b/vendor/github.com/otiai10/copy/stat_times_freebsd.go @@ -0,0 +1,20 @@ +//go:build freebsd +// +build freebsd + +package copy + +import ( + "os" + "syscall" + "time" +) + +func getTimeSpec(info os.FileInfo) timespec { + stat := info.Sys().(*syscall.Stat_t) + times := timespec{ + Mtime: info.ModTime(), + Atime: time.Unix(int64(stat.Atimespec.Sec), int64(stat.Atimespec.Nsec)), + Ctime: time.Unix(int64(stat.Ctimespec.Sec), int64(stat.Ctimespec.Nsec)), + } + return times +} diff --git a/vendor/github.com/otiai10/copy/stat_times_js.go b/vendor/github.com/otiai10/copy/stat_times_js.go new file mode 100644 index 0000000..c645771 --- /dev/null +++ b/vendor/github.com/otiai10/copy/stat_times_js.go @@ -0,0 +1,20 @@ +//go:build js +// +build js + +package copy + +import ( + "os" + "syscall" + "time" +) + +func getTimeSpec(info os.FileInfo) timespec { + stat := info.Sys().(*syscall.Stat_t) + times := timespec{ + Mtime: info.ModTime(), + Atime: time.Unix(int64(stat.Atime), int64(stat.AtimeNsec)), + Ctime: time.Unix(int64(stat.Ctime), int64(stat.CtimeNsec)), + } + return times +} diff --git a/vendor/github.com/otiai10/copy/stat_times_windows.go b/vendor/github.com/otiai10/copy/stat_times_windows.go new file mode 100644 index 0000000..d6a84a7 --- /dev/null +++ b/vendor/github.com/otiai10/copy/stat_times_windows.go @@ -0,0 +1,19 @@ +//go:build windows +// +build windows + +package copy + +import ( + "os" + "syscall" + "time" +) + +func getTimeSpec(info os.FileInfo) timespec { + stat := info.Sys().(*syscall.Win32FileAttributeData) + return timespec{ + Mtime: time.Unix(0, stat.LastWriteTime.Nanoseconds()), + Atime: time.Unix(0, stat.LastAccessTime.Nanoseconds()), + Ctime: time.Unix(0, stat.CreationTime.Nanoseconds()), + } +} diff --git a/vendor/github.com/otiai10/copy/stat_times_x.go b/vendor/github.com/otiai10/copy/stat_times_x.go new file mode 100644 index 0000000..886ddd3 --- /dev/null +++ b/vendor/github.com/otiai10/copy/stat_times_x.go @@ -0,0 +1,18 @@ +//go:build plan9 || netbsd +// +build plan9 netbsd + +package copy + +import ( + "os" +) + +// TODO: check plan9 netbsd in future +func getTimeSpec(info os.FileInfo) timespec { + times := timespec{ + Mtime: info.ModTime(), + Atime: info.ModTime(), + Ctime: info.ModTime(), + } + return times +} diff --git a/vendor/github.com/otiai10/copy/test/data/case18/assets/README.md b/vendor/github.com/otiai10/copy/test/data/case18/assets/README.md new file mode 100644 index 0000000..5570c7f --- /dev/null +++ b/vendor/github.com/otiai10/copy/test/data/case18/assets/README.md @@ -0,0 +1 @@ +# Hello
\ No newline at end of file diff --git a/vendor/github.com/otiai10/copy/test_setup.go b/vendor/github.com/otiai10/copy/test_setup.go new file mode 100644 index 0000000..64a5292 --- /dev/null +++ b/vendor/github.com/otiai10/copy/test_setup.go @@ -0,0 +1,20 @@ +//go:build !windows && !plan9 && !netbsd && !aix && !illumos && !solaris && !js +// +build !windows,!plan9,!netbsd,!aix,!illumos,!solaris,!js + +package copy + +import ( + "os" + "syscall" + "testing" +) + +func setup(m *testing.M) { + os.RemoveAll("test/data.copy") + os.MkdirAll("test/data.copy", os.ModePerm) + os.Symlink("test/data/case01", "test/data/case03/case01") + os.Chmod("test/data/case07/dir_0555", 0o555) + os.Chmod("test/data/case07/file_0444", 0o444) + syscall.Mkfifo("test/data/case11/foo/bar", 0o555) + Copy("test/data/case18/assets", "test/data/case18/assets.backup") +} diff --git a/vendor/github.com/otiai10/copy/test_setup_x.go b/vendor/github.com/otiai10/copy/test_setup_x.go new file mode 100644 index 0000000..4c35b14 --- /dev/null +++ b/vendor/github.com/otiai10/copy/test_setup_x.go @@ -0,0 +1,17 @@ +//go:build windows || plan9 || netbsd || aix || illumos || solaris || js +// +build windows plan9 netbsd aix illumos solaris js + +package copy + +import ( + "os" + "testing" +) + +func setup(m *testing.M) { + os.RemoveAll("test/data.copy") + os.MkdirAll("test/data.copy", os.ModePerm) + os.Symlink("test/data/case01", "test/data/case03/case01") + os.Chmod("test/data/case07/dir_0555", 0555) + os.Chmod("test/data/case07/file_0444", 0444) +} |
