Use envvars NIX_CACHE_HOME, NIX_CONFIG_HOME, NIX_DATA_HOME, NIX_STATE_HOME if defined (#11351)

This commit is contained in:
Noam Yorav-Raphael 2024-09-11 13:36:46 +03:00 committed by GitHub
parent c60e1be62c
commit 38bfbb297c
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
17 changed files with 118 additions and 48 deletions

View file

@ -0,0 +1,14 @@
---
synopsis: Use envvars NIX_CACHE_HOME, NIX_CONFIG_HOME, NIX_DATA_HOME, NIX_STATE_HOME if defined
prs: [11351]
---
Added new environment variables:
- `NIX_CACHE_HOME`
- `NIX_CONFIG_HOME`
- `NIX_DATA_HOME`
- `NIX_STATE_HOME`
Each, if defined, takes precedence over the corresponding [XDG environment variable](@docroot@/command-ref/env-common.md#xdg-base-directories).
This provides more fine-grained control over where Nix looks for files, and allows to have a stand-alone Nix environment, which only uses files in a specific directory, and doesn't interfere with the user environment.

View file

@ -138,6 +138,19 @@ The following environment variables are used to determine locations of various s
- [`XDG_STATE_HOME`]{#env-XDG_STATE_HOME} (default `~/.local/state`)
- [`XDG_CACHE_HOME`]{#env-XDG_CACHE_HOME} (default `~/.cache`)
[XDG Base Directory Specification]: https://specifications.freedesktop.org/basedir-spec/basedir-spec-latest.html
[`use-xdg-base-directories`]: @docroot@/command-ref/conf-file.md#conf-use-xdg-base-directories
In addition, setting the following environment variables overrides the XDG base directories:
- [`NIX_CONFIG_HOME`]{#env-NIX_CONFIG_HOME} (default `$XDG_CONFIG_HOME/nix`)
- [`NIX_STATE_HOME`]{#env-NIX_STATE_HOME} (default `$XDG_STATE_HOME/nix`)
- [`NIX_CACHE_HOME`]{#env-NIX_CACHE_HOME} (default `$XDG_CACHE_HOME/nix`)
When [`use-xdg-base-directories`] is enabled, the configuration directory is:
1. `$NIX_CONFIG_HOME`, if it is defined
2. Otherwise, `$XDG_CONFIG_HOME/nix`, if `XDG_CONFIG_HOME` is defined
3. Otherwise, `~/.config/nix`.
Likewise for the state and cache directories.

View file

@ -3,29 +3,33 @@ if [ -n "$HOME" ] && [ -n "$USER" ]; then
# Set up the per-user profile.
NIX_LINK="$HOME/.nix-profile"
if [ -n "${XDG_STATE_HOME-}" ]; then
NIX_LINK_NEW="$XDG_STATE_HOME/nix/profile"
if [ -n "$NIX_STATE_HOME" ]; then
NIX_LINK="$NIX_STATE_HOME/profile"
else
NIX_LINK_NEW="$HOME/.local/state/nix/profile"
fi
if [ -e "$NIX_LINK_NEW" ]; then
if [ -t 2 ] && [ -e "$NIX_LINK" ]; then
warning="\033[1;35mwarning:\033[0m"
printf "$warning Both %s and legacy %s exist; using the former.\n" "$NIX_LINK_NEW" "$NIX_LINK" 1>&2
if [ "$(realpath "$NIX_LINK")" = "$(realpath "$NIX_LINK_NEW")" ]; then
printf " Since the profiles match, you can safely delete either of them.\n" 1>&2
else
# This should be an exceptionally rare occasion: the only way to get it would be to
# 1. Update to newer Nix;
# 2. Remove .nix-profile;
# 3. Set the $NIX_LINK_NEW to something other than the default user profile;
# 4. Roll back to older Nix.
# If someone did all that, they can probably figure out how to migrate the profile.
printf "$warning Profiles do not match. You should manually migrate from %s to %s.\n" "$NIX_LINK" "$NIX_LINK_NEW" 1>&2
fi
NIX_LINK="$HOME/.nix-profile"
if [ -n "${XDG_STATE_HOME-}" ]; then
NIX_LINK_NEW="$XDG_STATE_HOME/nix/profile"
else
NIX_LINK_NEW="$HOME/.local/state/nix/profile"
fi
if [ -e "$NIX_LINK_NEW" ]; then
if [ -t 2 ] && [ -e "$NIX_LINK" ]; then
warning="\033[1;35mwarning:\033[0m"
printf "$warning Both %s and legacy %s exist; using the former.\n" "$NIX_LINK_NEW" "$NIX_LINK" 1>&2
if [ "$(realpath "$NIX_LINK")" = "$(realpath "$NIX_LINK_NEW")" ]; then
printf " Since the profiles match, you can safely delete either of them.\n" 1>&2
else
# This should be an exceptionally rare occasion: the only way to get it would be to
# 1. Update to newer Nix;
# 2. Remove .nix-profile;
# 3. Set the $NIX_LINK_NEW to something other than the default user profile;
# 4. Roll back to older Nix.
# If someone did all that, they can probably figure out how to migrate the profile.
printf "$warning Profiles do not match. You should manually migrate from %s to %s.\n" "$NIX_LINK" "$NIX_LINK_NEW" 1>&2
fi
fi
NIX_LINK="$NIX_LINK_NEW"
fi
NIX_LINK="$NIX_LINK_NEW"
fi
# Set up environment.

View file

@ -134,7 +134,7 @@ NixRepl::NixRepl(const LookupPath & lookupPath, nix::ref<Store> store, ref<EvalS
, getValues(getValues)
, staticEnv(new StaticEnv(nullptr, state->staticBaseEnv.get()))
, runNixPtr{runNix}
, interacter(make_unique<ReadlineLikeInteracter>(getDataDir() + "/nix/repl-history"))
, interacter(make_unique<ReadlineLikeInteracter>(getDataDir() + "/repl-history"))
{
}

View file

@ -69,7 +69,7 @@ struct AttrDb
{
auto state(_state->lock());
Path cacheDir = getCacheDir() + "/nix/eval-cache-v5";
Path cacheDir = getCacheDir() + "/eval-cache-v5";
createDirs(cacheDir);
Path dbPath = cacheDir + "/" + fingerprint.to_string(HashFormat::Base16, false) + ".sqlite";

View file

@ -99,7 +99,7 @@ const std::string & EvalSettings::getCurrentSystem() const
Path getNixDefExpr()
{
return settings.useXDGBaseDirectories
? getStateDir() + "/nix/defexpr"
? getStateDir() + "/defexpr"
: getHome() + "/.nix-defexpr";
}

View file

@ -36,7 +36,7 @@ struct CacheImpl : Cache
{
auto state(_state.lock());
auto dbPath = getCacheDir() + "/nix/fetcher-cache-v2.sqlite";
auto dbPath = getCacheDir() + "/fetcher-cache-v2.sqlite";
createDirs(dirOf(dbPath));
state->db = SQLite(dbPath);

View file

@ -1083,7 +1083,7 @@ std::vector<std::tuple<GitRepoImpl::Submodule, Hash>> GitRepoImpl::getSubmodules
ref<GitRepo> getTarballCache()
{
static auto repoDir = std::filesystem::path(getCacheDir()) / "nix" / "tarball-cache";
static auto repoDir = std::filesystem::path(getCacheDir()) / "tarball-cache";
return GitRepo::openRepo(repoDir, true, true);
}

View file

@ -44,7 +44,7 @@ bool isCacheFileWithinTtl(time_t now, const struct stat & st)
Path getCachePath(std::string_view key, bool shallow)
{
return getCacheDir()
+ "/nix/gitv3/"
+ "/gitv3/"
+ hashString(HashAlgorithm::SHA256, key).to_string(HashFormat::Nix32, false)
+ (shallow ? "-shallow" : "");
}

View file

@ -263,7 +263,7 @@ struct MercurialInputScheme : InputScheme
return makeResult(res->value, res->storePath);
}
Path cacheDir = fmt("%s/nix/hg/%s", getCacheDir(), hashString(HashAlgorithm::SHA256, actualUrl).to_string(HashFormat::Nix32, false));
Path cacheDir = fmt("%s/hg/%s", getCacheDir(), hashString(HashAlgorithm::SHA256, actualUrl).to_string(HashFormat::Nix32, false));
/* If this is a commit hash that we already have, we don't
have to pull again. */

View file

@ -116,7 +116,7 @@ static std::shared_ptr<Registry> getSystemRegistry(const Settings & settings)
Path getUserRegistryPath()
{
return getConfigDir() + "/nix/registry.json";
return getConfigDir() + "/registry.json";
}
std::shared_ptr<Registry> getUserRegistry(const Settings & settings)
@ -159,7 +159,7 @@ static std::shared_ptr<Registry> getGlobalRegistry(const Settings & settings, re
if (!hasPrefix(path, "/")) {
auto storePath = downloadFile(store, path, "flake-registry.json").storePath;
if (auto store2 = store.dynamic_pointer_cast<LocalFSStore>())
store2->addPermRoot(storePath, getCacheDir() + "/nix/flake-registry.json");
store2->addPermRoot(storePath, getCacheDir() + "/flake-registry.json");
path = store->toRealPath(storePath);
}

View file

@ -12,7 +12,7 @@ typedef std::map<std::string, std::map<std::string, bool>> TrustedList;
Path trustedListPath()
{
return getDataDir() + "/nix/trusted-settings.json";
return getDataDir() + "/trusted-settings.json";
}
static TrustedList readTrustedList()

View file

@ -135,7 +135,7 @@ std::vector<Path> getUserConfigFiles()
std::vector<Path> files;
auto dirs = getConfigDirs();
for (auto & dir : dirs) {
files.insert(files.end(), dir + "/nix/nix.conf");
files.insert(files.end(), dir + "/nix.conf");
}
return files;
}

View file

@ -87,7 +87,7 @@ public:
Sync<State> _state;
NarInfoDiskCacheImpl(Path dbPath = getCacheDir() + "/nix/binary-cache-v6.sqlite")
NarInfoDiskCacheImpl(Path dbPath = getCacheDir() + "/binary-cache-v6.sqlite")
{
auto state(_state.lock());

View file

@ -1315,7 +1315,7 @@ ref<Store> openStore(StoreReference && storeURI)
/* If /nix doesn't exist, there is no daemon socket, and
we're not root, then automatically set up a chroot
store in ~/.local/share/nix/root. */
auto chrootStore = getDataDir() + "/nix/root";
auto chrootStore = getDataDir() + "/root";
if (!pathExists(chrootStore)) {
try {
createDirs(chrootStore);

View file

@ -7,15 +7,33 @@ namespace nix {
Path getCacheDir()
{
auto cacheDir = getEnv("XDG_CACHE_HOME");
return cacheDir ? *cacheDir : getHome() + "/.cache";
auto dir = getEnv("NIX_CACHE_HOME");
if (dir) {
return *dir;
} else {
auto xdgDir = getEnv("XDG_CACHE_HOME");
if (xdgDir) {
return *xdgDir + "/nix";
} else {
return getHome() + "/.cache/nix";
}
}
}
Path getConfigDir()
{
auto configDir = getEnv("XDG_CONFIG_HOME");
return configDir ? *configDir : getHome() + "/.config";
auto dir = getEnv("NIX_CONFIG_HOME");
if (dir) {
return *dir;
} else {
auto xdgDir = getEnv("XDG_CONFIG_HOME");
if (xdgDir) {
return *xdgDir + "/nix";
} else {
return getHome() + "/.config/nix";
}
}
}
std::vector<Path> getConfigDirs()
@ -23,6 +41,9 @@ std::vector<Path> getConfigDirs()
Path configHome = getConfigDir();
auto configDirs = getEnv("XDG_CONFIG_DIRS").value_or("/etc/xdg");
std::vector<Path> result = tokenizeString<std::vector<std::string>>(configDirs, ":");
for (auto& p : result) {
p += "/nix";
}
result.insert(result.begin(), configHome);
return result;
}
@ -30,19 +51,37 @@ std::vector<Path> getConfigDirs()
Path getDataDir()
{
auto dataDir = getEnv("XDG_DATA_HOME");
return dataDir ? *dataDir : getHome() + "/.local/share";
auto dir = getEnv("NIX_DATA_HOME");
if (dir) {
return *dir;
} else {
auto xdgDir = getEnv("XDG_DATA_HOME");
if (xdgDir) {
return *xdgDir + "/nix";
} else {
return getHome() + "/.local/share/nix";
}
}
}
Path getStateDir()
{
auto stateDir = getEnv("XDG_STATE_HOME");
return stateDir ? *stateDir : getHome() + "/.local/state";
auto dir = getEnv("NIX_STATE_HOME");
if (dir) {
return *dir;
} else {
auto xdgDir = getEnv("XDG_STATE_HOME");
if (xdgDir) {
return *xdgDir + "/nix";
} else {
return getHome() + "/.local/state/nix";
}
}
}
Path createNixStateDir()
{
Path dir = getStateDir() + "/nix";
Path dir = getStateDir();
createDirs(dir);
return dir;
}

View file

@ -24,12 +24,12 @@ Path getHomeOf(uid_t userId);
Path getHome();
/**
* @return $XDG_CACHE_HOME or $HOME/.cache.
* @return $NIX_CACHE_HOME or $XDG_CACHE_HOME/nix or $HOME/.cache/nix.
*/
Path getCacheDir();
/**
* @return $XDG_CONFIG_HOME or $HOME/.config.
* @return $NIX_CONFIG_HOME or $XDG_CONFIG_HOME/nix or $HOME/.config/nix.
*/
Path getConfigDir();
@ -39,12 +39,12 @@ Path getConfigDir();
std::vector<Path> getConfigDirs();
/**
* @return $XDG_DATA_HOME or $HOME/.local/share.
* @return $NIX_DATA_HOME or $XDG_DATA_HOME/nix or $HOME/.local/share/nix.
*/
Path getDataDir();
/**
* @return $XDG_STATE_HOME or $HOME/.local/state.
* @return $NIX_STATE_HOME or $XDG_STATE_HOME/nix or $HOME/.local/state/nix.
*/
Path getStateDir();