diff --git a/include/teqp/json_tools.hpp b/include/teqp/json_tools.hpp index 5647b6a2..5f49295d 100644 --- a/include/teqp/json_tools.hpp +++ b/include/teqp/json_tools.hpp @@ -74,7 +74,7 @@ namespace teqp{ 3. A JSON-encoded string */ - inline auto multilevel_JSON_load(const nlohmann::json &j, const std::optional& default_path){ + inline auto multilevel_JSON_load(const nlohmann::json &j, const std::optional& default_path = std::nullopt){ auto is_valid_path = [](const std::string & s){ try{ diff --git a/include/teqp/models/multifluid.hpp b/include/teqp/models/multifluid.hpp index 1dcefbfa..4c5ca9d9 100644 --- a/include/teqp/models/multifluid.hpp +++ b/include/teqp/models/multifluid.hpp @@ -1039,8 +1039,43 @@ inline auto multifluidfactory(const nlohmann::json& spec) { nlohmann::json depcollection = nlohmann::json::array(); if (components.size() > 1){ BIPcollection = multilevel_JSON_load(spec.at("BIP"), root + "/dev/mixtures/mixture_binary_pairs.json"); + if (spec.contains("departure")){ - depcollection = multilevel_JSON_load(spec.at("departure"), root + "/dev/mixtures/mixture_departure_functions.json"); + std::string msg = "departure was provided but is invalid; options are non-empty array, path to file as string, or JSON data encoded as string"; + auto load_departure = [&msg](const nlohmann::json& j){ + if (j.is_array() && j.size() > 0){ + return j; + } + else if (j.is_string()){ + const std::string& s = j; + if (s.find("PATH::") == 0){ + load_a_JSON_file(s.substr(6, s.size()-6)); + } + else{ + try{ + try{ + return multilevel_JSON_load(s); + } + catch(...){ + return nlohmann::json::parse(s); + } + } + catch(...){ + throw teqp::InvalidArgument(msg); + } + } + } + else{ + throw teqp::InvalidArgument(msg); + } + }; + + if (root.empty()){ + depcollection = load_departure(spec.at("departure")); + } + else{ + depcollection = multilevel_JSON_load(spec.at("departure"), root + "/dev/mixtures/mixture_departure_functions.json"); + } } } diff --git a/src/tests/catch_test_multifluid_RPinterop.cxx b/src/tests/catch_test_multifluid_RPinterop.cxx index 9ebdc1a4..c9167261 100644 --- a/src/tests/catch_test_multifluid_RPinterop.cxx +++ b/src/tests/catch_test_multifluid_RPinterop.cxx @@ -107,6 +107,28 @@ TEST_CASE("Check RPinterop conversion Fij instead of F in BIP", "[RPinterop]") { CHECK_THROWS(cppinterface::make_model(j)); } +TEST_CASE("Check RPinterop departure present but empty", "[RPinterop]") { + auto [BIP, DEP] = RPinterop::HMXBNCfile("../doc/source/models/HMX.BNC").make_jsons(); + auto get_w_dep = [&](nlohmann::json dep){ + nlohmann::json model = { + {"components", { + "FLDPATH::../doc/source/models/R152A.FLD", + "FLDPATH::../doc/source/models/NEWR1234YF.FLD"}}, + {"BIP", BIP}, + {"departure", dep} + }; + nlohmann::json j = { + {"kind", "multifluid"}, + {"model", model} + }; + return j; + }; + CHECK_THROWS(cppinterface::make_model(get_w_dep(nullptr))); + CHECK_THROWS(cppinterface::make_model(get_w_dep({}))); + CHECK_NOTHROW(cppinterface::make_model(get_w_dep(DEP))); + CHECK_NOTHROW(cppinterface::make_model(get_w_dep(DEP.dump(1)))); +} + TEST_CASE("Check RPinterop conversion with passing FLDFILE:: prefix for both fluids, specified BIP and null departure function", "[RPinterop]") { auto BIP = R"([{ "hash1": "63f364b0",