|
29 | 29 |
|
30 | 30 | using namespace Database;
|
31 | 31 |
|
32 |
| -Connection::Connection(const std::string &connectionString) |
33 |
| - : internalConnection(std::make_unique<pqxx::connection>(connectionString)) {} |
| 32 | +Connection::Connection(const std::string &connectionString) { |
| 33 | + try { |
| 34 | + internalConnection = std::make_unique<pqxx::connection>(connectionString); |
| 35 | + } catch (const pqxx::broken_connection &e) { |
| 36 | + throw std::runtime_error("Failed to connect to the database: " + std::string(e.what())); |
| 37 | + } catch (const std::exception &e) { |
| 38 | + throw std::runtime_error("Unexpected error while initializing database connection: " + std::string(e.what())); |
| 39 | + } |
| 40 | +} |
34 | 41 |
|
35 | 42 | void Connection::beginTransaction() {
|
36 | 43 | if (!internalConnection) {
|
37 | 44 | throw std::domain_error("Transaction not possible while internal connection is not set.");
|
38 | 45 | }
|
39 | 46 |
|
40 | 47 | rollbackTransaction();
|
41 |
| - transaction = std::make_unique<pqxx::transaction<>>(*internalConnection); |
| 48 | + |
| 49 | + try { |
| 50 | + transaction = std::make_unique<pqxx::transaction<>>(*internalConnection); |
| 51 | + } catch (const pqxx::broken_connection &e) { |
| 52 | + throw std::runtime_error("Failed to begin transaction: " + std::string(e.what())); |
| 53 | + } catch (const std::exception &e) { |
| 54 | + throw std::runtime_error("Unexpected error while starting transaction: " + std::string(e.what())); |
| 55 | + } |
42 | 56 | }
|
43 | 57 |
|
44 | 58 | void Connection::commitTransaction() {
|
45 |
| - if (transaction) { |
46 |
| - transaction->commit(); |
47 |
| - transaction.reset(); |
| 59 | + try { |
| 60 | + if (transaction) { |
| 61 | + transaction->commit(); |
| 62 | + transaction.reset(); |
| 63 | + } |
| 64 | + } catch (const pqxx::broken_connection &e) { |
| 65 | + throw std::runtime_error("Failed to commit transaction: " + std::string(e.what())); |
| 66 | + } catch (const std::exception &e) { |
| 67 | + throw std::runtime_error("Unexpected error during transaction commit: " + std::string(e.what())); |
48 | 68 | }
|
49 | 69 | }
|
50 | 70 |
|
51 | 71 | void Connection::rollbackTransaction() {
|
52 |
| - if (transaction) { |
53 |
| - transaction->abort(); |
54 |
| - transaction.reset(); |
| 72 | + try { |
| 73 | + if (transaction) { |
| 74 | + transaction->abort(); |
| 75 | + transaction.reset(); |
| 76 | + } |
| 77 | + } catch (const pqxx::broken_connection &e) { |
| 78 | + std::cerr << "Warning: Failed to rollback transaction (connection issue): " << e.what() << std::endl; |
| 79 | + } catch (const std::exception &e) { |
| 80 | + std::cerr << "Warning: Unexpected error during transaction rollback: " << e.what() << std::endl; |
55 | 81 | }
|
56 | 82 | }
|
57 | 83 |
|
58 | 84 | auto Connection::query(const std::string &query) -> pqxx::result {
|
59 |
| - if (transaction) { |
60 |
| - return transaction->exec(query); |
| 85 | + const int max_retries = 3; |
| 86 | + int retries = 0; |
| 87 | + |
| 88 | + while (retries < max_retries) { |
| 89 | + try { |
| 90 | + if (transaction) { |
| 91 | + return transaction->exec(query); |
| 92 | + } |
| 93 | + throw std::domain_error("No active transaction"); |
| 94 | + } catch (const pqxx::broken_connection &e) { |
| 95 | + retries++; |
| 96 | + if (retries >= max_retries) { |
| 97 | + throw std::runtime_error("Database connection error after retries: " + std::string(e.what())); |
| 98 | + } |
| 99 | + std::cerr << "Retrying database query (" << retries << "/" << max_retries << "): " << e.what() << std::endl; |
| 100 | + std::this_thread::sleep_for(std::chrono::seconds(1)); // Wait before retrying |
| 101 | + } catch (const std::exception &e) { |
| 102 | + throw std::runtime_error("Unexpected error during query execution: " + std::string(e.what())); |
| 103 | + } |
61 | 104 | }
|
62 | 105 |
|
63 |
| - throw std::domain_error("No active transaction"); |
| 106 | + // Fallback return (though retries should handle most cases) |
| 107 | + return pqxx::result{}; |
64 | 108 | }
|
65 | 109 |
|
66 | 110 | auto Connection::streamTo(pqxx::table_path path, std::initializer_list<std::string_view> columns) -> pqxx::stream_to {
|
|
0 commit comments