mirror of
https://github.com/NixOS/nix.git
synced 2025-11-08 19:46:02 +01:00
JSON impl for DummyStore
This commit is contained in:
parent
436e3e779a
commit
f446cb290c
6 changed files with 225 additions and 0 deletions
5
src/libstore-tests/data/dummy-store/empty.json
Normal file
5
src/libstore-tests/data/dummy-store/empty.json
Normal file
|
|
@ -0,0 +1,5 @@
|
|||
{
|
||||
"build-trace": {},
|
||||
"contents": {},
|
||||
"store-dir": "/nix/store"
|
||||
}
|
||||
34
src/libstore-tests/data/dummy-store/one-flat-file.json
Normal file
34
src/libstore-tests/data/dummy-store/one-flat-file.json
Normal file
|
|
@ -0,0 +1,34 @@
|
|||
{
|
||||
"build-trace": {},
|
||||
"contents": {
|
||||
"5hizn7xyyrhxr0k2magvxl5ccvk0ci9n-my-file": {
|
||||
"contents": {
|
||||
"contents": "asdf",
|
||||
"executable": false,
|
||||
"type": "regular"
|
||||
},
|
||||
"info": {
|
||||
"ca": {
|
||||
"hash": {
|
||||
"algorithm": "sha256",
|
||||
"format": "base64",
|
||||
"hash": "f1eduuSIYC1BofXA1tycF79Ai2NSMJQtUErx5DxLYSU="
|
||||
},
|
||||
"method": "nar"
|
||||
},
|
||||
"deriver": null,
|
||||
"narHash": {
|
||||
"algorithm": "sha256",
|
||||
"format": "base64",
|
||||
"hash": "f1eduuSIYC1BofXA1tycF79Ai2NSMJQtUErx5DxLYSU="
|
||||
},
|
||||
"narSize": 120,
|
||||
"references": [],
|
||||
"registrationTime": null,
|
||||
"signatures": [],
|
||||
"ultimate": false
|
||||
}
|
||||
}
|
||||
},
|
||||
"store-dir": "/nix/store"
|
||||
}
|
||||
|
|
@ -1,11 +1,32 @@
|
|||
#include <gtest/gtest.h>
|
||||
#include <nlohmann/json.hpp>
|
||||
|
||||
#include "nix/util/memory-source-accessor.hh"
|
||||
#include "nix/store/dummy-store-impl.hh"
|
||||
#include "nix/store/globals.hh"
|
||||
#include "nix/store/realisation.hh"
|
||||
|
||||
#include "nix/util/tests/json-characterization.hh"
|
||||
|
||||
namespace nix {
|
||||
|
||||
class DummyStoreTest : public virtual CharacterizationTest
|
||||
{
|
||||
std::filesystem::path unitTestData = getUnitTestData() / "dummy-store";
|
||||
|
||||
public:
|
||||
|
||||
std::filesystem::path goldenMaster(std::string_view testStem) const override
|
||||
{
|
||||
return unitTestData / testStem;
|
||||
}
|
||||
|
||||
static void SetUpTestSuite()
|
||||
{
|
||||
initLibStore(false);
|
||||
}
|
||||
};
|
||||
|
||||
TEST(DummyStore, realisation_read)
|
||||
{
|
||||
initLibStore(/*loadConfig=*/false);
|
||||
|
|
@ -35,4 +56,66 @@ TEST(DummyStore, realisation_read)
|
|||
EXPECT_EQ(*value2, value);
|
||||
}
|
||||
|
||||
/* ----------------------------------------------------------------------------
|
||||
* JSON
|
||||
* --------------------------------------------------------------------------*/
|
||||
|
||||
using nlohmann::json;
|
||||
|
||||
struct DummyStoreJsonTest : DummyStoreTest,
|
||||
JsonCharacterizationTest<ref<DummyStore>>,
|
||||
::testing::WithParamInterface<std::pair<std::string_view, ref<DummyStore>>>
|
||||
{};
|
||||
|
||||
TEST_P(DummyStoreJsonTest, from_json)
|
||||
{
|
||||
auto & [name, expected] = GetParam();
|
||||
using namespace nlohmann;
|
||||
/* Cannot use `readJsonTest` because need to dereference the stores
|
||||
for equality. */
|
||||
readTest(Path{name} + ".json", [&](const auto & encodedRaw) {
|
||||
auto encoded = json::parse(encodedRaw);
|
||||
ref<DummyStore> decoded = adl_serializer<ref<DummyStore>>::from_json(encoded);
|
||||
ASSERT_EQ(*decoded, *expected);
|
||||
});
|
||||
}
|
||||
|
||||
TEST_P(DummyStoreJsonTest, to_json)
|
||||
{
|
||||
auto & [name, value] = GetParam();
|
||||
writeJsonTest(name, value);
|
||||
}
|
||||
|
||||
INSTANTIATE_TEST_SUITE_P(DummyStoreJSON, DummyStoreJsonTest, [] {
|
||||
initLibStore(false);
|
||||
auto writeCfg = make_ref<DummyStore::Config>(DummyStore::Config::Params{});
|
||||
writeCfg->readOnly = false;
|
||||
return ::testing::Values(
|
||||
std::pair{
|
||||
"empty",
|
||||
make_ref<DummyStore::Config>(DummyStore::Config::Params{})->openDummyStore(),
|
||||
},
|
||||
std::pair{
|
||||
"one-flat-file",
|
||||
[&] {
|
||||
auto store = writeCfg->openDummyStore();
|
||||
store->addToStore(
|
||||
"my-file",
|
||||
SourcePath{
|
||||
[] {
|
||||
auto sc = make_ref<MemorySourceAccessor>();
|
||||
sc->root = MemorySourceAccessor::File{MemorySourceAccessor::File::Regular{
|
||||
.executable = false,
|
||||
.contents = "asdf",
|
||||
}};
|
||||
return sc;
|
||||
}(),
|
||||
},
|
||||
ContentAddressMethod::Raw::NixArchive,
|
||||
HashAlgorithm::SHA256);
|
||||
return store;
|
||||
}(),
|
||||
});
|
||||
}());
|
||||
|
||||
} // namespace nix
|
||||
|
|
|
|||
|
|
@ -2,6 +2,7 @@
|
|||
#include "nix/util/archive.hh"
|
||||
#include "nix/util/callback.hh"
|
||||
#include "nix/util/memory-source-accessor.hh"
|
||||
#include "nix/util/json-utils.hh"
|
||||
#include "nix/store/dummy-store-impl.hh"
|
||||
#include "nix/store/realisation.hh"
|
||||
|
||||
|
|
@ -16,6 +17,16 @@ std::string DummyStoreConfig::doc()
|
|||
;
|
||||
}
|
||||
|
||||
bool DummyStore::PathInfoAndContents::operator==(const PathInfoAndContents & other) const
|
||||
{
|
||||
return info == other.info && contents->root == other.contents->root;
|
||||
}
|
||||
|
||||
bool DummyStore::operator==(const DummyStore & other) const
|
||||
{
|
||||
return contents == other.contents && buildTrace == other.buildTrace;
|
||||
}
|
||||
|
||||
namespace {
|
||||
|
||||
class WholeStoreViewAccessor : public SourceAccessor
|
||||
|
|
@ -378,3 +389,78 @@ ref<DummyStore> DummyStore::Config::openDummyStore() const
|
|||
static RegisterStoreImplementation<DummyStore::Config> regDummyStore;
|
||||
|
||||
} // namespace nix
|
||||
|
||||
namespace nlohmann {
|
||||
|
||||
using namespace nix;
|
||||
|
||||
DummyStore::PathInfoAndContents adl_serializer<DummyStore::PathInfoAndContents>::from_json(const json & json)
|
||||
{
|
||||
auto & obj = getObject(json);
|
||||
return DummyStore::PathInfoAndContents{
|
||||
.info = valueAt(obj, "info"),
|
||||
.contents = make_ref<MemorySourceAccessor>(valueAt(obj, "contents")),
|
||||
};
|
||||
}
|
||||
|
||||
void adl_serializer<DummyStore::PathInfoAndContents>::to_json(json & json, const DummyStore::PathInfoAndContents & val)
|
||||
{
|
||||
json = {
|
||||
{"info", val.info},
|
||||
{"contents", *val.contents},
|
||||
};
|
||||
}
|
||||
|
||||
ref<DummyStore> adl_serializer<ref<DummyStore>>::from_json(const json & json)
|
||||
{
|
||||
auto & obj = getObject(json);
|
||||
ref<DummyStore> res = [&] {
|
||||
auto cfg = make_ref<DummyStore::Config>(DummyStore::Config::Params{});
|
||||
const_cast<PathSetting &>(cfg->storeDir_).set(getString(valueAt(obj, "store-dir")));
|
||||
cfg->readOnly = true;
|
||||
return cfg->openDummyStore();
|
||||
}();
|
||||
for (auto & [k, v] : getObject(valueAt(obj, "contents")))
|
||||
res->contents.insert({StorePath{k}, v});
|
||||
for (auto & [k0, v] : getObject(valueAt(obj, "build-trace"))) {
|
||||
for (auto & [k1, v2] : getObject(v)) {
|
||||
auto vref = make_ref<UnkeyedRealisation>(v2);
|
||||
res->buildTrace.insert_or_visit(
|
||||
{
|
||||
Hash::parseExplicitFormatUnprefixed(k0, HashAlgorithm::SHA256, HashFormat::Base64),
|
||||
{{k1, vref}},
|
||||
},
|
||||
[&](auto & kv) { kv.second.insert_or_assign(k1, vref); });
|
||||
}
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
void adl_serializer<ref<DummyStore>>::to_json(json & json, const ref<DummyStore> & val)
|
||||
{
|
||||
json = {
|
||||
{"store-dir", val->storeDir},
|
||||
{"contents",
|
||||
[&] {
|
||||
auto obj = json::object();
|
||||
val->contents.cvisit_all([&](const auto & kv) {
|
||||
auto & [k, v] = kv;
|
||||
obj[k.to_string()] = v;
|
||||
});
|
||||
return obj;
|
||||
}()},
|
||||
{"build-trace",
|
||||
[&] {
|
||||
auto obj = json::object();
|
||||
val->buildTrace.cvisit_all([&](const auto & kv) {
|
||||
auto & [k, v] = kv;
|
||||
auto & obj2 = obj[k.to_string(HashFormat::Base64, false)] = json::object();
|
||||
for (auto & [k2, v2] : kv.second)
|
||||
obj2[k2] = *v2;
|
||||
});
|
||||
return obj;
|
||||
}()},
|
||||
};
|
||||
}
|
||||
|
||||
} // namespace nlohmann
|
||||
|
|
|
|||
|
|
@ -23,6 +23,8 @@ struct DummyStore : virtual Store
|
|||
{
|
||||
UnkeyedValidPathInfo info;
|
||||
ref<MemorySourceAccessor> contents;
|
||||
|
||||
bool operator==(const PathInfoAndContents &) const;
|
||||
};
|
||||
|
||||
/**
|
||||
|
|
@ -54,6 +56,14 @@ struct DummyStore : virtual Store
|
|||
, config(config)
|
||||
{
|
||||
}
|
||||
|
||||
bool operator==(const DummyStore &) const;
|
||||
};
|
||||
|
||||
template<>
|
||||
struct json_avoids_null<DummyStore::PathInfoAndContents> : std::true_type
|
||||
{};
|
||||
|
||||
} // namespace nix
|
||||
|
||||
JSON_IMPL(nix::DummyStore::PathInfoAndContents)
|
||||
|
|
|
|||
|
|
@ -2,6 +2,7 @@
|
|||
///@file
|
||||
|
||||
#include "nix/store/store-api.hh"
|
||||
#include "nix/util/json-impls.hh"
|
||||
|
||||
#include <boost/unordered/concurrent_flat_map.hpp>
|
||||
|
||||
|
|
@ -65,4 +66,10 @@ struct DummyStoreConfig : public std::enable_shared_from_this<DummyStoreConfig>,
|
|||
}
|
||||
};
|
||||
|
||||
template<>
|
||||
struct json_avoids_null<ref<nix::DummyStore>> : std::true_type
|
||||
{};
|
||||
|
||||
} // namespace nix
|
||||
|
||||
JSON_IMPL(nix::ref<nix::DummyStore>)
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue