You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

90 lines
2.5 KiB

  1. #include "Schema.h"
  2. #include <io/debug.h>
  3. #include "migrations/1624829187_create_events.h"
  4. #include "migrations/1624964657_create_alarms.h"
  5. namespace db {
  6. namespace db_builder = db::migrations::builder;
  7. Schema::Schema(sql::Database* db) : m_db(db) {
  8. }
  9. uint32_t Schema::get_user_version() const {
  10. try {
  11. int user_version = m_db->execAndGet("PRAGMA user_version;");
  12. return user_version;
  13. } catch (std::exception& e) {
  14. std::cout << "Exception: " << e.what() << std::endl;
  15. return -1;
  16. }
  17. }
  18. void Schema::set_user_version(uint32_t version) {
  19. try {
  20. m_db->exec("PRAGMA user_version = " + std::to_string(version) + ";");
  21. m_user_version = version;
  22. } catch (std::exception& e) {
  23. std::cout << "Exception: " << e.what() << std::endl;
  24. }
  25. }
  26. void Schema::set_savepoint() {
  27. try {
  28. m_db->exec("BEGIN;");
  29. m_db->exec("SAVEPOINT " + m_migration_savepoint + ";");
  30. } catch (std::exception& e) {
  31. std::cout << "Exception: " << e.what() << std::endl;
  32. }
  33. }
  34. void Schema::rollback_migrations() {
  35. try {
  36. m_db->exec("ROLLBACK TO " + m_migration_savepoint + ";");
  37. } catch (std::exception& e) {
  38. std::cout << "Exception: " << e.what() << std::endl;
  39. }
  40. }
  41. void Schema::commit_migrations() {
  42. try {
  43. m_db->exec("COMMIT;");
  44. } catch (std::exception& e) {
  45. std::cout << "Exception: " << e.what() << std::endl;
  46. }
  47. }
  48. uint32_t Schema::run_migrations() {
  49. assemble_migrations();
  50. if(migrations.begin() == migrations.end()) {
  51. DEBUG << "No migrations found...";
  52. return ERROR_NO_MIGRATIONS;
  53. }
  54. set_savepoint();
  55. uint32_t user_version = get_user_version();
  56. for(auto const& [epoch, migration] : migrations) {
  57. if(epoch <= user_version) {
  58. DEBUG << "Skipping: " << migration->get_migration_name();
  59. continue;
  60. }
  61. std::cout << "migrating: " << migration->get_migration_name() << std::endl;
  62. try {
  63. m_db->exec(migration->get_statement());
  64. } catch (std::exception& e) {
  65. std::cout << "Exception: " << e.what() << std::endl;
  66. std::cout << "Rolling back migrations..." << std::endl;
  67. rollback_migrations();
  68. return ERROR_FAULTY_MIGRATION;
  69. }
  70. }
  71. commit_migrations();
  72. set_user_version(migrations.rbegin()->first);
  73. return 0;
  74. }
  75. void Schema::assemble_migrations() {
  76. migrations.emplace(1624829187, new db::migrations::m1624829187_create_events());
  77. migrations.emplace(1624964657, new db::migrations::m1624964657_create_alarms());
  78. }
  79. }