Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions doc/manual/rl-next/narinfo-cache-meta-ttl.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
---
synopsis: New setting `narinfo-cache-meta-ttl`
prs: [15287]
---

The new setting `narinfo-cache-meta-ttl` controls how long binary cache metadata (i.e. `/nix-cache-info`) is cached locally, in seconds. This was previously hard-coded to 7 days, which is still the default. As a result, you can now use `nix store info --refresh` to check whether a binary cache is still valid.
11 changes: 11 additions & 0 deletions src/libstore/include/nix/store/globals.hh
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,17 @@ struct NarInfoDiskCacheSettings : public virtual Config
would prevent trying to pull the path again and failing with a hash
mismatch if the build isn't reproducible.
)"};

Setting<unsigned int> ttlMeta{
this,
7 * 24 * 3600,
"narinfo-cache-meta-ttl",
R"(
The TTL in seconds for caching binary cache metadata (i.e.
`/nix-cache-info`). This determines how long information about a
binary cache (such as its store directory, priority, and whether it
wants mass queries) is considered valid before being refreshed.
)"};
};

class Settings : public virtual Config,
Expand Down
5 changes: 1 addition & 4 deletions src/libstore/nar-info-disk-cache.cc
Original file line number Diff line number Diff line change
Expand Up @@ -63,9 +63,6 @@ struct NarInfoDiskCacheImpl : NarInfoDiskCache
/* How often to purge expired entries from the cache. */
const int purgeInterval = 24 * 3600;

/* How long to cache binary cache info (i.e. /nix-cache-info) */
const int cacheInfoTtl = 7 * 24 * 3600;

struct Cache
{
int id;
Expand Down Expand Up @@ -184,7 +181,7 @@ struct NarInfoDiskCacheImpl : NarInfoDiskCache
{
auto i = state.caches.find(uri);
if (i == state.caches.end()) {
auto queryCache(state.queryCache.use()(uri)(time(0) - cacheInfoTtl));
auto queryCache(state.queryCache.use()(uri)(time(0) - settings.ttlMeta));

@xokdvium xokdvium Feb 26, 2026

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is subtle, note that the test on i686 (and other 32 bit platforms) fails because this does a silent integral unsigned promotion.
https://hydra.nixos.org/build/322992746/nixlog/1

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Will put up a fix

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in #15356

if (!queryCache.next())
return std::nullopt;
auto cache = Cache{
Expand Down
4 changes: 4 additions & 0 deletions src/nix/main.cc
Original file line number Diff line number Diff line change
Expand Up @@ -564,12 +564,16 @@ void mainWrapped(int argc, char ** argv)
fileTransferSettings.tries = 0;
if (!fileTransferSettings.connectTimeout.overridden)
fileTransferSettings.connectTimeout = 1;
auto & ttlMeta = settings.getNarInfoDiskCacheSettings().ttlMeta;
if (!ttlMeta.overridden)
ttlMeta = std::numeric_limits<unsigned int>::max();
}

if (args.refresh) {
fetchSettings.tarballTtl = 0;
settings.getNarInfoDiskCacheSettings().ttlNegative = 0;
settings.getNarInfoDiskCacheSettings().ttlPositive = 0;
settings.getNarInfoDiskCacheSettings().ttlMeta = 0;
}

if (args.command->second->forceImpureByDefault() && !evalSettings.pureEval.overridden) {
Expand Down
21 changes: 21 additions & 0 deletions tests/functional/binary-cache.sh
Original file line number Diff line number Diff line change
Expand Up @@ -312,3 +312,24 @@ nix-store --delete "$outPath" "$docPath"
# -vvv is the level that logs during the loop
timeout 60 nix-build --no-out-link -E "$expr" --option substituters "file://$cacheDir" \
--option trusted-binary-caches "file://$cacheDir" --no-require-sigs


# Test that the narinfo-cache-meta-ttl causes nix-cache-info to be cached,
# and that --refresh overrides it.

# Populate the metadata cache by querying store info over HTTP.
_NIX_FORCE_HTTP=1 nix store info --store "file://$cacheDir"

# Remove nix-cache-info from the binary cache.
rm "$cacheDir/nix-cache-info"

# nix store info should still work because the metadata is cached
# (narinfo-cache-meta-ttl defaults to 7 days).
_NIX_FORCE_HTTP=1 nix store info --store "file://$cacheDir"

# But with --refresh, it should fail because nix-cache-info is gone
# and the cached metadata TTL is overridden to 0.
_NIX_FORCE_HTTP=1 expectStderr 1 nix store info --store "file://$cacheDir" --refresh | grepQuiet "uploading.*is not supported"

# Remove --refresh and it should work again.
_NIX_FORCE_HTTP=1 nix store info --store "file://$cacheDir"
Loading