diff --git a/src/libexpr/eval-cache.cc b/src/libexpr/eval-cache.cc index a47a539f5..3a18b71d4 100644 --- a/src/libexpr/eval-cache.cc +++ b/src/libexpr/eval-cache.cc @@ -2,6 +2,7 @@ #include "sqlite.hh" #include "eval.hh" #include "eval-inline.hh" +#include "store-api.hh" namespace nix::eval_cache { @@ -502,4 +503,19 @@ bool AttrCursor::isDerivation() return aType && aType->getString() == "derivation"; } +StorePath AttrCursor::forceDerivation() +{ + auto aDrvPath = getAttr(root->state.sDrvPath); + auto drvPath = root->state.store->parseStorePath(aDrvPath->getString()); + if (!root->state.store->isValidPath(drvPath) && !settings.readOnlyMode) { + /* The eval cache contains 'drvPath', but the actual path has + been garbage-collected. So force it to be regenerated. */ + aDrvPath->forceValue(); + if (!root->state.store->isValidPath(drvPath)) + throw Error("don't know how to recreate store derivation '%s'!", + root->state.store->printStorePath(drvPath)); + } + return drvPath; +} + } diff --git a/src/libexpr/eval-cache.hh b/src/libexpr/eval-cache.hh index 9c47da315..30261fd3a 100644 --- a/src/libexpr/eval-cache.hh +++ b/src/libexpr/eval-cache.hh @@ -101,6 +101,9 @@ public: bool isDerivation(); Value & forceValue(); + + /* Force creation of the .drv file in the Nix store. */ + StorePath forceDerivation(); }; } diff --git a/src/nix/installables.cc b/src/nix/installables.cc index fb79fad5d..3683ab945 100644 --- a/src/nix/installables.cc +++ b/src/nix/installables.cc @@ -444,17 +444,7 @@ std::tuple InstallableF if (!attr->isDerivation()) throw Error("flake output attribute '%s' is not a derivation", attrPath); - auto aDrvPath = attr->getAttr(state->sDrvPath); - auto drvPath = state->store->parseStorePath(aDrvPath->getString()); - if (!state->store->isValidPath(drvPath) && !settings.readOnlyMode) { - /* The eval cache contains 'drvPath', but the actual path - has been garbage-collected. So force it to be - regenerated. */ - aDrvPath->forceValue(); - if (!state->store->isValidPath(drvPath)) - throw Error("don't know how to recreate store derivation '%s'!", - state->store->printStorePath(drvPath)); - } + auto drvPath = attr->forceDerivation(); auto drvInfo = DerivationInfo{ std::move(drvPath),