summaryrefslogtreecommitdiff
path: root/example/describe.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'example/describe.cpp')
-rw-r--r--example/describe.cpp202
1 files changed, 0 insertions, 202 deletions
diff --git a/example/describe.cpp b/example/describe.cpp
deleted file mode 100644
index 9b00f8b..0000000
--- a/example/describe.cpp
+++ /dev/null
@@ -1,202 +0,0 @@
-//
-// Copyright (c) 2022 Klemens Morgenstern (klemens.morgenstern@gmx.net)
-//
-// Distributed under the Boost Software License, Version 1.0. (See accompanying
-// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
-//
-
-#include <boost/sqlite.hpp>
-#include <boost/unordered_map.hpp>
-#include <boost/describe.hpp>
-#include <boost/variant2/variant.hpp>
-
-#include <iomanip>
-#include <iostream>
-
-// This example shows how a virtual table can be created using boost.describe
-
-using namespace boost;
-
-// add more conversions here if you need more types in the described struct
-void assign_value(std::int64_t & res, sqlite::value val) { res = val.get_int();}
-void assign_value(std::string & res, sqlite::value val) { res = val.get_text();}
-
-template<typename T>
-struct describe_cursor final : sqlite::vtab::cursor<>
-{
- describe_cursor(
- typename boost::unordered_map<sqlite3_int64, T>::const_iterator itr,
- typename boost::unordered_map<sqlite3_int64, T>::const_iterator end
- ) : itr(itr), end(end)
- {
- }
-
- typename boost::unordered_map<sqlite3_int64, T>::const_iterator itr, end;
- constexpr static std::size_t column_count = mp11::mp_size<describe::describe_members<T, describe::mod_any_access>>::value;
-
- sqlite::result<void> next() {itr++; return {};}
- sqlite::result<sqlite3_int64> row_id() {return itr->first;}
-
- void column(sqlite::context<> ctx, int i, bool /* no_change */)
- {
- mp11::mp_with_index<column_count>(
- i, [&](auto Idx)
- {
- using type = mp11::mp_at_c<describe::describe_members<T, describe::mod_public>, Idx>;
- ctx.set_result(itr->second.*type::pointer);
- });
- }
-
- bool eof() noexcept {return itr == end;}
-};
-
-template<typename T>
-struct describe_table final :
- sqlite::vtab::table<describe_cursor<T>>,
- sqlite::vtab::modifiable
-{
- boost::unordered_map<sqlite3_int64, T> &data;
- describe_table(boost::unordered_map<sqlite3_int64, T> &data) : data(data) {}
-
- std::string decl;
- const char * declaration()
- {
- if (!decl.empty())
- return decl.c_str();
- mp11::mp_for_each<describe::describe_members<T, describe::mod_public>>(
- [&](auto elem)
- {
- if (decl.empty())
- decl += "create table x(";
- else
- decl += ", ";
-
- decl += elem.name;
- });
- decl += ");";
- return decl.c_str();
- }
-
-
- sqlite3_int64 last_index = 0;
-
- sqlite::result<describe_cursor<T>> open()
- {
- return describe_cursor<T>{data.begin(), data.end()};
- }
-
- sqlite::result<void> delete_(sqlite::value key)
- {
- data.erase(key.get_int());
- return {};
- }
- sqlite::result<sqlite_int64> insert(sqlite::value key, span<sqlite::value> values, int /*on_conflict*/)
- {
- T res;
- sqlite_int64 id = key.is_null() ? last_index++ : key.get_int();
- auto vtr = values.begin();
- mp11::mp_for_each<describe::describe_members<T, describe::mod_public>>(
- [&](auto elem)
- {
- assign_value(res.*elem.pointer , *vtr);
- vtr++;
- });
-
- auto itr = data.emplace(id, std::move(res)).first;
- return itr->first;
-
- }
- sqlite::result<sqlite_int64> update(sqlite::value old_key, sqlite::value new_key,
- span<sqlite::value> values, int /*on_conflict*/)
- {
- if (new_key.get_int() != old_key.get_int())
- data.erase(old_key.get_int());
- auto & res = data[new_key.get_int()];
-
- auto vtr = values.begin();
- mp11::mp_for_each<describe::describe_members<T, describe::mod_public>>(
- [&](auto elem)
- {
- assign_value(res.*elem.pointer , *vtr);
- vtr++;
- });
- return 0u;
- }
-};
-
-template<typename T>
-struct describe_module final : sqlite::vtab::eponymous_module<describe_table<T>>
-{
- boost::unordered_map<sqlite3_int64, T> data;
- constexpr static std::size_t column_count = mp11::mp_size<describe::describe_members<T, describe::mod_any_access>>::value;
- sqlite::result<describe_table<T>> connect(sqlite::connection ,
- int, const char * const [])
- {
- return describe_table<T>{data};
- }
-};
-
-
-void print_table(std::ostream & str, sqlite::resultset res)
-{
- for (auto i = 0u; i < res.column_count(); i ++)
- str << "| " << std::setfill(' ') << std::setw(15) << res.column_name(i) << " ";
-
- str << "|\n";
-
- for (auto i = 0u; i < res.column_count(); i ++)
- str << "|-----------------";
- str << "|\n";
-
- for (auto && r : res)
- {
- for (auto i = 0u; i < res.column_count(); i ++)
- str << "| " << std::setfill(' ') << std::setw(15) << r.at(i).get_text() << " ";
-
- str << "|\n" ;
- }
- str << std::endl;
-}
-
-
-struct boost_library
-{
- std::string name;
- std::int64_t first_released;
- std::int64_t standard;
-};
-
-BOOST_DESCRIBE_STRUCT(boost_library, (), (name, first_released, standard));
-
-
-int main (int /*argc*/, char * /*argv*/[])
-{
- sqlite::connection conn{":memory:"};
- auto & md = sqlite::create_module(conn, "boost_libraries", describe_module<boost_library>());
-
- {
- auto p = conn.prepare("insert into boost_libraries (name, first_released, standard) values ($name, $version, $std);");
- p.execute({{"name", "process"}, {"version", 64}, {"std", 11}});
- p.execute({{"name", "asio"}, {"version", 35}, {"std", 98}});
- p.execute({{"name", "bimap"}, {"version", 35}, {"std", 98}});
- p.execute({{"name", "circular_buffer"}, {"version", 35}, {"std", 98}});
- p.execute({{"name", "mpi"}, {"version", 35}, {"std", 98}});
- p.execute({{"name", "beast"}, {"version", 66}, {"std", 11}});
- p.execute({{"name", "describe"}, {"version", 77}, {"std", 14}});
- }
-
-
- print_table(std::cout, conn.query("select * from boost_libraries;"));
-
- // same as conn.execute("update boost_libraries set standard = 11 where standard = 98;");
- for (auto & p : md.data)
- if (p.second.standard == 98)
- p.second.standard = 11;
-
- print_table(std::cout, conn.query("select * from boost_libraries;"));
-
- conn.prepare("delete from boost_libraries where name = ?").execute({"mpi"});
- print_table(std::cout, conn.query("select * from boost_libraries;"));
-
- return 0;
-}