@brief creates a diff as a JSON patch @sa https://json.nlohmann.me/api/basic_json/diff/
| 24124 | /// @brief creates a diff as a JSON patch |
| 24125 | /// @sa https://json.nlohmann.me/api/basic_json/diff/ |
| 24126 | JSON_HEDLEY_WARN_UNUSED_RESULT |
| 24127 | static basic_json diff(const basic_json& source, const basic_json& target, |
| 24128 | const std::string& path = "") |
| 24129 | { |
| 24130 | // the patch |
| 24131 | basic_json result(value_t::array); |
| 24132 | |
| 24133 | // if the values are the same, return empty patch |
| 24134 | if (source == target) |
| 24135 | { |
| 24136 | return result; |
| 24137 | } |
| 24138 | |
| 24139 | if (source.type() != target.type()) |
| 24140 | { |
| 24141 | // different types: replace value |
| 24142 | result.push_back( |
| 24143 | { |
| 24144 | {"op", "replace"}, {"path", path}, {"value", target} |
| 24145 | }); |
| 24146 | return result; |
| 24147 | } |
| 24148 | |
| 24149 | switch (source.type()) |
| 24150 | { |
| 24151 | case value_t::array: |
| 24152 | { |
| 24153 | // first pass: traverse common elements |
| 24154 | std::size_t i = 0; |
| 24155 | while (i < source.size() && i < target.size()) |
| 24156 | { |
| 24157 | // recursive call to compare array values at index i |
| 24158 | auto temp_diff = diff(source[i], target[i], detail::concat(path, '/', std::to_string(i))); |
| 24159 | result.insert(result.end(), temp_diff.begin(), temp_diff.end()); |
| 24160 | ++i; |
| 24161 | } |
| 24162 | |
| 24163 | // We now reached the end of at least one array |
| 24164 | // in a second pass, traverse the remaining elements |
| 24165 | |
| 24166 | // remove my remaining elements |
| 24167 | const auto end_index = static_cast<difference_type>(result.size()); |
| 24168 | while (i < source.size()) |
| 24169 | { |
| 24170 | // add operations in reverse order to avoid invalid |
| 24171 | // indices |
| 24172 | result.insert(result.begin() + end_index, object( |
| 24173 | { |
| 24174 | {"op", "remove"}, |
| 24175 | {"path", detail::concat(path, '/', std::to_string(i))} |
| 24176 | })); |
| 24177 | ++i; |
| 24178 | } |
| 24179 | |
| 24180 | // add other remaining elements |
| 24181 | while (i < target.size()) |
| 24182 | { |
| 24183 | result.push_back( |