libsl3 1.3.51003
A C++ interface for SQLite
Loading...
Searching...
No Matches
dbvalue.hpp
1/******************************************************************************
2 ------------- Copyright (c) 2009-2023 H a r a l d A c h i t z ---------------
3 ---------- < h a r a l d dot a c h i t z at g m a i l dot c o m > ------------
4 ---- This Source Code Form is subject to the terms of the Mozilla Public -----
5 ---- License, v. 2.0. If a copy of the MPL was not distributed with this -----
6 ---------- file, You can obtain one at http://mozilla.org/MPL/2.0/. ----------
7 ******************************************************************************/
8
9#ifndef SL3_DBVALUE_HPP_
10#define SL3_DBVALUE_HPP_
11
12#include <string>
13
14#include <sl3/config.hpp>
15#include <sl3/error.hpp>
16#include <sl3/types.hpp>
17#include <sl3/value.hpp>
18
19// todo after a while, type and storage type become confusing
20// find better name, type should be value type,
21// storage type something else, find better name!
22
23namespace sl3
24{
25 /**
26 * \brief
27 *
28 * This class models the duck typing sqlite uses.
29 * It supports int, real, text, blob and null values.
30 *
31 * The type can be a variant, to support all of the possible types,
32 * or it can be set explicitly to a wanted type.
33 *
34 * Using this type for communication with the database can ensure either
35 * type guarantee or give the flexibility of variant types.
36 *
37 * If a type is of type variant, the storage type can be any of the
38 * supported types, otherwise, if the type is set to a specific type, it
39 * is guaranteed that the type will match, or an exception occurs.
40 *
41 */
42 class LIBSL3_API DbValue
43 {
44 public:
45 /**
46 * \brief Constructor
47 *
48 * Constructs a type and the value is null.
49 *
50 * \param type wanted storage type
51 * If Type::Null is given, the type will be a variant.
52 */
53 DbValue (Type type) noexcept;
54
55 // TODO constructor Value, Value - Type,
56 // would this maybe make the other value c'tors obsolete?
57 // this would be fine
58 // don't like the constructors below anyway; they should take a flag,
59 // variant or not, but not the type
60
61 /** \brief Constructor
62 *
63 * This constructor takes an initialization value, and optionally a type
64 * which can only be Type::Variant or the default one.
65 *
66 *
67 * \throw sl3::ErrTypeMisMatch if given type is incompatible
68 * \param val initial value
69 * \param type wanted type, default set to type but can
70 * be set to DbValue::Variant if wanted
71 */
72 explicit DbValue (int val, Type type = Type::Int);
73
74 /**
75 * \copydoc DbValue(int val, Type type = Type::Int)
76 */
77 explicit DbValue (int64_t val, Type type = Type::Int);
78
79 /**
80 * \copydoc DbValue(int val, Type type = Type::Int)
81 */
82 explicit DbValue (std::string val, Type type = Type::Text);
83
84 /**
85 * \copydoc DbValue(int val, Type type = Type::Int)
86 */
87 explicit DbValue (double val, Type type = Type::Real);
88
89 /**
90 * \copydoc DbValue(int val, Type type = Type::Int)
91 */
92 explicit DbValue (Blob val, Type type = Type::Blob);
93
94 /**
95 * \brief Destructor
96 */
97 ~DbValue () noexcept = default;
98
99 /**
100 * \brief Copy constructor
101 */
102 DbValue (const DbValue&) noexcept = default;
103
104 /**
105 * \brief Move constructor
106 */
107 DbValue (DbValue&&) noexcept = default;
108
109 /** \brief Assignment
110 * \throw sl3::ErrTypeMisMatch if getType is incompatible
111 * \note , only value assignment happens here,
112 * the type does not change; the storage type might change if the type is
113 * a variant.
114 *
115 * \param val new value
116 * \return reference to this
117 */
118 DbValue& operator= (const DbValue& val);
119
120 /**
121 * \copydoc operator=(const DbValue& val)
122 */
123 DbValue& operator= (DbValue&& val);
124
125 /**
126 * \copydoc operator=(const DbValue& val)
127 */
128 DbValue& operator= (int val);
129
130 /**
131 * \copydoc operator=(const DbValue& val)
132 */
133 DbValue& operator= (const int64_t& val);
134
135 /**
136 * \copydoc operator=(const DbValue& val)
137 */
138 DbValue& operator= (const double& val);
139
140 /**
141 * \copydoc operator=(const DbValue& val)
142 */
143 DbValue& operator= (const std::string& val);
144
145 /**
146 * \copydoc operator=(const DbValue& val)
147 */
148 DbValue&
149 operator= (const char* val)
150 {
151 return *this = std::string{val};
152 }
153
154 /**
155 * \copydoc operator=(const DbValue& val)
156 */
157 DbValue& operator= (const Blob& val);
158
159 /**
160 * \copydoc operator=(const DbValue& val)
161 */
162 DbValue& operator= (const Value& val);
163
164 /** \brief Assignment
165 * \throw sl3::ErrTypeMisMatch if getType is incompatible
166 * \note , only value assignment happens here,
167 * the type does not change; the storage type might change if the type is
168 * a variant.
169 * \param val new value
170 */
171 void set (int val);
172
173 /**
174 * \copydoc set(int val)
175 */
176 void set (int64_t val);
177
178 /**
179 * \copydoc set(int val)
180 */
181 void set (const std::string& val);
182
183 /**
184 * \copydoc set(int val)
185 */
186 void set (double val);
187
188 /**
189 * \copydoc set(int val)
190 */
191 void set (const Blob& val);
192
193 /** \brief Value access
194 * \return reference to the underlying Value
195 */
196 const Value& getValue () const noexcept;
197
198 /** \brief Value access
199 * Just a shorter way than getValue.
200 * \return reference to the
201 * underlying Value
202 */
203 const Value&
204 value () const noexcept
205 {
206 return getValue ();
207 };
208
209 /** \brief Value access
210 * \throw sl3::ErrNullValueAccess if value is null.
211 * \throw sl3::ErrTypeMisMatch if getType is incorrect
212 * \return reference to the value
213 */
214 const int64_t& getInt () const;
215
216 /**
217 * \copydoc getInt() const
218 */
219 const double& getReal () const;
220
221 /**
222 * \copydoc getInt() const
223 */
224 const std::string& getText () const;
225
226 /**
227 * \copydoc getInt() const
228 */
229 const Blob& getBlob () const;
230
231 /** \brief Value access with default for a NULL value.
232 *
233 * \throw sl3::ErrTypeMisMatch if getType is incorrect
234 * \param defval default value to return if value is NULL
235 * \return the value or the given defval in case the value is NULL
236 */
237 int64_t getInt (int64_t defval) const;
238
239 /**
240 * \copydoc getInt(int64_t defval) const;
241 */
242 double getReal (double defval) const;
243
244 /**
245 * \copydoc getInt(int64_t defval) const;
246 */
247 std::string getText (const std::string& defval) const;
248
249 /**
250 * \copydoc getInt(int64_t defval) const;
251 */
252 Blob getBlob (const Blob& defval) const;
253
254 /** \brief Value access with default for a NULL and different type value.
255 *
256 * This method will not throw. If the actual value is null or of a
257 * different type, the given default value will be returned.
258 *
259 * \param defval default value to return
260 * \return the value or the given default value if the value needs to be
261 * replaced
262 */
263 int64_t get (int64_t defval) const;
264
265 /**
266 * \copydoc get(int64_t defval) const;
267 */
268 int64_t get (int defval) const;
269
270 /**
271 * \copydoc get(int64_t defval) const;
272 */
273 double get (double defval) const;
274
275 /**
276 * \copydoc get(int64_t defval) const;
277 */
278 std::string get (const std::string& defval) const;
279
280 /**
281 * \copydoc get(int64_t defval) const;
282 */
283 Blob get (const Blob& defval) const;
284
285 /** \brief Moves the current value into the return value
286 *
287 * After calling this function the value will be Null.
288 *
289 * \throw sl3::ErrTypeMisMatch in case of wrong type.
290 * \return The value
291 */
292 std::string ejectText ();
293
294 /**
295 * \copydoc ejectText()
296 */
298
299 /**
300 * \brief Set to NULL
301 */
302 void setNull ();
303
304 /**
305 * \brief Check Null
306 * \return if the value is null
307 */
308 bool isNull () const;
309
310 /**
311 * \brief The Type of the value.
312 *
313 * This is the type with which the Value has been created
314 * and will not change.
315 *
316 * The type might be Type::Variant, so that a DbValue can hold any value,
317 *
318 * or a specific Type to guarantee that only the allowed type is used.
319 *
320 * \return the type
321 */
322 Type dbtype () const;
323
324 /**
325 * \brief Returns the type of the underlying Value
326 *
327 * If getType() is a Variant this property
328 * returns the actual type information, otherwise it will be the same as
329 * type or null.
330 *
331 * \return the type the value actually holds
332 */
333 Type type () const;
334
335 /**
336 * \brief Check if assignment would be OK
337 *
338 * If this function returns true, the other value can
339 * be assigned
340 * because it is type compatible.
341 *
342 * \param other value to check
343 * \return true if the other value can be assigned
344 */
345 bool canAssign (const DbValue& other) const;
346
347 /**
348 * \brief Swap 2 DbValues
349 * \param a first value to swap second value
350 * \param b second value to swap with first
351 */
352 friend void swap (DbValue& a, DbValue& b) noexcept;
353
354 private:
355 Type _type;
356
357 Value _value;
358
359 friend class DbValues;
360
361 void assign (const DbValue& other);
362 };
363
364 /**
365 * \brief Stream op for a DbValue
366 *
367 * \param stm an outstream
368 * \param v the value to stream
369 * \return ostream
370 */
371 LIBSL3_API std::ostream& operator<< (std::ostream& stm,
372 const sl3::DbValue& v);
373
374 /**
375 * \brief equality, including type info
376 *
377 * Check if 2 DbValue instances are of the same type and of the same value.
378 *
379 * \param a first value to compare
380 * \param b second value to compare
381 *
382 * \return true if the type and the current value are equal, false otherwise
383 */
384 bool dbval_type_eq (const DbValue& a, const DbValue& b) noexcept;
385
386 /**
387 * \brief less than, including type info
388 *
389 * Applies following rules which are equal to the sorting rules of sqlite.
390 *
391 * - Type::Null is always less than any other storage type.
392 * - Type::Integer or Type::Real is always less than Type::Text or
393 * Type::Blob
394 * - Type::Text is less than Type::Blob
395 *
396 * The type used is DbValue.getStorageType.
397 *
398 * The comparison of the value itself is implemented via std::less.
399 *
400 * \param a first value to compare
401 * \param b second value to compare
402 *
403 * \returns true if given DbValue a is less than given DbValue b
404 */
405 bool dbval_type_lt (const DbValue& a, const DbValue& b) noexcept;
406
407 /**
408 * \brief equality, ignoring type info
409 *
410 * Compares only the stored value for equality and ignores type information.
411 *
412 * \param a first value to compare
413 * \param b second value to compare
414 * \return the comparison result
415 */
416 bool dbval_eq (const DbValue& a, const DbValue& b) noexcept;
417
418 /**
419 * \brief less than, ignoring type info
420 *
421 * Compares only the stored value and ignores type information.
422 *
423 * \param a first value to compare
424 * \param b second value to compare
425 * \return the comparison result
426 */
427 bool dbval_lt (const DbValue& a, const DbValue& b) noexcept;
428
429}
430
431#endif /* DbValue_HPP_ */
This class models the duck typing sqlite uses. It supports int, real, text, blob and null values.
Definition dbvalue.hpp:43
const Value & value() const noexcept
Value access Just a shorter way than getValue.
Definition dbvalue.hpp:204
void set(int val)
Assignment.
const Blob & getBlob() const
Value access.
const double & getReal() const
Value access.
void setNull()
Set to NULL.
DbValue(std::string val, Type type=Type::Text)
Constructor.
const Value & getValue() const noexcept
Value access.
void set(int64_t val)
Assignment.
std::string get(const std::string &defval) const
Value access with default for a NULL and different type value. ;
int64_t getInt(int64_t defval) const
Value access with default for a NULL value.
int64_t get(int64_t defval) const
Value access with default for a NULL and different type value.
DbValue(Type type) noexcept
Constructor.
int64_t get(int defval) const
Value access with default for a NULL and different type value. ;
double getReal(double defval) const
Value access with default for a NULL value. ;
void set(const Blob &val)
Assignment.
bool isNull() const
Check Null.
DbValue(Blob val, Type type=Type::Blob)
Constructor.
Blob get(const Blob &defval) const
Value access with default for a NULL and different type value. ;
Type dbtype() const
The Type of the value.
DbValue(double val, Type type=Type::Real)
Constructor.
void set(double val)
Assignment.
std::string getText(const std::string &defval) const
Value access with default for a NULL value. ;
double get(double defval) const
Value access with default for a NULL and different type value. ;
const std::string & getText() const
Value access.
Blob getBlob(const Blob &defval) const
Value access with default for a NULL value. ;
Type type() const
Returns the type of the underlying Value.
~DbValue() noexcept=default
Destructor.
void set(const std::string &val)
Assignment.
friend void swap(DbValue &a, DbValue &b) noexcept
Swap 2 DbValues.
std::string ejectText()
Moves the current value into the return value.
const int64_t & getInt() const
Value access.
Blob ejectBlob()
Moves the current value into the return value.
bool canAssign(const DbValue &other) const
Check if assignment would be OK.
DbValue(int val, Type type=Type::Int)
Constructor.
DbValue(int64_t val, Type type=Type::Int)
Constructor.
This class models the duck typing sqlite uses. It supports int, real, text, blob and null values.
Definition value.hpp:32
Namespace of libSL3.
Definition columns.hpp:18
bool dbval_lt(const DbValue &a, const DbValue &b) noexcept
less than, ignoring type info
std::vector< std::byte > Blob
Definition types.hpp:90
Type
Definition types.hpp:30
@ Int
Int value.
Definition types.hpp:32
@ Real
Real value.
Definition types.hpp:33
@ Text
Text value.
Definition types.hpp:34
@ Blob
Blob value.
Definition types.hpp:35
LIBSL3_API std::ostream & operator<<(std::ostream &stm, const sl3::DbValue &v)
Stream op for a DbValue.
bool dbval_eq(const DbValue &a, const DbValue &b) noexcept
equality, ignoring type info
bool dbval_type_lt(const DbValue &a, const DbValue &b) noexcept
less than, including type info
bool dbval_type_eq(const DbValue &a, const DbValue &b) noexcept
equality, including type info
STL namespace.