Include symlinks in snapshots when migrating disks

Fixes #2685
This commit is contained in:
Mark Mickan 2017-06-03 20:45:00 +09:30
parent d1dd380890
commit 236f24c9a4
2 changed files with 18 additions and 8 deletions

View File

@ -118,26 +118,29 @@ func (d *AllocDir) Snapshot(w io.Writer) error {
defer tw.Close()
walkFn := func(path string, fileInfo os.FileInfo, err error) error {
// Ignore if the file is a symlink
if fileInfo.Mode() == os.ModeSymlink {
return nil
}
// Include the path of the file name relative to the alloc dir
// so that we can put the files in the right directories
relPath, err := filepath.Rel(d.AllocDir, path)
if err != nil {
return err
}
hdr, err := tar.FileInfoHeader(fileInfo, "")
link := ""
if fileInfo.Mode()&os.ModeSymlink != 0 {
target, err := os.Readlink(path)
if err != nil {
return fmt.Errorf("error reading symlink: %v", err)
}
link = target
}
hdr, err := tar.FileInfoHeader(fileInfo, link)
if err != nil {
return fmt.Errorf("error creating file header: %v", err)
}
hdr.Name = relPath
tw.WriteHeader(hdr)
// If it's a directory we just write the header into the tar
if fileInfo.IsDir() {
// If it's a directory or symlink we just write the header into the tar
if fileInfo.IsDir() || (fileInfo.Mode()&os.ModeSymlink != 0) {
return nil
}

View File

@ -1851,6 +1851,13 @@ func (c *Client) unarchiveAllocDir(resp io.ReadCloser, allocID string, pathToAll
os.MkdirAll(filepath.Join(pathToAllocDir, hdr.Name), os.FileMode(hdr.Mode))
continue
}
// If the header is for a symlink we create the symlink
if hdr.Typeflag == tar.TypeSymlink {
if os.Symlink(hdr.Linkname, filepath.Join(pathToAllocDir, hdr.Name)); err != nil {
c.logger.Printf("[ERR] client: error creating symlink: %v", err)
}
continue
}
// If the header is a file, we write to a file
if hdr.Typeflag == tar.TypeReg {
f, err := os.Create(filepath.Join(pathToAllocDir, hdr.Name))