Comply with XDG Base Directory specification

Fixes #868
This commit is contained in:
Dario Giovannetti 2017-01-14 11:47:55 +08:00 committed by Nick Craig-Wood
parent 9fdeb82328
commit 9d36258923
2 changed files with 78 additions and 25 deletions

View File

@ -8,9 +8,9 @@ Configure
---------
First you'll need to configure rclone. As the object storage systems
have quite complicated authentication these are kept in a config file
`.rclone.conf` in your home directory by default. (You can use the
`--config` option to choose a different config file.)
have quite complicated authentication these are kept in a config file.
(See the `--config` entry for how to find the config file and choose
its location.)
The easiest way to make the config is to run rclone with the config
option:
@ -281,11 +281,18 @@ they are incorrect as it would normally.
### --config=CONFIG_FILE ###
Specify the location of the rclone config file. Normally this is in
your home directory as a file called `.rclone.conf`. If you run
`rclone -h` and look at the help for the `--config` option you will
see where the default location is for you. Use this flag to override
the config location, eg `rclone --config=".myconfig" .config`.
Specify the location of the rclone config file.
Normally the config file is in your home directory as a file called
`.config/rclone/rclone.conf` (or `.rclone.conf` if created with an
older version). If `$XDG_CONFIG_HOME` is set it will be at
`$XDG_CONFIG_HOME/rclone/rclone.conf`
If you run `rclone -h` and look at the help for the `--config` option
you will see where the default location is for you.
Use this flag to override the config location, eg `rclone
--config=".myconfig" .config`.
### --contimeout=TIME ###

View File

@ -16,7 +16,7 @@ import (
"log"
"os"
"os/user"
"path"
"path/filepath"
"regexp"
"sort"
"strconv"
@ -31,7 +31,8 @@ import (
)
const (
configFileName = ".rclone.conf"
configFileName = "rclone.conf"
hiddenConfigFileName = "." + configFileName
// ConfigToken is the key used to store the token under
ConfigToken = "token"
@ -50,10 +51,8 @@ const (
var (
// configData is the config file data structure
configData *goconfig.ConfigFile
// HomeDir is the home directory of the user
HomeDir = configHome()
// ConfigPath points to the config file
ConfigPath = path.Join(HomeDir, configFileName)
ConfigPath = makeConfigPath()
// Config is the global config
Config = &ConfigInfo{}
// Flags
@ -215,25 +214,72 @@ type ConfigInfo struct {
Suffix string
}
// Find the config directory
func configHome() string {
// Find users home directory
// Return the path to the configuration file
func makeConfigPath() string {
// Find user's home directory
usr, err := user.Current()
var homedir string
if err == nil {
return usr.HomeDir
homedir = usr.HomeDir
} else {
// Fall back to reading $HOME - work around user.Current() not
// working for cross compiled binaries on OSX.
// https://github.com/golang/go/issues/6376
homedir = os.Getenv("HOME")
}
// Fall back to reading $HOME - work around user.Current() not
// working for cross compiled binaries on OSX.
// https://github.com/golang/go/issues/6376
home := os.Getenv("HOME")
if home != "" {
return home
// Possibly find the user's XDG config paths
// See XDG Base Directory specification
// https://specifications.freedesktop.org/basedir-spec/latest/
xdgdir := os.Getenv("XDG_CONFIG_HOME")
var xdgcfgdir string
if xdgdir != "" {
xdgcfgdir = filepath.Join(xdgdir, "rclone")
} else if homedir != "" {
xdgdir = filepath.Join(homedir, ".config")
xdgcfgdir = filepath.Join(xdgdir, "rclone")
}
ErrorLog(nil, "Couldn't find home directory or read HOME environment variable.")
// Use $XDG_CONFIG_HOME/rclone/rclone.conf if already existing
var xdgconf string
if xdgcfgdir != "" {
xdgconf = filepath.Join(xdgcfgdir, configFileName)
_, err := os.Stat(xdgconf)
if err == nil {
return xdgconf
}
}
// Use $HOME/.rclone.conf if already existing
var homeconf string
if homedir != "" {
homeconf = filepath.Join(homedir, hiddenConfigFileName)
_, err := os.Stat(homeconf)
if err == nil {
return homeconf
}
}
// Try to create $XDG_CONFIG_HOME/rclone/rclone.conf
if xdgconf != "" {
// xdgconf != "" implies xdgcfgdir != ""
err := os.MkdirAll(xdgcfgdir, os.ModePerm)
if err == nil {
return xdgconf
}
}
// Try to create $HOME/.rclone.conf
if homeconf != "" {
return homeconf
}
// Default to ./.rclone.conf (current working directory)
ErrorLog(nil, "Couldn't find home directory or read HOME or XDG_CONFIG_HOME environment variables.")
ErrorLog(nil, "Defaulting to storing config in current directory.")
ErrorLog(nil, "Use -config flag to workaround.")
ErrorLog(nil, "Error was: %v", err)
return ""
return hiddenConfigFileName
}
// LoadConfig loads the config file