some progress over building

This commit is contained in:
Blue 2023-09-30 17:13:44 -03:00
parent 0fa8ba6918
commit 4843fcc77f
Signed by: blue
GPG key ID: 9B203B252A63EE38
7 changed files with 228 additions and 27 deletions

View file

@ -3,7 +3,25 @@
#include "collection.h"
constexpr std::string_view masonJSON("mason.json");
constexpr std::string_view dependencies("dependencies");
constexpr std::array<std::string_view, 5> sourceVariants({
"source",
"src",
"from",
"in",
"file"
});
constexpr std::array<std::string_view, 5> targetVariants({
"target",
"dst",
"to",
"out",
"destination"
});
constexpr std::array<std::string_view, Component::done + 1> stringStates {
"initial",
"reading",
@ -22,7 +40,7 @@ constexpr std::array<std::string_view, Component::unknown + 1> stringTypes {
Component::Component(
const std::filesystem::path& path,
const std::weak_ptr<Collection>& collection,
Collection* collection,
const std::shared_ptr<Logger>& logger
):
Loggable(logger),
@ -101,10 +119,9 @@ bool Component::readMasonDependencies(const nlohmann::json& deps, const std::str
return errorScenario(manifestPath + " dependencies are not organized as an array");
for (const nlohmann::json& dep : deps) {
std::shared_ptr<Collection> col = collection.lock();
switch (dep.type()) {
case nlohmann::json::value_t::string:
col->addSource(dep);
collection->addSource(dep);
break;
case nlohmann::json::value_t::object: {
nlohmann::json::const_iterator ditr = dep.find("path");
@ -115,7 +132,7 @@ bool Component::readMasonDependencies(const nlohmann::json& deps, const std::str
if (!path.is_string())
return errorScenario(manifestPath + " object of unexpected format in dependecies");
col->addSource(path);
collection->addSource(path);
}
break;
default:
@ -146,7 +163,7 @@ void Component::build(const std::filesystem::path& destination, const std::strin
buildAsFile(destination);
break;
case directory:
buildAsDiractory(destination);
buildAsDirectory(destination);
break;
case mason:
buildAsMason(destination, target);
@ -154,19 +171,21 @@ void Component::build(const std::filesystem::path& destination, const std::strin
default:
break;
}
}
void Component::buildAsFile(const std::filesystem::path& destination) {
copyFile(location, destination/location.filename());
state = done;
}
void Component::buildAsFile(const std::filesystem::path& destination) {
std::filesystem::copy(location, destination/location.filename());
}
void Component::buildAsDiractory(const std::filesystem::path& destination) {
void Component::buildAsDirectory(const std::filesystem::path& destination) {
std::filesystem::copy(location, destination/location.filename(),
std::filesystem::copy_options::recursive |
std::filesystem::copy_options::overwrite_existing
);
state = done;
}
std::string Component::getLibrariesPath() const {
@ -196,8 +215,160 @@ bool Component::successfullyRead() const {
return state > reading && state != error;
}
bool Component::successfullyBuilt() const {
return state == done;
}
void Component::buildAsMason(const std::filesystem::path& destination, const std::string& target) {
warn("mason build is not implemented yet");
const nlohmann::json& mnfst = manifest.value();
nlohmann::json::const_iterator itr = mnfst.find("build");
if (itr == mnfst.end()) {
warn("Mason project at " + location.string() + " has no \"build\" section in its manifest");
state = done;
return;
}
const nlohmann::json& build = *itr;
if (!build.is_array()) {
warn("Mason project at " + location.string() + " has unexpected \"build\" section in its manifest");
state = done;
return;
}
for (const nlohmann::json& entry : build) {
switch (entry.type()) {
case nlohmann::json::value_t::string:
copyFile(location/entry, destination/entry);
break;
case nlohmann::json::value_t::array:
masonFilesArray(entry, destination);
break;
case nlohmann::json::value_t::object:
if (allowedForTarget(entry, target)) {
nlohmann::json::const_iterator fitr = entry.find("files");
if (fitr != entry.end()) {
const nlohmann::json& files = *fitr;
if (files.is_array())
masonFilesArray(files, destination);
else
warn(std::string("Unexpected ") + entry.type_name()
+ " of files subsection of build section of its manifest in "
+ location.string() + ", ignoring");
}
}
break;
default:
warn(std::string("Unexpected ") + entry.type_name() + " in build section of manifest in " + location.string() + ", ignoring");
break;
}
}
state = done;
}
void Component::copyFile(const std::filesystem::path& from, const std::filesystem::path& to) const {
std::filesystem::create_directories(to.parent_path());
if (std::filesystem::exists(to))
minor("File " + to.string() + " already exists, overwriting from " + from.string());
else
debug("Copying " + from.string() + " to " + to.string());
std::filesystem::copy(from, to, std::filesystem::copy_options::overwrite_existing);
}
void Component::masonFilesArray(const nlohmann::json& files, const std::filesystem::path& destination) {
for (const nlohmann::json& entry : files) {
switch (entry.type()) {
case nlohmann::json::value_t::string:
copyFile(location/entry, destination/entry);
break;
case nlohmann::json::value_t::object: {
std::optional<std::string> src = getFileSource(entry);
if (!src.has_value()) {
warn("Couldn't understand file source processing file array in " + location.string() + ", ignoring");
break;
}
std::optional<std::string> dst = getFileTarget(entry);
if (!src.has_value()) {
warn("Couldn't understand file destination processing file array in " + location.string() + ", ignoring");
break;
}
copyFile(location/src.value(), destination/src.value());
} break;
default:
warn(std::string("Unexpected ") + entry.type_name()
+ " in files subsection of build section of manifest in "
+ location.string() + ", ignoring");
}
}
}
bool Component::allowedForTarget(const nlohmann::json& object, const std::string& target) const {
nlohmann::json::const_iterator itr = object.find("target");
if (itr != object.end()) {
const nlohmann::json& tg = *itr;
if (tg.is_string())
return tg == target;
else
warn("\"target\" in build section has unexpected type, ignoring");
}
itr = object.find("targets");
if (itr != object.end()) {
const nlohmann::json& targets = *itr;
if (targets.is_array()) {
for (const nlohmann::json& entry : targets) {
if (entry.is_string()) {
if (entry == target)
return true;
} else {
warn("one of the targets in \"targets\" in build section has unexpected type, ignoring it");
}
}
return false;
} else {
warn("\"targets\" in build section has unexpected type, ignoring");
}
}
//TODO may be notTarget and notTargets?
return true;
}
std::optional<std::string> Component::getFileSource(const nlohmann::json& object) const {
for (const std::string_view& key : sourceVariants) {
std::optional<std::string> value = tryStringValue(object, key.data());
if (value.has_value())
return value;
}
return std::nullopt;
}
std::optional<std::string> Component::getFileTarget(const nlohmann::json& object) const {
for (const std::string_view& key : targetVariants) {
std::optional<std::string> value = tryStringValue(object, key.data());
if (value.has_value())
return value;
}
return std::nullopt;
}
std::optional<std::string> Component::tryStringValue(const nlohmann::json& object, const std::string& key) {
nlohmann::json::const_iterator itr = object.find(key);
if (itr != object.end()) {
const nlohmann::json& value = *itr;
if (value.is_string())
return value;
}
return std::nullopt;
}
Component::State Component::getState() const {