// Squawk messenger. // Copyright (C) 2019 Yury Gubich // // This program is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by // the Free Software Foundation, either version 3 of the License, or // (at your option) any later version. // // This program is distributed in the hope that it will be useful, // but WITHOUT ANY WARRANTY; without even the implied warranty of // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the // GNU General Public License for more details. // // You should have received a copy of the GNU General Public License // along with this program. If not, see . #ifndef CORE_TABLE_HPP #define CORE_TABLE_HPP #include "table.h" #include "exceptions.h" template Core::DataBase::Table::Table(const std::string& p_name, Core::DataBase* parent): _Table(p_name, parent), keySerializer(), valueSerializer() { } template Core::DataBase::Table::~Table() { } template void Core::DataBase::Table::addRecord(const K& key, const V& value) { if (!db->opened) { throw Closed("addRecord", db->name, name); } MDB_val lmdbKey = keySerializer.setData(key); MDB_val lmdbData = valueSerializer.setData(value); MDB_txn *txn; mdb_txn_begin(db->environment, NULL, 0, &txn); int rc; rc = mdb_put(txn, dbi, &lmdbKey, &lmdbData, MDB_NOOVERWRITE); if (rc != 0) { mdb_txn_abort(txn); if (rc == MDB_KEYEXIST) { throw Exist(std::to_string(key), db->name, name); } else { throw Unknown(db->name, mdb_strerror(rc), name); } } else { mdb_txn_commit(txn); } } template void Core::DataBase::Table::changeRecord(const K& key, const V& value) { if (!db->opened) { throw Closed("changeRecord", db->name, name); } MDB_val lmdbKey = keySerializer.setData(key); MDB_val lmdbData = valueSerializer.setData(value); MDB_txn *txn; mdb_txn_begin(db->environment, NULL, 0, &txn); int rc; rc = mdb_put(txn, dbi, &lmdbKey, &lmdbData, 0); if (rc != 0) { mdb_txn_abort(txn); if (rc) { throw Unknown(db->name, mdb_strerror(rc), name); } } else { mdb_txn_commit(txn); } } template V Core::DataBase::Table::getRecord(const K& key) const { if (!db->opened) { throw Closed("getRecord", db->name, name); } MDB_val lmdbKey = keySerializer.setData(key); MDB_val lmdbData; MDB_txn *txn; int rc; mdb_txn_begin(db->environment, NULL, MDB_RDONLY, &txn); rc = mdb_get(txn, dbi, &lmdbKey, &lmdbData); if (rc) { mdb_txn_abort(txn); if (rc == MDB_NOTFOUND) { throw NotFound(std::to_string(key), db->name, name); } else { throw Unknown(db->name, mdb_strerror(rc), name); } } else { V value; lmdbData >> value; mdb_txn_abort(txn); return value; } } template void Core::DataBase::Table::removeRecord(const K& key) { if (!db->opened) { throw Closed("removeRecord", db->name, name); } MDB_val lmdbKey = keySerializer.setData(key); MDB_txn *txn; int rc; mdb_txn_begin(db->environment, NULL, 0, &txn); rc = mdb_del(txn, dbi, &lmdbKey, NULL); if (rc) { mdb_txn_abort(txn); if (rc == MDB_NOTFOUND) { throw NotFound(std::to_string(key), db->name, name); } else { throw Unknown(db->name, mdb_strerror(rc), name); } } else { mdb_txn_commit(txn); } } std::string std::to_string(const QString& str) { return str.toStdString(); } #endif //CORE_TABLE_HPP