Fix resolving indirect flakerefs

This commit is contained in:
Eelco Dolstra 2022-05-13 14:41:42 +02:00
parent a0ed002ba9
commit de35e2d3b4
No known key found for this signature in database
GPG key ID: 8170B4726D7198DE
2 changed files with 20 additions and 13 deletions

View file

@ -78,7 +78,6 @@ static void forceTrivialValue(EvalState & state, Value & value, const PosIdx pos
state.forceValue(value, pos); state.forceValue(value, pos);
} }
static void expectType(EvalState & state, ValueType type, static void expectType(EvalState & state, ValueType type,
Value & value, const PosIdx pos) Value & value, const PosIdx pos)
{ {
@ -202,15 +201,16 @@ static std::map<FlakeId, FlakeInput> parseFlakeInputs(
static Flake readFlake( static Flake readFlake(
EvalState & state, EvalState & state,
const FlakeRef & lockedRef, const FlakeRef & originalRef,
const FlakeRef & resolvedRef,
InputAccessor & accessor, InputAccessor & accessor,
const InputPath & lockRootPath) const InputPath & lockRootPath)
{ {
auto flakeDir = canonPath("/" + lockedRef.subdir); auto flakeDir = canonPath("/" + resolvedRef.subdir);
SourcePath flakePath{accessor, canonPath(flakeDir + "/flake.nix")}; SourcePath flakePath{accessor, canonPath(flakeDir + "/flake.nix")};
if (!flakePath.pathExists()) if (!flakePath.pathExists())
throw Error("source tree referenced by '%s' does not contain a file named '%s'", lockedRef, flakePath.path); throw Error("source tree referenced by '%s' does not contain a file named '%s'", resolvedRef, flakePath.path);
Value vInfo; Value vInfo;
state.evalFile(flakePath, vInfo, true); state.evalFile(flakePath, vInfo, true);
@ -218,10 +218,9 @@ static Flake readFlake(
expectType(state, nAttrs, vInfo, state.positions.add({flakePath.to_string(), foFile}, 0, 0)); expectType(state, nAttrs, vInfo, state.positions.add({flakePath.to_string(), foFile}, 0, 0));
Flake flake { Flake flake {
// FIXME .originalRef = originalRef,
.originalRef = lockedRef, .resolvedRef = resolvedRef,
.resolvedRef = lockedRef, .lockedRef = resolvedRef, // FIXME
.lockedRef = lockedRef,
.path = flakePath, .path = flakePath,
}; };
@ -250,7 +249,7 @@ static Flake readFlake(
} }
} else } else
throw Error("flake '%s' lacks attribute 'outputs'", lockedRef); throw Error("flake '%s' lacks attribute 'outputs'", resolvedRef);
auto sNixConfig = state.symbols.create("nixConfig"); auto sNixConfig = state.symbols.create("nixConfig");
@ -299,7 +298,7 @@ static Flake readFlake(
attr.name != sOutputs && attr.name != sOutputs &&
attr.name != sNixConfig) attr.name != sNixConfig)
throw Error("flake '%s' has an unsupported attribute '%s', at %s", throw Error("flake '%s' has an unsupported attribute '%s', at %s",
lockedRef, state.symbols[attr.name], state.positions[attr.pos]); resolvedRef, state.symbols[attr.name], state.positions[attr.pos]);
} }
return flake; return flake;
@ -312,10 +311,17 @@ static Flake getFlake(
FlakeCache & flakeCache, FlakeCache & flakeCache,
const InputPath & lockRootPath) const InputPath & lockRootPath)
{ {
// FIXME: resolve auto resolvedRef = originalRef;
auto [accessor, input] = originalRef.input.lazyFetch(state.store);
return readFlake(state, originalRef, state.registerAccessor(accessor), lockRootPath); if (!originalRef.input.isDirect()) {
if (!allowLookup)
throw Error("'%s' is an indirect flake reference, but registry lookups are not allowed", originalRef);
resolvedRef = originalRef.resolve(state.store);
}
auto [accessor, input] = resolvedRef.input.lazyFetch(state.store);
return readFlake(state, originalRef, resolvedRef, state.registerAccessor(accessor), lockRootPath);
} }
Flake getFlake(EvalState & state, const FlakeRef & originalRef, bool allowLookup, FlakeCache & flakeCache) Flake getFlake(EvalState & state, const FlakeRef & originalRef, bool allowLookup, FlakeCache & flakeCache)

View file

@ -96,6 +96,7 @@ struct IndirectInputScheme : InputScheme
std::pair<StorePath, Input> fetch(ref<Store> store, const Input & input) override std::pair<StorePath, Input> fetch(ref<Store> store, const Input & input) override
{ {
abort();
throw Error("indirect input '%s' cannot be fetched directly", input.to_string()); throw Error("indirect input '%s' cannot be fetched directly", input.to_string());
} }
}; };