summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/database/database.hpp7
-rw-r--r--src/database/query.cpp10
-rw-r--r--src/database/query.hpp2
-rw-r--r--src/database/select_query.hpp17
-rw-r--r--src/database/type_to_sql.cpp1
-rw-r--r--src/database/type_to_sql.hpp5
-rw-r--r--src/utils/optional_bool.hpp25
-rw-r--r--tests/database.cpp4
8 files changed, 68 insertions, 3 deletions
diff --git a/src/database/database.hpp b/src/database/database.hpp
index 1ad62fc..28b6b1b 100644
--- a/src/database/database.hpp
+++ b/src/database/database.hpp
@@ -7,6 +7,8 @@
#include <database/column.hpp>
#include <database/count_query.hpp>
+#include <utils/optional_bool.hpp>
+
#include <chrono>
#include <string>
@@ -82,6 +84,9 @@ class Database
static constexpr auto options = "";
RecordHistory(): Column<bool>(true) {}};
+ struct RecordHistoryOptional: Column<OptionalBool> { static constexpr auto name = "recordHistory_";
+ static constexpr auto options = ""; };
+
struct VerifyCert: Column<bool> { static constexpr auto name = "verifyCert_";
static constexpr auto options = "";
VerifyCert(): Column<bool>(true) {} };
@@ -99,7 +104,7 @@ class Database
using IrcServerOptionsTable = Table<Id, Owner, Server, Pass, AfterConnectionCommand, TlsPorts, Ports, Username, Realname, VerifyCert, TrustedFingerprint, EncodingOut, EncodingIn, MaxHistoryLength>;
using IrcServerOptions = IrcServerOptionsTable::RowType;
- using IrcChannelOptionsTable = Table<Id, Owner, Server, Channel, EncodingOut, EncodingIn, MaxHistoryLength, Persistent>;
+ using IrcChannelOptionsTable = Table<Id, Owner, Server, Channel, EncodingOut, EncodingIn, MaxHistoryLength, Persistent, RecordHistoryOptional>;
using IrcChannelOptions = IrcChannelOptionsTable::RowType;
Database() = default;
diff --git a/src/database/query.cpp b/src/database/query.cpp
index fb8c055..e6cf072 100644
--- a/src/database/query.cpp
+++ b/src/database/query.cpp
@@ -9,3 +9,13 @@ void actual_add_param(Query& query, const std::string& val)
{
query.params.push_back(val);
}
+
+void actual_add_param(Query& query, const OptionalBool& val)
+{
+ if (!val.is_set)
+ query.params.push_back("0");
+ else if (val.value)
+ query.params.push_back("1");
+ else
+ query.params.push_back("-1");
+} \ No newline at end of file
diff --git a/src/database/query.hpp b/src/database/query.hpp
index 42eeda2..d9638f7 100644
--- a/src/database/query.hpp
+++ b/src/database/query.hpp
@@ -1,5 +1,6 @@
#pragma once
+#include <utils/optional_bool.hpp>
#include <database/statement.hpp>
#include <database/column.hpp>
@@ -49,3 +50,4 @@ void actual_add_param(Query& query, const T& val)
}
void actual_add_param(Query& query, const std::string& val);
+void actual_add_param(Query& query, const OptionalBool& val);
diff --git a/src/database/select_query.hpp b/src/database/select_query.hpp
index 93d69ed..837b064 100644
--- a/src/database/select_query.hpp
+++ b/src/database/select_query.hpp
@@ -5,6 +5,8 @@
#include <logger/logger.hpp>
#include <database/row.hpp>
+#include <utils/optional_bool.hpp>
+
#include <vector>
#include <string>
@@ -20,7 +22,7 @@ extract_row_value(Statement& statement, const int i)
}
template <typename T>
-typename std::enable_if<std::is_same<std::string, T>::value, std::string>::type
+typename std::enable_if<std::is_same<std::string, T>::value, T>::type
extract_row_value(Statement& statement, const int i)
{
const auto size = sqlite3_column_bytes(statement.get(), i);
@@ -29,6 +31,19 @@ extract_row_value(Statement& statement, const int i)
return result;
}
+template <typename T>
+typename std::enable_if<std::is_same<OptionalBool, T>::value, T>::type
+extract_row_value(Statement& statement, const int i)
+{
+ const auto integer = sqlite3_column_int(statement.get(), i);
+ OptionalBool result;
+ if (integer > 0)
+ result.set_value(true);
+ else if (integer < 0)
+ result.set_value(false);
+ return result;
+}
+
template <std::size_t N=0, typename... T>
typename std::enable_if<N < sizeof...(T), void>::type
extract_row_values(Row<T...>& row, Statement& statement)
diff --git a/src/database/type_to_sql.cpp b/src/database/type_to_sql.cpp
index 0b26185..bcd9daa 100644
--- a/src/database/type_to_sql.cpp
+++ b/src/database/type_to_sql.cpp
@@ -6,3 +6,4 @@ template <> const std::string TypeToSQLType<long>::type = "INTEGER";
template <> const std::string TypeToSQLType<long long>::type = "INTEGER";
template <> const std::string TypeToSQLType<bool>::type = "INTEGER";
template <> const std::string TypeToSQLType<std::string>::type = "TEXT";
+template <> const std::string TypeToSQLType<OptionalBool>::type = "INTEGER"; \ No newline at end of file
diff --git a/src/database/type_to_sql.hpp b/src/database/type_to_sql.hpp
index 1942268..ba806ab 100644
--- a/src/database/type_to_sql.hpp
+++ b/src/database/type_to_sql.hpp
@@ -1,5 +1,7 @@
#pragma once
+#include <utils/optional_bool.hpp>
+
#include <string>
template <typename T>
@@ -10,4 +12,5 @@ template <> const std::string TypeToSQLType<std::size_t>::type;
template <> const std::string TypeToSQLType<long>::type;
template <> const std::string TypeToSQLType<long long>::type;
template <> const std::string TypeToSQLType<bool>::type;
-template <> const std::string TypeToSQLType<std::string>::type; \ No newline at end of file
+template <> const std::string TypeToSQLType<std::string>::type;
+template <> const std::string TypeToSQLType<OptionalBool>::type; \ No newline at end of file
diff --git a/src/utils/optional_bool.hpp b/src/utils/optional_bool.hpp
new file mode 100644
index 0000000..824e76d
--- /dev/null
+++ b/src/utils/optional_bool.hpp
@@ -0,0 +1,25 @@
+#pragma once
+
+#include <string>
+
+struct OptionalBool
+{
+ OptionalBool() = default;
+
+ OptionalBool(bool value):
+ is_set(true), value(value) {}
+
+ void set_value(bool value)
+ {
+ this->is_set = true;
+ this->value = value;
+ }
+
+ void unset()
+ {
+ this->is_set = false;
+ }
+
+ bool is_set{false};
+ bool value{false};
+};
diff --git a/tests/database.cpp b/tests/database.cpp
index 47dfd7c..f49220a 100644
--- a/tests/database.cpp
+++ b/tests/database.cpp
@@ -33,9 +33,13 @@ TEST_CASE("Database")
CHECK(o.col<Database::EncodingIn>() == "");
o.col<Database::EncodingIn>() = "ISO-8859-1";
+ CHECK(o.col<Database::RecordHistoryOptional>().is_set == false);
+ o.col<Database::RecordHistoryOptional>().set_value(false);
o.save(Database::db);
auto b = Database::get_irc_channel_options("zouzou@example.com", "irc.example.com", "#foo");
CHECK(o.col<Database::EncodingIn>() == "ISO-8859-1");
+ CHECK(o.col<Database::RecordHistoryOptional>().is_set == true);
+ CHECK(o.col<Database::RecordHistoryOptional>().value == false);
}
SECTION("Channel options with server default")