3#include <launchdarkly/detail/serialization/json_errors.hpp>
4#include <tl/expected.hpp>
6#include <boost/core/ignore_unused.hpp>
7#include <boost/json.hpp>
10#include <unordered_map>
12namespace launchdarkly {
15tl::expected<std::optional<std::vector<T>>, JsonError> tag_invoke(
16 boost::json::value_to_tag<
17 tl::expected<std::optional<std::vector<T>>, JsonError>>
const& unused,
18 boost::json::value
const& json_value) {
19 boost::ignore_unused(unused);
21 if (json_value.is_null()) {
25 if (!json_value.is_array()) {
26 return tl::unexpected(JsonError::kSchemaFailure);
29 auto const& arr = json_value.as_array();
31 items.reserve(arr.size());
32 for (
auto const& item : arr) {
34 boost::json::value_to<tl::expected<std::optional<T>, JsonError>>(
36 if (!eval_result.has_value()) {
37 return tl::unexpected(eval_result.error());
39 auto maybe_val = eval_result.value();
41 items.emplace_back(std::move(maybe_val.value()));
47tl::expected<std::optional<bool>, JsonError> tag_invoke(
48 boost::json::value_to_tag<
49 tl::expected<std::optional<bool>, JsonError>>
const& unused,
50 boost::json::value
const& json_value);
52tl::expected<std::optional<std::uint64_t>, JsonError> tag_invoke(
53 boost::json::value_to_tag<
54 tl::expected<std::optional<std::uint64_t>, JsonError>>
const& unused,
55 boost::json::value
const& json_value);
57tl::expected<std::optional<std::int64_t>, JsonError> tag_invoke(
58 boost::json::value_to_tag<
59 tl::expected<std::optional<std::int64_t>, JsonError>>
const& unused,
60 boost::json::value
const& json_value);
62tl::expected<std::optional<std::string>, JsonError> tag_invoke(
63 boost::json::value_to_tag<
64 tl::expected<std::optional<std::string>, JsonError>>
const& unused,
65 boost::json::value
const& json_value);
67template <
typename K,
typename V>
68tl::expected<std::optional<std::unordered_map<K, V>>, JsonError> tag_invoke(
69 boost::json::value_to_tag<
70 tl::expected<std::optional<std::unordered_map<K, V>>, JsonError>>
const&
72 boost::json::value
const& json_value) {
73 boost::ignore_unused(unused);
75 if (json_value.is_null()) {
78 if (!json_value.is_object()) {
79 return tl::unexpected(JsonError::kSchemaFailure);
81 auto const& obj = json_value.as_object();
82 std::unordered_map<K, V> descriptors;
83 for (
auto const& pair : obj) {
85 boost::json::value_to<tl::expected<std::optional<V>, JsonError>>(
88 return tl::unexpected(eval_result.error());
90 auto const& maybe_val = eval_result.value();
92 descriptors.emplace(pair.key(), std::move(maybe_val.value()));
108tl::expected<T, JsonError> tag_invoke(
109 boost::json::value_to_tag<tl::expected<T, JsonError>>
const& unused,
110 boost::json::value
const& json_value) {
111 boost::ignore_unused(unused);
113 boost::json::value_to<tl::expected<std::optional<T>, JsonError>>(
115 if (!maybe_val.has_value()) {
116 return tl::unexpected(maybe_val.error());
118 return maybe_val.value().value_or(T());