#include "database.h" #include #include #include #include #include Database::Database(const std::string &conninfo) { try { connection_ = std::make_unique(conninfo); if (!connection_->is_open()) { throw std::runtime_error("Konnte DB-Verbindung nicht öffnen!"); } } catch (const std::exception &e) { std::cerr << "[Database] Fehler beim Verbinden: " << e.what() << std::endl; throw; } } std::vector> Database::query(const std::string &sql) { std::vector> rows; try { pqxx::work txn(*connection_); pqxx::result r = txn.exec(sql); txn.commit(); for (auto row : r) { std::map oneRow; for (auto f = 0u; f < row.size(); f++) { std::string colName = r.column_name(f); std::string value = row[f].c_str() ? row[f].c_str() : ""; oneRow[colName] = value; } rows.push_back(std::move(oneRow)); } } catch (const std::exception &ex) { std::cerr << "[Database] query-Fehler: " << ex.what() << "\nSQL: " << sql << std::endl; } return rows; } void Database::prepare(const std::string &stmtName, const std::string &sql) { try { pqxx::work txn(*connection_); txn.conn().prepare(stmtName, sql); txn.commit(); } catch (const std::exception &ex) { std::cerr << "[Database] prepare-Fehler: " << ex.what() << "\nSQL: " << sql << std::endl; } } Database::FieldList Database::execute(const std::string &stmtName, const std::vector ¶ms) { std::vector> rows; try { pqxx::work txn(*connection_); pqxx::prepare::invocation inv = txn.prepared(stmtName); for (auto &p : params) { inv(p); } pqxx::result r = inv.exec(); txn.commit(); for (const auto &row : r) { std::unordered_map mapRow; for (pqxx::row::size_type i = 0; i < row.size(); ++i) { std::string colName = r.column_name(i); mapRow[colName] = row[i].c_str() ? row[i].c_str() : ""; } rows.push_back(std::move(mapRow)); } } catch (const std::exception &ex) { std::cerr << "[Database] execute-Fehler: " << ex.what() << "\nStatement: " << stmtName << std::endl; } return rows; } void Database::remove(const std::string &stmtName) { pqxx::work txn(*connection_); txn.conn().unprepare(stmtName); txn.commit(); } bool Database::isValid() const { try { if (!connection_ || !connection_->is_open()) { return false; } pqxx::work txn(*connection_); txn.exec("SELECT 1"); // Einfacher Ping txn.commit(); return true; } catch (const std::exception &ex) { std::cerr << "[Database] Verbindung ungültig: " << ex.what() << "\n"; return false; } }