diff --git a/contrib/epee/include/storages/portable_storage_extended_for_doc.h b/contrib/epee/include/storages/portable_storage_extended_for_doc.h index 81e70ed9..6c314664 100644 --- a/contrib/epee/include/storages/portable_storage_extended_for_doc.h +++ b/contrib/epee/include/storages/portable_storage_extended_for_doc.h @@ -29,6 +29,8 @@ #pragma once #include "portable_storage.h" +#include "portable_storage.h" + namespace epee { @@ -51,8 +53,7 @@ namespace epee { TRY_ENTRY(); std::stringstream ss; - - //epee::serialization::dump_as_descriptions(ss, m_root, indent, eol); + epee::serialization::recursive_visitor::dump_as_(ss, m_root, indent); buff = ss.str(); return true; CATCH_ENTRY("portable_storage_base::dump_as_json", false) diff --git a/contrib/epee/include/storages/portable_storage_template_helper.h b/contrib/epee/include/storages/portable_storage_template_helper.h index 841a094a..318ae462 100644 --- a/contrib/epee/include/storages/portable_storage_template_helper.h +++ b/contrib/epee/include/storages/portable_storage_template_helper.h @@ -56,16 +56,16 @@ namespace epee } //----------------------------------------------------------------------------------------------------------- template - bool store_t_to_json(const t_struct& str_in, std::string& json_buff, size_t indent = 0/*, end_of_line_t eol = eol_crlf*/) + bool store_t_to_json(const t_struct& str_in, std::string& json_buff, size_t indent = 0) { portable_storage ps; str_in.store(ps); - ps.dump_as_json(json_buff, indent/*, eol*/); + ps.dump_as_json(json_buff, indent); return true; } //----------------------------------------------------------------------------------------------------------- template - std::string store_t_to_json(const t_struct& str_in, size_t indent = 0, end_of_line_t eol = eol_crlf) + std::string store_t_to_json(const t_struct& str_in, size_t indent = 0) { std::string json_buff; store_t_to_json(str_in, json_buff, indent); diff --git a/contrib/epee/include/storages/portable_storage_to_.h b/contrib/epee/include/storages/portable_storage_to_.h new file mode 100644 index 00000000..cb5ece69 --- /dev/null +++ b/contrib/epee/include/storages/portable_storage_to_.h @@ -0,0 +1,149 @@ +// Copyright (c) 2006-2013, Andrey N. Sabelnikov, www.sabelnikov.net +// All rights reserved. +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are met: +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above copyright +// notice, this list of conditions and the following disclaimer in the +// documentation and/or other materials provided with the distribution. +// * Neither the name of the Andrey N. Sabelnikov nor the +// names of its contributors may be used to endorse or promote products +// derived from this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +// ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +// WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +// DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER BE LIABLE FOR ANY +// DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +// (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +// LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +// ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +// + + + +#pragma once + +#include "misc_language.h" +#include "portable_storage_base.h" + +namespace epee +{ + namespace serialization + { + template + class recursive_visitor + { + public: + template + struct array_entry_store_to_json_visitor : public boost::static_visitor + { + t_stream& m_strm; + size_t m_indent; + + array_entry_store_to_json_visitor(t_stream& strm, size_t indent) + : m_strm(strm) + , m_indent(indent) + {} + + template + void operator()(const array_entry_t& a) + { + + t_strategy_layout_strategy::handle_array_start(m_strm, m_indent); + if (a.m_array.size()) + { + auto last_it = --a.m_array.end(); + for (auto it = a.m_array.begin(); it != a.m_array.end(); it++) + { + dump_as_(m_strm, *it, m_indent); + if (it != last_it) + t_strategy_layout_strategy::handle_array_entry_separator(m_strm, m_indent); + } + } + t_strategy_layout_strategy::handle_array_end(m_strm, m_indent); + } + }; + + template + struct storage_entry_store_to_json_visitor : public boost::static_visitor + { + t_stream& m_strm; + size_t m_indent; + + storage_entry_store_to_json_visitor(t_stream& strm, size_t indent) + : m_strm(strm) + , m_indent(indent) + {} + + //section, array_entry + template + void operator()(const visited_type& v) + { + dump_as_(m_strm, v, m_indent); + } + }; + + template + void static dump_as_(t_stream& strm, const array_entry& ae, size_t indent) + { + array_entry_store_to_json_visitor aesv(strm, indent); + boost::apply_visitor(aesv, ae); + } + + template + void static dump_as_(t_stream& strm, const storage_entry& se, size_t indent) + { + storage_entry_store_to_json_visitor sv(strm, indent); + boost::apply_visitor(sv, se); + } + + template + void static dump_as_(t_stream& strm, const t_type& v, size_t indent) + { + t_strategy_layout_strategy::handle_value(strm, v, indent); + } + + template + void static dump_as_(t_stream& strm, const section& sec, size_t indent) + { + size_t local_indent = indent + 1; + t_strategy_layout_strategy::handle_obj_begin(strm, indent); + t_strategy_layout_strategy::handle_line_break(strm, indent); + + if (sec.m_entries.size()) + { + auto it_last = --sec.m_entries.end(); + for (auto it = sec.m_entries.begin(); it != sec.m_entries.end(); it++) + { + if (constexpr t_strategy_layout_strategy::use_descriptions::value) + { + std::string descr; + auto it_descr = sec.m_descriptions.find(it->first); + if (it_descr != sec.m_descriptions.end()) + descr = it_descr->second; + + t_strategy_layout_strategy::handle_print_key(strm, it->first, descr, local_indent); + } + else + { + t_strategy_layout_strategy::handle_print_key(strm, it->first, local_indent); + } + + dump_as_(strm, it->second, local_indent); + if (it_last != it) + t_strategy_layout_strategy::handle_section_entry_separator(strm, indent); + + t_strategy_layout_strategy::handle_line_break(strm, indent); + } + } + t_strategy_layout_strategy::handle_obj_end(strm, indent); + } + }; + + } +} diff --git a/contrib/epee/include/storages/portable_storage_to_description.h b/contrib/epee/include/storages/portable_storage_to_description.h new file mode 100644 index 00000000..2c9c1c91 --- /dev/null +++ b/contrib/epee/include/storages/portable_storage_to_description.h @@ -0,0 +1,118 @@ +// Copyright (c) 2006-2024, Andrey N. Sabelnikov, www.sabelnikov.net +// All rights reserved. +// +// Redistribution and use in source and binary forms, with or without +// modification, are permitted provided that the following conditions are met: +// * Redistributions of source code must retain the above copyright +// notice, this list of conditions and the following disclaimer. +// * Redistributions in binary form must reproduce the above copyright +// notice, this list of conditions and the following disclaimer in the +// documentation and/or other materials provided with the distribution. +// * Neither the name of the Andrey N. Sabelnikov nor the +// names of its contributors may be used to endorse or promote products +// derived from this software without specific prior written permission. +// +// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND +// ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED +// WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +// DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER BE LIABLE FOR ANY +// DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES +// (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; +// LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND +// ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS +// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +// + + + +#pragma once + +#include "misc_language.h" +#include "portable_storage_base.h" +#include "portable_storage_to_.h" + +namespace epee +{ + namespace serialization + { + inline const char* get_endline(end_of_line_t eol) + { + switch (eol) + { + case eol_lf: return "\n"; + case eol_cr: return "\r"; + case eol_space: return " "; + default: return "\r\n"; + } + } + + inline std::string make_indent(size_t indent) + { + return std::string(indent * 2, ' '); + } + + class strategy_json + { + public: + inline static const char* eol = get_endline(eol_crlf); + //static const end_of_line_t eol = eol_crlf; + + template + static void handle_value(t_stream& strm, const t_type& v, size_t indent) + {} + + template + static void handle_array_start(t_stream& strm, size_t indent) + { + strm << "["; + } + + template + static void handle_array_end(t_stream& strm, size_t indent) + { + strm << "]"; + } + + template + static void handle_obj_begin(t_stream& strm, size_t indent) + {} + + template + static void handle_obj_end(t_stream& strm, size_t indent) + {} + + template + static void handle_print_key(t_stream& strm, const std::string& key, size_t indent) + { + const std::string indent_str = make_indent(indent); + strm << indent_str << "\"" << misc_utils::parse::transform_to_json_escape_sequence(key) << "\"" << ": "; + } + + template + static void handle_print_description(t_stream& strm, const std::string& description, size_t indent) + { + } + + + template + static void handle_section_entry_separator(t_stream& strm, size_t indent) + { + strm << ","; + } + + template + static void handle_array_entry_separator(t_stream& strm, size_t indent) + { + strm << ","; + } + + template + static void handle_line_break(t_stream& strm, size_t indent) + { + strm << eol; + } + }; + + } +} diff --git a/contrib/epee/include/storages/portable_storage_to_json.h b/contrib/epee/include/storages/portable_storage_to_json.h index a118e755..415b4d91 100644 --- a/contrib/epee/include/storages/portable_storage_to_json.h +++ b/contrib/epee/include/storages/portable_storage_to_json.h @@ -30,6 +30,7 @@ #include "misc_language.h" #include "portable_storage_base.h" +#include "portable_storage_to_.h" namespace epee { @@ -54,6 +55,8 @@ namespace epee class strategy_json { public: + typedef std::false_type use_descriptions; + inline static const char* eol = get_endline(eol_crlf); //static const end_of_line_t eol = eol_crlf; template @@ -124,105 +127,22 @@ namespace epee } - - }; - - - template - class recursive_visitor - { - public: template - struct array_entry_store_to_json_visitor : public boost::static_visitor + static void handle_section_entry_separator(t_stream& strm, size_t indent) { - t_stream& m_strm; - size_t m_indent; - - array_entry_store_to_json_visitor(t_stream& strm, size_t indent) - : m_strm(strm) - , m_indent(indent) - {} - - template - void operator()(const array_entry_t& a) - { - - t_strategy_layout_strategy::handle_array_start(m_strm, m_indent); - if (a.m_array.size()) - { - auto last_it = --a.m_array.end(); - for (auto it = a.m_array.begin(); it != a.m_array.end(); it++) - { - dump_as_(m_strm, *it, m_indent); - if (it != last_it) - m_strm << ","; - } - } - t_strategy_layout_strategy::handle_array_end(m_strm, m_indent); - } - }; - - template - struct storage_entry_store_to_json_visitor : public boost::static_visitor - { - t_stream& m_strm; - size_t m_indent; - - storage_entry_store_to_json_visitor(t_stream& strm, size_t indent) - : m_strm(strm) - , m_indent(indent) - {} - - //section, array_entry - template - void operator()(const visited_type& v) - { - dump_as_(m_strm, v, m_indent); - } - }; - - template - void static dump_as_(t_stream& strm, const array_entry& ae, size_t indent) - { - array_entry_store_to_json_visitor aesv(strm, indent); - boost::apply_visitor(aesv, ae); + strm << ","; } template - void static dump_as_(t_stream& strm, const storage_entry& se, size_t indent) + static void handle_array_entry_separator(t_stream& strm, size_t indent) { - storage_entry_store_to_json_visitor sv(strm, indent); - boost::apply_visitor(sv, se); - } - - template - void static dump_as_(t_stream& strm, const t_type& v, size_t indent) - { - t_strategy_layout_strategy::handle_value(strm, v, indent); + strm << ","; } template - void static dump_as_(t_stream& strm, const section& sec, size_t indent) + static void handle_line_break(t_stream& strm, size_t indent) { - - - size_t local_indent = indent + 1; - t_strategy_layout_strategy::handle_obj_begin(strm, indent); - put_eol(); - - if (sec.m_entries.size()) - { - auto it_last = --sec.m_entries.end(); - for (auto it = sec.m_entries.begin(); it != sec.m_entries.end(); it++) - { - t_strategy_layout_strategy::handle_print_key(strm, it->first, local_indent); - dump_as_(strm, it->second, local_indent/*, eol*/); - if (it_last != it) - strm << ","; - put_eol(); - } - } - t_strategy_layout_strategy::handle_obj_end(strm, indent); + strm << eol; } };