aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJohn Ericson <John.Ericson@Obsidian.Systems>2023-01-11 16:32:30 -0500
committerJohn Ericson <John.Ericson@Obsidian.Systems>2023-01-11 19:08:19 -0500
commit5ba6e5d0d9bed2806ddb59c8a3305b3cb5784d53 (patch)
tree065e7eccec8a228a4045a434c4d5a1de5aa0cf3b
parent114a6e2b09eda7f23e7776e1cdf77715044e073e (diff)
Remove default constructor from `OutputsSpec`
This forces us to be explicit. It also requires to rework how `from_json` works. A `JSON_IMPL` is added to assist with this.
-rw-r--r--src/libcmd/installables.cc2
-rw-r--r--src/libcmd/repl.cc7
-rw-r--r--src/libstore/build/entry-points.cc7
-rw-r--r--src/libstore/legacy-ssh-store.cc7
-rw-r--r--src/libstore/outputs-spec.cc53
-rw-r--r--src/libstore/outputs-spec.hh15
-rw-r--r--src/libstore/remote-store.cc7
-rw-r--r--src/libutil/json-impls.hh14
-rw-r--r--src/nix-env/nix-env.cc18
-rw-r--r--src/nix/bundle.cc7
-rw-r--r--src/nix/develop.cc7
-rw-r--r--src/nix/flake.cc8
12 files changed, 103 insertions, 49 deletions
diff --git a/src/libcmd/installables.cc b/src/libcmd/installables.cc
index 3457f2e47..d73109873 100644
--- a/src/libcmd/installables.cc
+++ b/src/libcmd/installables.cc
@@ -827,7 +827,7 @@ std::vector<std::shared_ptr<Installable>> SourceExprCommand::parseInstallables(
return storePath.isDerivation()
? (DerivedPath) DerivedPath::Built {
.drvPath = std::move(storePath),
- .outputs = {},
+ .outputs = OutputsSpec::All {},
}
: (DerivedPath) DerivedPath::Opaque {
.path = std::move(storePath),
diff --git a/src/libcmd/repl.cc b/src/libcmd/repl.cc
index 71a7e079a..9b12f8fa2 100644
--- a/src/libcmd/repl.cc
+++ b/src/libcmd/repl.cc
@@ -641,7 +641,12 @@ bool NixRepl::processLine(std::string line)
Path drvPathRaw = state->store->printStorePath(drvPath);
if (command == ":b" || command == ":bl") {
- state->store->buildPaths({DerivedPath::Built{drvPath}});
+ state->store->buildPaths({
+ DerivedPath::Built {
+ .drvPath = drvPath,
+ .outputs = OutputsSpec::All { },
+ },
+ });
auto drv = state->store->readDerivation(drvPath);
logger->cout("\nThis derivation produced the following outputs:");
for (auto & [outputName, outputPath] : state->store->queryDerivationOutputMap(drvPath)) {
diff --git a/src/libstore/build/entry-points.cc b/src/libstore/build/entry-points.cc
index df7722733..2925fe3ca 100644
--- a/src/libstore/build/entry-points.cc
+++ b/src/libstore/build/entry-points.cc
@@ -80,7 +80,7 @@ BuildResult Store::buildDerivation(const StorePath & drvPath, const BasicDerivat
BuildMode buildMode)
{
Worker worker(*this, *this);
- auto goal = worker.makeBasicDerivationGoal(drvPath, drv, {}, buildMode);
+ auto goal = worker.makeBasicDerivationGoal(drvPath, drv, OutputsSpec::All {}, buildMode);
try {
worker.run(Goals{goal});
@@ -89,7 +89,10 @@ BuildResult Store::buildDerivation(const StorePath & drvPath, const BasicDerivat
return BuildResult {
.status = BuildResult::MiscFailure,
.errorMsg = e.msg(),
- .path = DerivedPath::Built { .drvPath = drvPath },
+ .path = DerivedPath::Built {
+ .drvPath = drvPath,
+ .outputs = OutputsSpec::All { },
+ },
};
};
}
diff --git a/src/libstore/legacy-ssh-store.cc b/src/libstore/legacy-ssh-store.cc
index 4d398b21d..e1a4e13a3 100644
--- a/src/libstore/legacy-ssh-store.cc
+++ b/src/libstore/legacy-ssh-store.cc
@@ -279,7 +279,12 @@ public:
conn->to.flush();
- BuildResult status { .path = DerivedPath::Built { .drvPath = drvPath } };
+ BuildResult status {
+ .path = DerivedPath::Built {
+ .drvPath = drvPath,
+ .outputs = OutputsSpec::All { },
+ },
+ };
status.status = (BuildResult::Status) readInt(conn->from);
conn->from >> status.errorMsg;
diff --git a/src/libstore/outputs-spec.cc b/src/libstore/outputs-spec.cc
index 891252990..1eeab1aa8 100644
--- a/src/libstore/outputs-spec.cc
+++ b/src/libstore/outputs-spec.cc
@@ -110,9 +110,21 @@ bool OutputsSpec::merge(const OutputsSpec & that)
}, raw());
}
+}
-void to_json(nlohmann::json & json, const OutputsSpec & outputsSpec)
-{
+namespace nlohmann {
+
+using namespace nix;
+
+OutputsSpec adl_serializer<OutputsSpec>::from_json(const json & json) {
+ auto names = json.get<StringSet>();
+ if (names == StringSet({"*"}))
+ return OutputsSpec::All {};
+ else
+ return OutputsSpec::Names { std::move(names) };
+}
+
+void adl_serializer<OutputsSpec>::to_json(json & json, OutputsSpec t) {
std::visit(overloaded {
[&](const OutputsSpec::All &) {
json = std::vector<std::string>({"*"});
@@ -120,40 +132,27 @@ void to_json(nlohmann::json & json, const OutputsSpec & outputsSpec)
[&](const OutputsSpec::Names & names) {
json = names;
},
- }, outputsSpec);
+ }, t);
}
-void to_json(nlohmann::json & json, const ExtendedOutputsSpec & extendedOutputsSpec)
-{
+ExtendedOutputsSpec adl_serializer<ExtendedOutputsSpec>::from_json(const json & json) {
+ if (json.is_null())
+ return ExtendedOutputsSpec::Default {};
+ else {
+ return ExtendedOutputsSpec::Explicit { json.get<OutputsSpec>() };
+ }
+}
+
+void adl_serializer<ExtendedOutputsSpec>::to_json(json & json, ExtendedOutputsSpec t) {
std::visit(overloaded {
[&](const ExtendedOutputsSpec::Default &) {
json = nullptr;
},
[&](const ExtendedOutputsSpec::Explicit & e) {
- to_json(json, e);
+ adl_serializer<OutputsSpec>::to_json(json, e);
},
- }, extendedOutputsSpec);
-}
-
-
-void from_json(const nlohmann::json & json, OutputsSpec & outputsSpec)
-{
- auto names = json.get<StringSet>();
- if (names == StringSet({"*"}))
- outputsSpec = OutputsSpec::All {};
- else
- outputsSpec = OutputsSpec::Names { std::move(names) };
-}
-
-
-void from_json(const nlohmann::json & json, ExtendedOutputsSpec & extendedOutputsSpec)
-{
- if (json.is_null())
- extendedOutputsSpec = ExtendedOutputsSpec::Default {};
- else {
- extendedOutputsSpec = ExtendedOutputsSpec::Explicit { json.get<OutputsSpec>() };
- }
+ }, t);
}
}
diff --git a/src/libstore/outputs-spec.hh b/src/libstore/outputs-spec.hh
index 9c477ee2b..babf29d16 100644
--- a/src/libstore/outputs-spec.hh
+++ b/src/libstore/outputs-spec.hh
@@ -4,7 +4,7 @@
#include <set>
#include <variant>
-#include "nlohmann/json_fwd.hpp"
+#include "json-impls.hh"
namespace nix {
@@ -35,6 +35,9 @@ struct OutputsSpec : _OutputsSpecRaw {
using Raw = _OutputsSpecRaw;
using Raw::Raw;
+ /* Force choosing a variant */
+ OutputsSpec() = delete;
+
using Names = OutputNames;
using All = AllOutputs;
@@ -85,11 +88,7 @@ struct ExtendedOutputsSpec : _ExtendedOutputsSpecRaw {
std::string to_string() const;
};
-
-void to_json(nlohmann::json &, const OutputsSpec &);
-void from_json(const nlohmann::json &, OutputsSpec &);
-
-void to_json(nlohmann::json &, const ExtendedOutputsSpec &);
-void from_json(const nlohmann::json &, ExtendedOutputsSpec &);
-
}
+
+JSON_IMPL(OutputsSpec)
+JSON_IMPL(ExtendedOutputsSpec)
diff --git a/src/libstore/remote-store.cc b/src/libstore/remote-store.cc
index 832be08f7..ff57a77ca 100644
--- a/src/libstore/remote-store.cc
+++ b/src/libstore/remote-store.cc
@@ -910,7 +910,12 @@ BuildResult RemoteStore::buildDerivation(const StorePath & drvPath, const BasicD
writeDerivation(conn->to, *this, drv);
conn->to << buildMode;
conn.processStderr();
- BuildResult res { .path = DerivedPath::Built { .drvPath = drvPath } };
+ BuildResult res {
+ .path = DerivedPath::Built {
+ .drvPath = drvPath,
+ .outputs = OutputsSpec::All { },
+ },
+ };
res.status = (BuildResult::Status) readInt(conn->from);
conn->from >> res.errorMsg;
if (GET_PROTOCOL_MINOR(conn->daemonVersion) >= 29) {
diff --git a/src/libutil/json-impls.hh b/src/libutil/json-impls.hh
new file mode 100644
index 000000000..bd75748ad
--- /dev/null
+++ b/src/libutil/json-impls.hh
@@ -0,0 +1,14 @@
+#pragma once
+
+#include "nlohmann/json_fwd.hpp"
+
+// Following https://github.com/nlohmann/json#how-can-i-use-get-for-non-default-constructiblenon-copyable-types
+#define JSON_IMPL(TYPE) \
+ namespace nlohmann { \
+ using namespace nix; \
+ template <> \
+ struct adl_serializer<TYPE> { \
+ static TYPE from_json(const json & json); \
+ static void to_json(json & json, TYPE t); \
+ }; \
+ }
diff --git a/src/nix-env/nix-env.cc b/src/nix-env/nix-env.cc
index 31823a966..406e548c0 100644
--- a/src/nix-env/nix-env.cc
+++ b/src/nix-env/nix-env.cc
@@ -478,9 +478,14 @@ static void printMissing(EvalState & state, DrvInfos & elems)
std::vector<DerivedPath> targets;
for (auto & i : elems)
if (auto drvPath = i.queryDrvPath())
- targets.push_back(DerivedPath::Built{*drvPath});
+ targets.push_back(DerivedPath::Built{
+ .drvPath = *drvPath,
+ .outputs = OutputsSpec::All { },
+ });
else
- targets.push_back(DerivedPath::Opaque{i.queryOutPath()});
+ targets.push_back(DerivedPath::Opaque{
+ .path = i.queryOutPath(),
+ });
printMissing(state.store, targets);
}
@@ -751,8 +756,13 @@ static void opSet(Globals & globals, Strings opFlags, Strings opArgs)
auto drvPath = drv.queryDrvPath();
std::vector<DerivedPath> paths {
drvPath
- ? (DerivedPath) (DerivedPath::Built { *drvPath })
- : (DerivedPath) (DerivedPath::Opaque { drv.queryOutPath() }),
+ ? (DerivedPath) (DerivedPath::Built {
+ .drvPath = *drvPath,
+ .outputs = OutputsSpec::All { },
+ })
+ : (DerivedPath) (DerivedPath::Opaque {
+ .path = drv.queryOutPath(),
+ }),
};
printMissing(globals.state->store, paths);
if (globals.dryRun) return;
diff --git a/src/nix/bundle.cc b/src/nix/bundle.cc
index a09dadff4..6ae9460f6 100644
--- a/src/nix/bundle.cc
+++ b/src/nix/bundle.cc
@@ -105,7 +105,12 @@ struct CmdBundle : InstallableCommand
auto outPath = evalState->coerceToStorePath(attr2->pos, *attr2->value, context2, "");
- store->buildPaths({ DerivedPath::Built { drvPath } });
+ store->buildPaths({
+ DerivedPath::Built {
+ .drvPath = drvPath,
+ .outputs = OutputsSpec::All { },
+ },
+ });
auto outPathS = store->printStorePath(outPath);
diff --git a/src/nix/develop.cc b/src/nix/develop.cc
index 6aa675386..16bbd8613 100644
--- a/src/nix/develop.cc
+++ b/src/nix/develop.cc
@@ -232,7 +232,12 @@ static StorePath getDerivationEnvironment(ref<Store> store, ref<Store> evalStore
auto shellDrvPath = writeDerivation(*evalStore, drv);
/* Build the derivation. */
- store->buildPaths({DerivedPath::Built{shellDrvPath}}, bmNormal, evalStore);
+ store->buildPaths(
+ { DerivedPath::Built {
+ .drvPath = shellDrvPath,
+ .outputs = OutputsSpec::All { },
+ }},
+ bmNormal, evalStore);
for (auto & [_0, optPath] : evalStore->queryPartialDerivationOutputMap(shellDrvPath)) {
assert(optPath);
diff --git a/src/nix/flake.cc b/src/nix/flake.cc
index 33ce3f401..d16d88ef8 100644
--- a/src/nix/flake.cc
+++ b/src/nix/flake.cc
@@ -513,8 +513,12 @@ struct CmdFlakeCheck : FlakeCommand
auto drvPath = checkDerivation(
fmt("%s.%s.%s", name, attr_name, state->symbols[attr2.name]),
*attr2.value, attr2.pos);
- if (drvPath && attr_name == settings.thisSystem.get())
- drvPaths.push_back(DerivedPath::Built{*drvPath});
+ if (drvPath && attr_name == settings.thisSystem.get()) {
+ drvPaths.push_back(DerivedPath::Built {
+ .drvPath = *drvPath,
+ .outputs = OutputsSpec::All { },
+ });
+ }
}
}
}