1 | //===----------------------------------------------------------------------===// |
2 | // DuckDB |
3 | // |
4 | // duckdb/common/serializer.hpp |
5 | // |
6 | // |
7 | //===----------------------------------------------------------------------===// |
8 | |
9 | #pragma once |
10 | |
11 | #include "duckdb/common/common.hpp" |
12 | #include "duckdb/common/exception.hpp" |
13 | |
14 | namespace duckdb { |
15 | |
16 | //! The Serialize class is a base class that can be used to serializing objects into a binary buffer |
17 | class Serializer { |
18 | public: |
19 | virtual ~Serializer() { |
20 | } |
21 | |
22 | virtual void WriteData(const_data_ptr_t buffer, idx_t write_size) = 0; |
23 | |
24 | template <class T> void Write(T element) { |
25 | WriteData((const_data_ptr_t)&element, sizeof(T)); |
26 | } |
27 | |
28 | void WriteString(const string &val) { |
29 | assert(val.size() <= std::numeric_limits<uint32_t>::max()); |
30 | Write<uint32_t>((uint32_t)val.size()); |
31 | if (val.size() > 0) { |
32 | WriteData((const_data_ptr_t)val.c_str(), val.size()); |
33 | } |
34 | } |
35 | |
36 | template <class T> void WriteList(vector<unique_ptr<T>> &list) { |
37 | assert(list.size() <= std::numeric_limits<uint32_t>::max()); |
38 | Write<uint32_t>((uint32_t)list.size()); |
39 | for (auto &child : list) { |
40 | child->Serialize(*this); |
41 | } |
42 | } |
43 | |
44 | template <class T> void WriteOptional(unique_ptr<T> &element) { |
45 | Write<bool>(element ? true : false); |
46 | if (element) { |
47 | element->Serialize(*this); |
48 | } |
49 | } |
50 | }; |
51 | |
52 | //! The Deserializer class assists in deserializing a binary blob back into an |
53 | //! object |
54 | class Deserializer { |
55 | public: |
56 | virtual ~Deserializer() { |
57 | } |
58 | |
59 | //! Reads [read_size] bytes into the buffer |
60 | virtual void ReadData(data_ptr_t buffer, idx_t read_size) = 0; |
61 | |
62 | template <class T> T Read() { |
63 | T value; |
64 | ReadData((data_ptr_t)&value, sizeof(T)); |
65 | return value; |
66 | } |
67 | |
68 | template <class T> void ReadList(vector<unique_ptr<T>> &list) { |
69 | auto select_count = Read<uint32_t>(); |
70 | for (uint32_t i = 0; i < select_count; i++) { |
71 | auto child = T::Deserialize(*this); |
72 | list.push_back(move(child)); |
73 | } |
74 | } |
75 | |
76 | template <class T> unique_ptr<T> ReadOptional() { |
77 | auto has_entry = Read<bool>(); |
78 | if (has_entry) { |
79 | return T::Deserialize(*this); |
80 | } |
81 | return nullptr; |
82 | } |
83 | }; |
84 | |
85 | template <> string Deserializer::Read(); |
86 | |
87 | } // namespace duckdb |
88 | |