rippled
Loading...
Searching...
No Matches
KnownFormats.h
1#pragma once
2
3#include <xrpl/basics/contract.h>
4#include <xrpl/beast/type_name.h>
5#include <xrpl/protocol/SOTemplate.h>
6
7#include <boost/container/flat_map.hpp>
8
9#include <algorithm>
10#include <forward_list>
11
12namespace xrpl {
13
21template <class KeyType, class Derived>
23{
24public:
27 class Item
28 {
29 public:
31 char const* name,
32 KeyType type,
33 std::vector<SOElement> uniqueFields,
34 std::vector<SOElement> commonFields)
35 : soTemplate_(std::move(uniqueFields), std::move(commonFields))
36 , name_(name)
37 , type_(type)
38 {
39 // Verify that KeyType is appropriate.
40 static_assert(
42 "KnownFormats KeyType must be integral or enum.");
43 }
44
47 std::string const&
48 getName() const
49 {
50 return name_;
51 }
52
56 getType() const
57 {
58 return type_;
59 }
60
61 SOTemplate const&
63 {
64 return soTemplate_;
65 }
66
67 private:
71 };
72
77 KnownFormats() : name_(beast::type_name<Derived>())
78 {
79 }
80
85 virtual ~KnownFormats() = default;
86 KnownFormats(KnownFormats const&) = delete;
88 operator=(KnownFormats const&) = delete;
89
98 findTypeByName(std::string const& name) const
99 {
100 if (auto const result = findByName(name))
101 return result->getType();
102 Throw<std::runtime_error>(
103 name_ + ": Unknown format name '" +
104 name.substr(0, std::min(name.size(), std::size_t(32))) + "'");
105 }
106
109 Item const*
110 findByType(KeyType type) const
111 {
112 auto const itr = types_.find(type);
113 if (itr == types_.end())
114 return nullptr;
115 return itr->second;
116 }
117
118 // begin() and end() are provided for testing purposes.
120 begin() const
121 {
122 return formats_.begin();
123 }
124
126 end() const
127 {
128 return formats_.end();
129 }
130
131protected:
134 Item const*
135 findByName(std::string const& name) const
136 {
137 auto const itr = names_.find(name);
138 if (itr == names_.end())
139 return nullptr;
140 return itr->second;
141 }
142
152 Item const&
153 add(char const* name,
154 KeyType type,
155 std::vector<SOElement> uniqueFields,
156 std::vector<SOElement> commonFields = {})
157 {
158 if (auto const item = findByType(type))
159 {
161 std::string("Duplicate key for item '") + name + "': already maps to " +
162 item->getName());
163 }
164
165 formats_.emplace_front(name, type, std::move(uniqueFields), std::move(commonFields));
166 Item const& item{formats_.front()};
167
168 names_[name] = &item;
169 types_[type] = &item;
170
171 return item;
172 }
173
174private:
176
177 // One of the situations where a std::forward_list is useful. We want to
178 // store each Item in a place where its address won't change. So a node-
179 // based container is appropriate. But we don't need searchability.
181
182 boost::container::flat_map<std::string, Item const*> names_;
183 boost::container::flat_map<KeyType, Item const*> types_;
184};
185
186} // namespace xrpl
KeyType getType() const
Retrieve the transaction type this format represents.
Item(char const *name, KeyType type, std::vector< SOElement > uniqueFields, std::vector< SOElement > commonFields)
SOTemplate const & getSOTemplate() const
std::string const name_
std::string const & getName() const
Retrieve the name of the format.
Manages a list of known formats.
virtual ~KnownFormats()=default
Destroy the known formats object.
KnownFormats()
Create the known formats object.
KnownFormats & operator=(KnownFormats const &)=delete
std::forward_list< Item >::const_iterator end() const
KnownFormats(KnownFormats const &)=delete
Item const & add(char const *name, KeyType type, std::vector< SOElement > uniqueFields, std::vector< SOElement > commonFields={})
Add a new format.
std::forward_list< Item > formats_
Item const * findByType(KeyType type) const
Retrieve a format based on its type.
Item const * findByName(std::string const &name) const
Retrieve a format based on its name.
std::forward_list< Item >::const_iterator begin() const
boost::container::flat_map< KeyType, Item const * > types_
boost::container::flat_map< std::string, Item const * > names_
KeyType findTypeByName(std::string const &name) const
Retrieve the type for a format specified by name.
Defines the fields and their attributes within a STObject.
Definition SOTemplate.h:92
T min(T... args)
STL namespace.
Use hash_* containers for keys that do not need a cryptographically secure hashing algorithm.
Definition algorithm.h:5
KeyType
Definition KeyType.h:8
void LogicError(std::string const &how) noexcept
Called when faulty logic causes a broken invariant.
T size(T... args)
T substr(T... args)