mirror of
https://github.com/NixOS/nix.git
synced 2025-11-29 21:50:58 +01:00
Merge remote-tracking branch 'origin/master' into lazy-trees
This commit is contained in:
commit
30ca717558
175 changed files with 4032 additions and 1936 deletions
|
|
@ -72,7 +72,7 @@ static std::tuple<fetchers::Tree, FlakeRef, FlakeRef> fetchOrSubstituteTree(
|
|||
return {std::move(tree), resolvedRef, lockedRef};
|
||||
}
|
||||
|
||||
static void forceTrivialValue(EvalState & state, Value & value, const Pos & pos)
|
||||
static void forceTrivialValue(EvalState & state, Value & value, const PosIdx pos)
|
||||
{
|
||||
if (value.isThunk() && value.isTrivial())
|
||||
state.forceValue(value, pos);
|
||||
|
|
@ -80,18 +80,18 @@ static void forceTrivialValue(EvalState & state, Value & value, const Pos & pos)
|
|||
|
||||
|
||||
static void expectType(EvalState & state, ValueType type,
|
||||
Value & value, const Pos & pos)
|
||||
Value & value, const PosIdx pos)
|
||||
{
|
||||
forceTrivialValue(state, value, pos);
|
||||
if (value.type() != type)
|
||||
throw Error("expected %s but got %s at %s",
|
||||
showType(type), showType(value.type()), pos);
|
||||
showType(type), showType(value.type()), state.positions[pos]);
|
||||
}
|
||||
|
||||
static std::map<FlakeId, FlakeInput> parseFlakeInputs(
|
||||
EvalState & state,
|
||||
Value * value,
|
||||
const Pos & pos,
|
||||
const PosIdx pos,
|
||||
const std::optional<Path> & baseDir,
|
||||
const InputPath & lockRootPath);
|
||||
|
||||
|
|
@ -99,7 +99,7 @@ static FlakeInput parseFlakeInput(
|
|||
EvalState & state,
|
||||
const std::string & inputName,
|
||||
Value * value,
|
||||
const Pos & pos,
|
||||
const PosIdx pos,
|
||||
const std::optional<Path> & baseDir,
|
||||
const InputPath & lockRootPath)
|
||||
{
|
||||
|
|
@ -118,37 +118,39 @@ static FlakeInput parseFlakeInput(
|
|||
for (nix::Attr attr : *(value->attrs)) {
|
||||
try {
|
||||
if (attr.name == sUrl) {
|
||||
expectType(state, nString, *attr.value, *attr.pos);
|
||||
expectType(state, nString, *attr.value, attr.pos);
|
||||
url = attr.value->string.s;
|
||||
attrs.emplace("url", *url);
|
||||
} else if (attr.name == sFlake) {
|
||||
expectType(state, nBool, *attr.value, *attr.pos);
|
||||
expectType(state, nBool, *attr.value, attr.pos);
|
||||
input.isFlake = attr.value->boolean;
|
||||
} else if (attr.name == sInputs) {
|
||||
input.overrides = parseFlakeInputs(state, attr.value, *attr.pos, baseDir, lockRootPath);
|
||||
input.overrides = parseFlakeInputs(state, attr.value, attr.pos, baseDir, lockRootPath);
|
||||
} else if (attr.name == sFollows) {
|
||||
expectType(state, nString, *attr.value, *attr.pos);
|
||||
expectType(state, nString, *attr.value, attr.pos);
|
||||
auto follows(parseInputPath(attr.value->string.s));
|
||||
follows.insert(follows.begin(), lockRootPath.begin(), lockRootPath.end());
|
||||
input.follows = follows;
|
||||
} else {
|
||||
switch (attr.value->type()) {
|
||||
case nString:
|
||||
attrs.emplace(attr.name, attr.value->string.s);
|
||||
attrs.emplace(state.symbols[attr.name], attr.value->string.s);
|
||||
break;
|
||||
case nBool:
|
||||
attrs.emplace(attr.name, Explicit<bool> { attr.value->boolean });
|
||||
attrs.emplace(state.symbols[attr.name], Explicit<bool> { attr.value->boolean });
|
||||
break;
|
||||
case nInt:
|
||||
attrs.emplace(attr.name, (long unsigned int)attr.value->integer);
|
||||
attrs.emplace(state.symbols[attr.name], (long unsigned int)attr.value->integer);
|
||||
break;
|
||||
default:
|
||||
throw TypeError("flake input attribute '%s' is %s while a string, Boolean, or integer is expected",
|
||||
attr.name, showType(*attr.value));
|
||||
state.symbols[attr.name], showType(*attr.value));
|
||||
}
|
||||
}
|
||||
} catch (Error & e) {
|
||||
e.addTrace(*attr.pos, hintfmt("in flake attribute '%s'", attr.name));
|
||||
e.addTrace(
|
||||
state.positions[attr.pos],
|
||||
hintfmt("in flake attribute '%s'", state.symbols[attr.name]));
|
||||
throw;
|
||||
}
|
||||
}
|
||||
|
|
@ -157,13 +159,13 @@ static FlakeInput parseFlakeInput(
|
|||
try {
|
||||
input.ref = FlakeRef::fromAttrs(attrs);
|
||||
} catch (Error & e) {
|
||||
e.addTrace(pos, hintfmt("in flake input"));
|
||||
e.addTrace(state.positions[pos], hintfmt("in flake input"));
|
||||
throw;
|
||||
}
|
||||
else {
|
||||
attrs.erase("url");
|
||||
if (!attrs.empty())
|
||||
throw Error("unexpected flake input attribute '%s', at %s", attrs.begin()->first, pos);
|
||||
throw Error("unexpected flake input attribute '%s', at %s", attrs.begin()->first, state.positions[pos]);
|
||||
if (url)
|
||||
input.ref = parseFlakeRef(*url, baseDir, true, input.isFlake);
|
||||
}
|
||||
|
|
@ -177,7 +179,7 @@ static FlakeInput parseFlakeInput(
|
|||
static std::map<FlakeId, FlakeInput> parseFlakeInputs(
|
||||
EvalState & state,
|
||||
Value * value,
|
||||
const Pos & pos,
|
||||
const PosIdx pos,
|
||||
const std::optional<Path> & baseDir,
|
||||
const InputPath & lockRootPath)
|
||||
{
|
||||
|
|
@ -186,11 +188,11 @@ static std::map<FlakeId, FlakeInput> parseFlakeInputs(
|
|||
expectType(state, nAttrs, *value, pos);
|
||||
|
||||
for (nix::Attr & inputAttr : *(*value).attrs) {
|
||||
inputs.emplace(inputAttr.name,
|
||||
inputs.emplace(state.symbols[inputAttr.name],
|
||||
parseFlakeInput(state,
|
||||
inputAttr.name,
|
||||
state.symbols[inputAttr.name],
|
||||
inputAttr.value,
|
||||
*inputAttr.pos,
|
||||
inputAttr.pos,
|
||||
baseDir,
|
||||
lockRootPath));
|
||||
}
|
||||
|
|
@ -213,37 +215,37 @@ static Flake readFlake(
|
|||
Value vInfo;
|
||||
state.evalFile(flakePath, vInfo, true);
|
||||
|
||||
expectType(state, nAttrs, vInfo, Pos(foFile, state.symbols.create(flakePath.to_string()), 0, 0));
|
||||
expectType(state, nAttrs, vInfo, state.positions.add({flakePath.to_string(), foFile}, 0, 0));
|
||||
|
||||
Flake flake {
|
||||
// FIXME
|
||||
.originalRef = lockedRef,
|
||||
.resolvedRef = lockedRef,
|
||||
.lockedRef = lockedRef,
|
||||
.accessor = ptr(&accessor),
|
||||
.accessor = &accessor,
|
||||
.flakePath = dirOf(flakePath.path),
|
||||
};
|
||||
|
||||
if (auto description = vInfo.attrs->get(state.sDescription)) {
|
||||
expectType(state, nString, *description->value, *description->pos);
|
||||
expectType(state, nString, *description->value, description->pos);
|
||||
flake.description = description->value->string.s;
|
||||
}
|
||||
|
||||
auto sInputs = state.symbols.create("inputs");
|
||||
|
||||
if (auto inputs = vInfo.attrs->get(sInputs))
|
||||
flake.inputs = parseFlakeInputs(state, inputs->value, *inputs->pos, flakeDir, lockRootPath);
|
||||
flake.inputs = parseFlakeInputs(state, inputs->value, inputs->pos, flakeDir, lockRootPath);
|
||||
|
||||
auto sOutputs = state.symbols.create("outputs");
|
||||
|
||||
if (auto outputs = vInfo.attrs->get(sOutputs)) {
|
||||
expectType(state, nFunction, *outputs->value, *outputs->pos);
|
||||
expectType(state, nFunction, *outputs->value, outputs->pos);
|
||||
|
||||
if (outputs->value->isLambda() && outputs->value->lambda.fun->hasFormals()) {
|
||||
for (auto & formal : outputs->value->lambda.fun->formals->formals) {
|
||||
if (formal.name != state.sSelf)
|
||||
flake.inputs.emplace(formal.name, FlakeInput {
|
||||
.ref = parseFlakeRef(formal.name)
|
||||
flake.inputs.emplace(state.symbols[formal.name], FlakeInput {
|
||||
.ref = parseFlakeRef(state.symbols[formal.name])
|
||||
});
|
||||
}
|
||||
}
|
||||
|
|
@ -254,35 +256,41 @@ static Flake readFlake(
|
|||
auto sNixConfig = state.symbols.create("nixConfig");
|
||||
|
||||
if (auto nixConfig = vInfo.attrs->get(sNixConfig)) {
|
||||
expectType(state, nAttrs, *nixConfig->value, *nixConfig->pos);
|
||||
expectType(state, nAttrs, *nixConfig->value, nixConfig->pos);
|
||||
|
||||
for (auto & setting : *nixConfig->value->attrs) {
|
||||
forceTrivialValue(state, *setting.value, *setting.pos);
|
||||
forceTrivialValue(state, *setting.value, setting.pos);
|
||||
if (setting.value->type() == nString)
|
||||
flake.config.settings.insert({setting.name, std::string(state.forceStringNoCtx(*setting.value, *setting.pos))});
|
||||
flake.config.settings.emplace(
|
||||
state.symbols[setting.name],
|
||||
std::string(state.forceStringNoCtx(*setting.value, setting.pos)));
|
||||
else if (setting.value->type() == nPath) {
|
||||
PathSet emptyContext = {};
|
||||
flake.config.settings.emplace(
|
||||
setting.name,
|
||||
state.coerceToString(*setting.pos, *setting.value, emptyContext, false, true, true) .toOwned());
|
||||
state.symbols[setting.name],
|
||||
state.coerceToString(setting.pos, *setting.value, emptyContext, false, true, true) .toOwned());
|
||||
}
|
||||
else if (setting.value->type() == nInt)
|
||||
flake.config.settings.insert({setting.name, state.forceInt(*setting.value, *setting.pos)});
|
||||
flake.config.settings.emplace(
|
||||
state.symbols[setting.name],
|
||||
state.forceInt(*setting.value, setting.pos));
|
||||
else if (setting.value->type() == nBool)
|
||||
flake.config.settings.insert({setting.name, Explicit<bool> { state.forceBool(*setting.value, *setting.pos) }});
|
||||
flake.config.settings.emplace(
|
||||
state.symbols[setting.name],
|
||||
Explicit<bool> { state.forceBool(*setting.value, setting.pos) });
|
||||
else if (setting.value->type() == nList) {
|
||||
std::vector<std::string> ss;
|
||||
for (auto elem : setting.value->listItems()) {
|
||||
if (elem->type() != nString)
|
||||
throw TypeError("list element in flake configuration setting '%s' is %s while a string is expected",
|
||||
setting.name, showType(*setting.value));
|
||||
ss.emplace_back(state.forceStringNoCtx(*elem, *setting.pos));
|
||||
state.symbols[setting.name], showType(*setting.value));
|
||||
ss.emplace_back(state.forceStringNoCtx(*elem, setting.pos));
|
||||
}
|
||||
flake.config.settings.insert({setting.name, ss});
|
||||
flake.config.settings.emplace(state.symbols[setting.name], ss);
|
||||
}
|
||||
else
|
||||
throw TypeError("flake configuration setting '%s' is %s",
|
||||
setting.name, showType(*setting.value));
|
||||
state.symbols[setting.name], showType(*setting.value));
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -292,7 +300,7 @@ static Flake readFlake(
|
|||
attr.name != sOutputs &&
|
||||
attr.name != sNixConfig)
|
||||
throw Error("flake '%s' has an unsupported attribute '%s', at %s",
|
||||
lockedRef, attr.name, *attr.pos);
|
||||
lockedRef, state.symbols[attr.name], state.positions[attr.pos]);
|
||||
}
|
||||
|
||||
return flake;
|
||||
|
|
@ -723,12 +731,12 @@ void callFlake(EvalState & state,
|
|||
state.callFunction(*vTmp2, *vRootSubdir, vRes, noPos);
|
||||
}
|
||||
|
||||
static void prim_getFlake(EvalState & state, const Pos & pos, Value * * args, Value & v)
|
||||
static void prim_getFlake(EvalState & state, const PosIdx pos, Value * * args, Value & v)
|
||||
{
|
||||
std::string flakeRefS(state.forceStringNoCtx(*args[0], pos));
|
||||
auto flakeRef = parseFlakeRef(flakeRefS, {}, true);
|
||||
if (evalSettings.pureEval && !flakeRef.input.isLocked())
|
||||
throw Error("cannot call 'getFlake' on unlocked flake reference '%s', at %s (use --impure to override)", flakeRefS, pos);
|
||||
throw Error("cannot call 'getFlake' on unlocked flake reference '%s', at %s (use --impure to override)", flakeRefS, state.positions[pos]);
|
||||
|
||||
callFlake(state,
|
||||
lockFlake(state, flakeRef,
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue