config: do not overwrite config file symbolic link - fixes #6754

This commit is contained in:
albertony 2023-04-04 14:35:53 +02:00
parent ec8bbb8d30
commit 6cb584f455
2 changed files with 31 additions and 5 deletions

View File

@ -956,6 +956,14 @@ the new file. Then it will rename the existing file to a temporary
name as backup. Next, rclone will rename the new file to the correct name,
before finally cleaning up by deleting the backup file.
If the configuration file path used by rclone is a symbolic link, then
this will be evaluated and rclone will write to the resolved path, instead
of overwriting the symbolic link. Temporary files used in the process
(described above) will be written to the same parent directory as that
of the resolved configuration file, but if this directory is also a
symbolic link it will not be resolved and the temporary files will be
written to the location of the directory symbolic link.
### --contimeout=TIME ###
Set the connection timeout. This should be in go time format which

View File

@ -106,12 +106,30 @@ func (s *Storage) Save() error {
if configPath == "" {
return fmt.Errorf("failed to save config file, path is empty")
}
dir, name := filepath.Split(configPath)
err := file.MkdirAll(dir, os.ModePerm)
configDir, configName := filepath.Split(configPath)
info, err := os.Lstat(configPath)
if err != nil {
if !os.IsNotExist(err) {
return fmt.Errorf("failed to resolve config file path: %w", err)
}
} else {
if info.Mode()&os.ModeSymlink != 0 {
configPath, err = os.Readlink(configPath)
if err != nil {
return fmt.Errorf("failed to resolve config file symbolic link: %w", err)
}
if !filepath.IsAbs(configPath) {
configPath = filepath.Join(configDir, configPath)
}
configDir = filepath.Dir(configPath)
}
}
err = file.MkdirAll(configDir, os.ModePerm)
if err != nil {
return fmt.Errorf("failed to create config directory: %w", err)
}
f, err := os.CreateTemp(dir, name)
f, err := os.CreateTemp(configDir, configName)
if err != nil {
return fmt.Errorf("failed to create temp file for new config: %w", err)
}
@ -138,7 +156,7 @@ func (s *Storage) Save() error {
}
var fileMode os.FileMode = 0600
info, err := os.Stat(configPath)
info, err = os.Stat(configPath)
if err != nil {
fs.Debugf(nil, "Using default permissions for config file: %v", fileMode)
} else if info.Mode() != fileMode {
@ -153,7 +171,7 @@ func (s *Storage) Save() error {
fs.Errorf(nil, "Failed to set permissions on config file: %v", err)
}
fbackup, err := os.CreateTemp(dir, name+".old")
fbackup, err := os.CreateTemp(configDir, configName+".old")
if err != nil {
return fmt.Errorf("failed to create temp file for old config backup: %w", err)
}