diff --git a/common/database/database_update_manifest_bots.cpp b/common/database/database_update_manifest_bots.cpp index 563ce69f7..3616969ff 100644 --- a/common/database/database_update_manifest_bots.cpp +++ b/common/database/database_update_manifest_bots.cpp @@ -104,6 +104,25 @@ ALTER TABLE `bot_timers` DROP PRIMARY KEY; ALTER TABLE `bot_timers` ADD PRIMARY KEY (`bot_id`, `timer_id`, `spell_id`, `item_id`); +)" + }, + ManifestEntry{ + .version = 9042, + .description = "2024_01_27_delete_bot_foreign_keys.sql", + .check = "SHOW CREATE TABLE `bot_stances`", + .condition = "contains", + .match = "FOREIGN", + .sql = R"( +ALTER TABLE `bot_buffs` DROP FOREIGN KEY `FK_bot_buffs_1`; +ALTER TABLE `bot_heal_rotations` DROP FOREIGN KEY `FK_bot_heal_rotations`; +ALTER TABLE `bot_heal_rotation_members` DROP FOREIGN KEY `FK_bot_heal_rotation_members_1`; +ALTER TABLE `bot_heal_rotation_members` DROP FOREIGN KEY `FK_bot_heal_rotation_members_2`; +ALTER TABLE `bot_heal_rotation_targets` DROP FOREIGN KEY `FK_bot_heal_rotation_targets`; +ALTER TABLE `bot_inventories` DROP FOREIGN KEY `FK_bot_inventories_1`; +ALTER TABLE `bot_pets` DROP FOREIGN KEY `FK_bot_pets_1`; +ALTER TABLE `bot_pet_buffs` DROP FOREIGN KEY `FK_bot_pet_buffs_1`; +ALTER TABLE `bot_pet_inventories` DROP FOREIGN KEY `FK_bot_pet_inventories_1`; +ALTER TABLE `bot_stances` DROP FOREIGN KEY `FK_bot_stances_1`; )" } // -- template; copy/paste this when you need to create a new entry diff --git a/common/repositories/base/base_bot_buffs_repository.h b/common/repositories/base/base_bot_buffs_repository.h index 729f4363c..a4e226c49 100644 --- a/common/repositories/base/base_bot_buffs_repository.h +++ b/common/repositories/base/base_bot_buffs_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_BUFFS_REPOSITORY_H @@ -180,8 +180,9 @@ public: { auto results = db.QueryDatabase( fmt::format( - "{} WHERE id = {} LIMIT 1", + "{} WHERE {} = {} LIMIT 1", BaseSelect(), + PrimaryKey(), bot_buffs_id ) ); @@ -190,26 +191,26 @@ public: if (results.RowCount() == 1) { BotBuffs e{}; - e.buffs_index = static_cast(strtoul(row[0], nullptr, 10)); - e.bot_id = static_cast(strtoul(row[1], nullptr, 10)); - e.spell_id = static_cast(strtoul(row[2], nullptr, 10)); - e.caster_level = static_cast(strtoul(row[3], nullptr, 10)); - e.duration_formula = static_cast(strtoul(row[4], nullptr, 10)); - e.tics_remaining = static_cast(strtoul(row[5], nullptr, 10)); - e.poison_counters = static_cast(strtoul(row[6], nullptr, 10)); - e.disease_counters = static_cast(strtoul(row[7], nullptr, 10)); - e.curse_counters = static_cast(strtoul(row[8], nullptr, 10)); - e.corruption_counters = static_cast(strtoul(row[9], nullptr, 10)); - e.numhits = static_cast(strtoul(row[10], nullptr, 10)); - e.melee_rune = static_cast(strtoul(row[11], nullptr, 10)); - e.magic_rune = static_cast(strtoul(row[12], nullptr, 10)); - e.dot_rune = static_cast(strtoul(row[13], nullptr, 10)); - e.persistent = static_cast(atoi(row[14])); - e.caston_x = static_cast(atoi(row[15])); - e.caston_y = static_cast(atoi(row[16])); - e.caston_z = static_cast(atoi(row[17])); - e.extra_di_chance = static_cast(strtoul(row[18], nullptr, 10)); - e.instrument_mod = static_cast(atoi(row[19])); + e.buffs_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.bot_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.spell_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.caster_level = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.duration_formula = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.tics_remaining = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; + e.poison_counters = row[6] ? static_cast(strtoul(row[6], nullptr, 10)) : 0; + e.disease_counters = row[7] ? static_cast(strtoul(row[7], nullptr, 10)) : 0; + e.curse_counters = row[8] ? static_cast(strtoul(row[8], nullptr, 10)) : 0; + e.corruption_counters = row[9] ? static_cast(strtoul(row[9], nullptr, 10)) : 0; + e.numhits = row[10] ? static_cast(strtoul(row[10], nullptr, 10)) : 0; + e.melee_rune = row[11] ? static_cast(strtoul(row[11], nullptr, 10)) : 0; + e.magic_rune = row[12] ? static_cast(strtoul(row[12], nullptr, 10)) : 0; + e.dot_rune = row[13] ? static_cast(strtoul(row[13], nullptr, 10)) : 0; + e.persistent = row[14] ? static_cast(atoi(row[14])) : 0; + e.caston_x = row[15] ? static_cast(atoi(row[15])) : 0; + e.caston_y = row[16] ? static_cast(atoi(row[16])) : 0; + e.caston_z = row[17] ? static_cast(atoi(row[17])) : 0; + e.extra_di_chance = row[18] ? static_cast(strtoul(row[18], nullptr, 10)) : 0; + e.instrument_mod = row[19] ? static_cast(atoi(row[19])) : 10; return e; } @@ -385,26 +386,26 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotBuffs e{}; - e.buffs_index = static_cast(strtoul(row[0], nullptr, 10)); - e.bot_id = static_cast(strtoul(row[1], nullptr, 10)); - e.spell_id = static_cast(strtoul(row[2], nullptr, 10)); - e.caster_level = static_cast(strtoul(row[3], nullptr, 10)); - e.duration_formula = static_cast(strtoul(row[4], nullptr, 10)); - e.tics_remaining = static_cast(strtoul(row[5], nullptr, 10)); - e.poison_counters = static_cast(strtoul(row[6], nullptr, 10)); - e.disease_counters = static_cast(strtoul(row[7], nullptr, 10)); - e.curse_counters = static_cast(strtoul(row[8], nullptr, 10)); - e.corruption_counters = static_cast(strtoul(row[9], nullptr, 10)); - e.numhits = static_cast(strtoul(row[10], nullptr, 10)); - e.melee_rune = static_cast(strtoul(row[11], nullptr, 10)); - e.magic_rune = static_cast(strtoul(row[12], nullptr, 10)); - e.dot_rune = static_cast(strtoul(row[13], nullptr, 10)); - e.persistent = static_cast(atoi(row[14])); - e.caston_x = static_cast(atoi(row[15])); - e.caston_y = static_cast(atoi(row[16])); - e.caston_z = static_cast(atoi(row[17])); - e.extra_di_chance = static_cast(strtoul(row[18], nullptr, 10)); - e.instrument_mod = static_cast(atoi(row[19])); + e.buffs_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.bot_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.spell_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.caster_level = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.duration_formula = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.tics_remaining = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; + e.poison_counters = row[6] ? static_cast(strtoul(row[6], nullptr, 10)) : 0; + e.disease_counters = row[7] ? static_cast(strtoul(row[7], nullptr, 10)) : 0; + e.curse_counters = row[8] ? static_cast(strtoul(row[8], nullptr, 10)) : 0; + e.corruption_counters = row[9] ? static_cast(strtoul(row[9], nullptr, 10)) : 0; + e.numhits = row[10] ? static_cast(strtoul(row[10], nullptr, 10)) : 0; + e.melee_rune = row[11] ? static_cast(strtoul(row[11], nullptr, 10)) : 0; + e.magic_rune = row[12] ? static_cast(strtoul(row[12], nullptr, 10)) : 0; + e.dot_rune = row[13] ? static_cast(strtoul(row[13], nullptr, 10)) : 0; + e.persistent = row[14] ? static_cast(atoi(row[14])) : 0; + e.caston_x = row[15] ? static_cast(atoi(row[15])) : 0; + e.caston_y = row[16] ? static_cast(atoi(row[16])) : 0; + e.caston_z = row[17] ? static_cast(atoi(row[17])) : 0; + e.extra_di_chance = row[18] ? static_cast(strtoul(row[18], nullptr, 10)) : 0; + e.instrument_mod = row[19] ? static_cast(atoi(row[19])) : 10; all_entries.push_back(e); } @@ -429,26 +430,26 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotBuffs e{}; - e.buffs_index = static_cast(strtoul(row[0], nullptr, 10)); - e.bot_id = static_cast(strtoul(row[1], nullptr, 10)); - e.spell_id = static_cast(strtoul(row[2], nullptr, 10)); - e.caster_level = static_cast(strtoul(row[3], nullptr, 10)); - e.duration_formula = static_cast(strtoul(row[4], nullptr, 10)); - e.tics_remaining = static_cast(strtoul(row[5], nullptr, 10)); - e.poison_counters = static_cast(strtoul(row[6], nullptr, 10)); - e.disease_counters = static_cast(strtoul(row[7], nullptr, 10)); - e.curse_counters = static_cast(strtoul(row[8], nullptr, 10)); - e.corruption_counters = static_cast(strtoul(row[9], nullptr, 10)); - e.numhits = static_cast(strtoul(row[10], nullptr, 10)); - e.melee_rune = static_cast(strtoul(row[11], nullptr, 10)); - e.magic_rune = static_cast(strtoul(row[12], nullptr, 10)); - e.dot_rune = static_cast(strtoul(row[13], nullptr, 10)); - e.persistent = static_cast(atoi(row[14])); - e.caston_x = static_cast(atoi(row[15])); - e.caston_y = static_cast(atoi(row[16])); - e.caston_z = static_cast(atoi(row[17])); - e.extra_di_chance = static_cast(strtoul(row[18], nullptr, 10)); - e.instrument_mod = static_cast(atoi(row[19])); + e.buffs_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.bot_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.spell_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.caster_level = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.duration_formula = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.tics_remaining = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; + e.poison_counters = row[6] ? static_cast(strtoul(row[6], nullptr, 10)) : 0; + e.disease_counters = row[7] ? static_cast(strtoul(row[7], nullptr, 10)) : 0; + e.curse_counters = row[8] ? static_cast(strtoul(row[8], nullptr, 10)) : 0; + e.corruption_counters = row[9] ? static_cast(strtoul(row[9], nullptr, 10)) : 0; + e.numhits = row[10] ? static_cast(strtoul(row[10], nullptr, 10)) : 0; + e.melee_rune = row[11] ? static_cast(strtoul(row[11], nullptr, 10)) : 0; + e.magic_rune = row[12] ? static_cast(strtoul(row[12], nullptr, 10)) : 0; + e.dot_rune = row[13] ? static_cast(strtoul(row[13], nullptr, 10)) : 0; + e.persistent = row[14] ? static_cast(atoi(row[14])) : 0; + e.caston_x = row[15] ? static_cast(atoi(row[15])) : 0; + e.caston_y = row[16] ? static_cast(atoi(row[16])) : 0; + e.caston_z = row[17] ? static_cast(atoi(row[17])) : 0; + e.extra_di_chance = row[18] ? static_cast(strtoul(row[18], nullptr, 10)) : 0; + e.instrument_mod = row[19] ? static_cast(atoi(row[19])) : 10; all_entries.push_back(e); } @@ -507,6 +508,100 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotBuffs &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.buffs_index)); + v.push_back(std::to_string(e.bot_id)); + v.push_back(std::to_string(e.spell_id)); + v.push_back(std::to_string(e.caster_level)); + v.push_back(std::to_string(e.duration_formula)); + v.push_back(std::to_string(e.tics_remaining)); + v.push_back(std::to_string(e.poison_counters)); + v.push_back(std::to_string(e.disease_counters)); + v.push_back(std::to_string(e.curse_counters)); + v.push_back(std::to_string(e.corruption_counters)); + v.push_back(std::to_string(e.numhits)); + v.push_back(std::to_string(e.melee_rune)); + v.push_back(std::to_string(e.magic_rune)); + v.push_back(std::to_string(e.dot_rune)); + v.push_back(std::to_string(e.persistent)); + v.push_back(std::to_string(e.caston_x)); + v.push_back(std::to_string(e.caston_y)); + v.push_back(std::to_string(e.caston_z)); + v.push_back(std::to_string(e.extra_di_chance)); + v.push_back(std::to_string(e.instrument_mod)); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.buffs_index)); + v.push_back(std::to_string(e.bot_id)); + v.push_back(std::to_string(e.spell_id)); + v.push_back(std::to_string(e.caster_level)); + v.push_back(std::to_string(e.duration_formula)); + v.push_back(std::to_string(e.tics_remaining)); + v.push_back(std::to_string(e.poison_counters)); + v.push_back(std::to_string(e.disease_counters)); + v.push_back(std::to_string(e.curse_counters)); + v.push_back(std::to_string(e.corruption_counters)); + v.push_back(std::to_string(e.numhits)); + v.push_back(std::to_string(e.melee_rune)); + v.push_back(std::to_string(e.magic_rune)); + v.push_back(std::to_string(e.dot_rune)); + v.push_back(std::to_string(e.persistent)); + v.push_back(std::to_string(e.caston_x)); + v.push_back(std::to_string(e.caston_y)); + v.push_back(std::to_string(e.caston_z)); + v.push_back(std::to_string(e.extra_di_chance)); + v.push_back(std::to_string(e.instrument_mod)); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_BUFFS_REPOSITORY_H diff --git a/common/repositories/base/base_bot_create_combinations_repository.h b/common/repositories/base/base_bot_create_combinations_repository.h index 1f096db5b..a759d08f4 100644 --- a/common/repositories/base/base_bot_create_combinations_repository.h +++ b/common/repositories/base/base_bot_create_combinations_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_CREATE_COMBINATIONS_REPOSITORY_H @@ -108,8 +108,9 @@ public: { auto results = db.QueryDatabase( fmt::format( - "{} WHERE id = {} LIMIT 1", + "{} WHERE {} = {} LIMIT 1", BaseSelect(), + PrimaryKey(), bot_create_combinations_id ) ); @@ -118,8 +119,8 @@ public: if (results.RowCount() == 1) { BotCreateCombinations e{}; - e.race = static_cast(strtoul(row[0], nullptr, 10)); - e.classes = static_cast(strtoul(row[1], nullptr, 10)); + e.race = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.classes = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; return e; } @@ -242,8 +243,8 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotCreateCombinations e{}; - e.race = static_cast(strtoul(row[0], nullptr, 10)); - e.classes = static_cast(strtoul(row[1], nullptr, 10)); + e.race = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.classes = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -268,8 +269,8 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotCreateCombinations e{}; - e.race = static_cast(strtoul(row[0], nullptr, 10)); - e.classes = static_cast(strtoul(row[1], nullptr, 10)); + e.race = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.classes = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -328,6 +329,64 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotCreateCombinations &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.race)); + v.push_back(std::to_string(e.classes)); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.race)); + v.push_back(std::to_string(e.classes)); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_CREATE_COMBINATIONS_REPOSITORY_H diff --git a/common/repositories/base/base_bot_data_repository.h b/common/repositories/base/base_bot_data_repository.h index b4d2c47b2..2e30936b3 100644 --- a/common/repositories/base/base_bot_data_repository.h +++ b/common/repositories/base/base_bot_data_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_DATA_REPOSITORY_H @@ -278,7 +278,7 @@ public: e.expansion_bitmask = -1; e.enforce_spell_settings = 0; e.archery_setting = 0; - e.caster_range = 0; + e.caster_range = 300; return e; } @@ -315,57 +315,57 @@ public: if (results.RowCount() == 1) { BotData e{}; - e.bot_id = static_cast(strtoul(row[0], nullptr, 10)); - e.owner_id = static_cast(strtoul(row[1], nullptr, 10)); - e.spells_id = static_cast(strtoul(row[2], nullptr, 10)); + e.bot_id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.owner_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.spells_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; e.name = row[3] ? row[3] : ""; e.last_name = row[4] ? row[4] : ""; e.title = row[5] ? row[5] : ""; e.suffix = row[6] ? row[6] : ""; - e.zone_id = static_cast(atoi(row[7])); - e.gender = static_cast(atoi(row[8])); - e.race = static_cast(atoi(row[9])); - e.class_ = static_cast(atoi(row[10])); - e.level = static_cast(strtoul(row[11], nullptr, 10)); - e.deity = static_cast(strtoul(row[12], nullptr, 10)); - e.creation_day = static_cast(strtoul(row[13], nullptr, 10)); - e.last_spawn = static_cast(strtoul(row[14], nullptr, 10)); - e.time_spawned = static_cast(strtoul(row[15], nullptr, 10)); - e.size = strtof(row[16], nullptr); - e.face = static_cast(atoi(row[17])); - e.hair_color = static_cast(atoi(row[18])); - e.hair_style = static_cast(atoi(row[19])); - e.beard = static_cast(atoi(row[20])); - e.beard_color = static_cast(atoi(row[21])); - e.eye_color_1 = static_cast(atoi(row[22])); - e.eye_color_2 = static_cast(atoi(row[23])); - e.drakkin_heritage = static_cast(atoi(row[24])); - e.drakkin_tattoo = static_cast(atoi(row[25])); - e.drakkin_details = static_cast(atoi(row[26])); - e.ac = static_cast(atoi(row[27])); - e.atk = static_cast(atoi(row[28])); - e.hp = static_cast(atoi(row[29])); - e.mana = static_cast(atoi(row[30])); - e.str = static_cast(atoi(row[31])); - e.sta = static_cast(atoi(row[32])); - e.cha = static_cast(atoi(row[33])); - e.dex = static_cast(atoi(row[34])); - e.int_ = static_cast(atoi(row[35])); - e.agi = static_cast(atoi(row[36])); - e.wis = static_cast(atoi(row[37])); - e.fire = static_cast(atoi(row[38])); - e.cold = static_cast(atoi(row[39])); - e.magic = static_cast(atoi(row[40])); - e.poison = static_cast(atoi(row[41])); - e.disease = static_cast(atoi(row[42])); - e.corruption = static_cast(atoi(row[43])); - e.show_helm = static_cast(strtoul(row[44], nullptr, 10)); - e.follow_distance = static_cast(strtoul(row[45], nullptr, 10)); - e.stop_melee_level = static_cast(strtoul(row[46], nullptr, 10)); - e.expansion_bitmask = static_cast(atoi(row[47])); - e.enforce_spell_settings = static_cast(strtoul(row[48], nullptr, 10)); - e.archery_setting = static_cast(strtoul(row[49], nullptr, 10)); - e.caster_range = static_cast(strtoul(row[50], nullptr, 10)); + e.zone_id = row[7] ? static_cast(atoi(row[7])) : 0; + e.gender = row[8] ? static_cast(atoi(row[8])) : 0; + e.race = row[9] ? static_cast(atoi(row[9])) : 0; + e.class_ = row[10] ? static_cast(atoi(row[10])) : 0; + e.level = row[11] ? static_cast(strtoul(row[11], nullptr, 10)) : 0; + e.deity = row[12] ? static_cast(strtoul(row[12], nullptr, 10)) : 0; + e.creation_day = row[13] ? static_cast(strtoul(row[13], nullptr, 10)) : 0; + e.last_spawn = row[14] ? static_cast(strtoul(row[14], nullptr, 10)) : 0; + e.time_spawned = row[15] ? static_cast(strtoul(row[15], nullptr, 10)) : 0; + e.size = row[16] ? strtof(row[16], nullptr) : 0; + e.face = row[17] ? static_cast(atoi(row[17])) : 1; + e.hair_color = row[18] ? static_cast(atoi(row[18])) : 1; + e.hair_style = row[19] ? static_cast(atoi(row[19])) : 1; + e.beard = row[20] ? static_cast(atoi(row[20])) : 0; + e.beard_color = row[21] ? static_cast(atoi(row[21])) : 1; + e.eye_color_1 = row[22] ? static_cast(atoi(row[22])) : 1; + e.eye_color_2 = row[23] ? static_cast(atoi(row[23])) : 1; + e.drakkin_heritage = row[24] ? static_cast(atoi(row[24])) : 0; + e.drakkin_tattoo = row[25] ? static_cast(atoi(row[25])) : 0; + e.drakkin_details = row[26] ? static_cast(atoi(row[26])) : 0; + e.ac = row[27] ? static_cast(atoi(row[27])) : 0; + e.atk = row[28] ? static_cast(atoi(row[28])) : 0; + e.hp = row[29] ? static_cast(atoi(row[29])) : 0; + e.mana = row[30] ? static_cast(atoi(row[30])) : 0; + e.str = row[31] ? static_cast(atoi(row[31])) : 75; + e.sta = row[32] ? static_cast(atoi(row[32])) : 75; + e.cha = row[33] ? static_cast(atoi(row[33])) : 75; + e.dex = row[34] ? static_cast(atoi(row[34])) : 75; + e.int_ = row[35] ? static_cast(atoi(row[35])) : 75; + e.agi = row[36] ? static_cast(atoi(row[36])) : 75; + e.wis = row[37] ? static_cast(atoi(row[37])) : 75; + e.fire = row[38] ? static_cast(atoi(row[38])) : 0; + e.cold = row[39] ? static_cast(atoi(row[39])) : 0; + e.magic = row[40] ? static_cast(atoi(row[40])) : 0; + e.poison = row[41] ? static_cast(atoi(row[41])) : 0; + e.disease = row[42] ? static_cast(atoi(row[42])) : 0; + e.corruption = row[43] ? static_cast(atoi(row[43])) : 0; + e.show_helm = row[44] ? static_cast(strtoul(row[44], nullptr, 10)) : 0; + e.follow_distance = row[45] ? static_cast(strtoul(row[45], nullptr, 10)) : 200; + e.stop_melee_level = row[46] ? static_cast(strtoul(row[46], nullptr, 10)) : 255; + e.expansion_bitmask = row[47] ? static_cast(atoi(row[47])) : -1; + e.enforce_spell_settings = row[48] ? static_cast(strtoul(row[48], nullptr, 10)) : 0; + e.archery_setting = row[49] ? static_cast(strtoul(row[49], nullptr, 10)) : 0; + e.caster_range = row[50] ? static_cast(strtoul(row[50], nullptr, 10)) : 300; return e; } @@ -634,57 +634,57 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotData e{}; - e.bot_id = static_cast(strtoul(row[0], nullptr, 10)); - e.owner_id = static_cast(strtoul(row[1], nullptr, 10)); - e.spells_id = static_cast(strtoul(row[2], nullptr, 10)); + e.bot_id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.owner_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.spells_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; e.name = row[3] ? row[3] : ""; e.last_name = row[4] ? row[4] : ""; e.title = row[5] ? row[5] : ""; e.suffix = row[6] ? row[6] : ""; - e.zone_id = static_cast(atoi(row[7])); - e.gender = static_cast(atoi(row[8])); - e.race = static_cast(atoi(row[9])); - e.class_ = static_cast(atoi(row[10])); - e.level = static_cast(strtoul(row[11], nullptr, 10)); - e.deity = static_cast(strtoul(row[12], nullptr, 10)); - e.creation_day = static_cast(strtoul(row[13], nullptr, 10)); - e.last_spawn = static_cast(strtoul(row[14], nullptr, 10)); - e.time_spawned = static_cast(strtoul(row[15], nullptr, 10)); - e.size = strtof(row[16], nullptr); - e.face = static_cast(atoi(row[17])); - e.hair_color = static_cast(atoi(row[18])); - e.hair_style = static_cast(atoi(row[19])); - e.beard = static_cast(atoi(row[20])); - e.beard_color = static_cast(atoi(row[21])); - e.eye_color_1 = static_cast(atoi(row[22])); - e.eye_color_2 = static_cast(atoi(row[23])); - e.drakkin_heritage = static_cast(atoi(row[24])); - e.drakkin_tattoo = static_cast(atoi(row[25])); - e.drakkin_details = static_cast(atoi(row[26])); - e.ac = static_cast(atoi(row[27])); - e.atk = static_cast(atoi(row[28])); - e.hp = static_cast(atoi(row[29])); - e.mana = static_cast(atoi(row[30])); - e.str = static_cast(atoi(row[31])); - e.sta = static_cast(atoi(row[32])); - e.cha = static_cast(atoi(row[33])); - e.dex = static_cast(atoi(row[34])); - e.int_ = static_cast(atoi(row[35])); - e.agi = static_cast(atoi(row[36])); - e.wis = static_cast(atoi(row[37])); - e.fire = static_cast(atoi(row[38])); - e.cold = static_cast(atoi(row[39])); - e.magic = static_cast(atoi(row[40])); - e.poison = static_cast(atoi(row[41])); - e.disease = static_cast(atoi(row[42])); - e.corruption = static_cast(atoi(row[43])); - e.show_helm = static_cast(strtoul(row[44], nullptr, 10)); - e.follow_distance = static_cast(strtoul(row[45], nullptr, 10)); - e.stop_melee_level = static_cast(strtoul(row[46], nullptr, 10)); - e.expansion_bitmask = static_cast(atoi(row[47])); - e.enforce_spell_settings = static_cast(strtoul(row[48], nullptr, 10)); - e.archery_setting = static_cast(strtoul(row[49], nullptr, 10)); - e.caster_range = static_cast(strtoul(row[50], nullptr, 10)); + e.zone_id = row[7] ? static_cast(atoi(row[7])) : 0; + e.gender = row[8] ? static_cast(atoi(row[8])) : 0; + e.race = row[9] ? static_cast(atoi(row[9])) : 0; + e.class_ = row[10] ? static_cast(atoi(row[10])) : 0; + e.level = row[11] ? static_cast(strtoul(row[11], nullptr, 10)) : 0; + e.deity = row[12] ? static_cast(strtoul(row[12], nullptr, 10)) : 0; + e.creation_day = row[13] ? static_cast(strtoul(row[13], nullptr, 10)) : 0; + e.last_spawn = row[14] ? static_cast(strtoul(row[14], nullptr, 10)) : 0; + e.time_spawned = row[15] ? static_cast(strtoul(row[15], nullptr, 10)) : 0; + e.size = row[16] ? strtof(row[16], nullptr) : 0; + e.face = row[17] ? static_cast(atoi(row[17])) : 1; + e.hair_color = row[18] ? static_cast(atoi(row[18])) : 1; + e.hair_style = row[19] ? static_cast(atoi(row[19])) : 1; + e.beard = row[20] ? static_cast(atoi(row[20])) : 0; + e.beard_color = row[21] ? static_cast(atoi(row[21])) : 1; + e.eye_color_1 = row[22] ? static_cast(atoi(row[22])) : 1; + e.eye_color_2 = row[23] ? static_cast(atoi(row[23])) : 1; + e.drakkin_heritage = row[24] ? static_cast(atoi(row[24])) : 0; + e.drakkin_tattoo = row[25] ? static_cast(atoi(row[25])) : 0; + e.drakkin_details = row[26] ? static_cast(atoi(row[26])) : 0; + e.ac = row[27] ? static_cast(atoi(row[27])) : 0; + e.atk = row[28] ? static_cast(atoi(row[28])) : 0; + e.hp = row[29] ? static_cast(atoi(row[29])) : 0; + e.mana = row[30] ? static_cast(atoi(row[30])) : 0; + e.str = row[31] ? static_cast(atoi(row[31])) : 75; + e.sta = row[32] ? static_cast(atoi(row[32])) : 75; + e.cha = row[33] ? static_cast(atoi(row[33])) : 75; + e.dex = row[34] ? static_cast(atoi(row[34])) : 75; + e.int_ = row[35] ? static_cast(atoi(row[35])) : 75; + e.agi = row[36] ? static_cast(atoi(row[36])) : 75; + e.wis = row[37] ? static_cast(atoi(row[37])) : 75; + e.fire = row[38] ? static_cast(atoi(row[38])) : 0; + e.cold = row[39] ? static_cast(atoi(row[39])) : 0; + e.magic = row[40] ? static_cast(atoi(row[40])) : 0; + e.poison = row[41] ? static_cast(atoi(row[41])) : 0; + e.disease = row[42] ? static_cast(atoi(row[42])) : 0; + e.corruption = row[43] ? static_cast(atoi(row[43])) : 0; + e.show_helm = row[44] ? static_cast(strtoul(row[44], nullptr, 10)) : 0; + e.follow_distance = row[45] ? static_cast(strtoul(row[45], nullptr, 10)) : 200; + e.stop_melee_level = row[46] ? static_cast(strtoul(row[46], nullptr, 10)) : 255; + e.expansion_bitmask = row[47] ? static_cast(atoi(row[47])) : -1; + e.enforce_spell_settings = row[48] ? static_cast(strtoul(row[48], nullptr, 10)) : 0; + e.archery_setting = row[49] ? static_cast(strtoul(row[49], nullptr, 10)) : 0; + e.caster_range = row[50] ? static_cast(strtoul(row[50], nullptr, 10)) : 300; all_entries.push_back(e); } @@ -709,57 +709,57 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotData e{}; - e.bot_id = static_cast(strtoul(row[0], nullptr, 10)); - e.owner_id = static_cast(strtoul(row[1], nullptr, 10)); - e.spells_id = static_cast(strtoul(row[2], nullptr, 10)); + e.bot_id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.owner_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.spells_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; e.name = row[3] ? row[3] : ""; e.last_name = row[4] ? row[4] : ""; e.title = row[5] ? row[5] : ""; e.suffix = row[6] ? row[6] : ""; - e.zone_id = static_cast(atoi(row[7])); - e.gender = static_cast(atoi(row[8])); - e.race = static_cast(atoi(row[9])); - e.class_ = static_cast(atoi(row[10])); - e.level = static_cast(strtoul(row[11], nullptr, 10)); - e.deity = static_cast(strtoul(row[12], nullptr, 10)); - e.creation_day = static_cast(strtoul(row[13], nullptr, 10)); - e.last_spawn = static_cast(strtoul(row[14], nullptr, 10)); - e.time_spawned = static_cast(strtoul(row[15], nullptr, 10)); - e.size = strtof(row[16], nullptr); - e.face = static_cast(atoi(row[17])); - e.hair_color = static_cast(atoi(row[18])); - e.hair_style = static_cast(atoi(row[19])); - e.beard = static_cast(atoi(row[20])); - e.beard_color = static_cast(atoi(row[21])); - e.eye_color_1 = static_cast(atoi(row[22])); - e.eye_color_2 = static_cast(atoi(row[23])); - e.drakkin_heritage = static_cast(atoi(row[24])); - e.drakkin_tattoo = static_cast(atoi(row[25])); - e.drakkin_details = static_cast(atoi(row[26])); - e.ac = static_cast(atoi(row[27])); - e.atk = static_cast(atoi(row[28])); - e.hp = static_cast(atoi(row[29])); - e.mana = static_cast(atoi(row[30])); - e.str = static_cast(atoi(row[31])); - e.sta = static_cast(atoi(row[32])); - e.cha = static_cast(atoi(row[33])); - e.dex = static_cast(atoi(row[34])); - e.int_ = static_cast(atoi(row[35])); - e.agi = static_cast(atoi(row[36])); - e.wis = static_cast(atoi(row[37])); - e.fire = static_cast(atoi(row[38])); - e.cold = static_cast(atoi(row[39])); - e.magic = static_cast(atoi(row[40])); - e.poison = static_cast(atoi(row[41])); - e.disease = static_cast(atoi(row[42])); - e.corruption = static_cast(atoi(row[43])); - e.show_helm = static_cast(strtoul(row[44], nullptr, 10)); - e.follow_distance = static_cast(strtoul(row[45], nullptr, 10)); - e.stop_melee_level = static_cast(strtoul(row[46], nullptr, 10)); - e.expansion_bitmask = static_cast(atoi(row[47])); - e.enforce_spell_settings = static_cast(strtoul(row[48], nullptr, 10)); - e.archery_setting = static_cast(strtoul(row[49], nullptr, 10)); - e.caster_range = static_cast(strtoul(row[50], nullptr, 10)); + e.zone_id = row[7] ? static_cast(atoi(row[7])) : 0; + e.gender = row[8] ? static_cast(atoi(row[8])) : 0; + e.race = row[9] ? static_cast(atoi(row[9])) : 0; + e.class_ = row[10] ? static_cast(atoi(row[10])) : 0; + e.level = row[11] ? static_cast(strtoul(row[11], nullptr, 10)) : 0; + e.deity = row[12] ? static_cast(strtoul(row[12], nullptr, 10)) : 0; + e.creation_day = row[13] ? static_cast(strtoul(row[13], nullptr, 10)) : 0; + e.last_spawn = row[14] ? static_cast(strtoul(row[14], nullptr, 10)) : 0; + e.time_spawned = row[15] ? static_cast(strtoul(row[15], nullptr, 10)) : 0; + e.size = row[16] ? strtof(row[16], nullptr) : 0; + e.face = row[17] ? static_cast(atoi(row[17])) : 1; + e.hair_color = row[18] ? static_cast(atoi(row[18])) : 1; + e.hair_style = row[19] ? static_cast(atoi(row[19])) : 1; + e.beard = row[20] ? static_cast(atoi(row[20])) : 0; + e.beard_color = row[21] ? static_cast(atoi(row[21])) : 1; + e.eye_color_1 = row[22] ? static_cast(atoi(row[22])) : 1; + e.eye_color_2 = row[23] ? static_cast(atoi(row[23])) : 1; + e.drakkin_heritage = row[24] ? static_cast(atoi(row[24])) : 0; + e.drakkin_tattoo = row[25] ? static_cast(atoi(row[25])) : 0; + e.drakkin_details = row[26] ? static_cast(atoi(row[26])) : 0; + e.ac = row[27] ? static_cast(atoi(row[27])) : 0; + e.atk = row[28] ? static_cast(atoi(row[28])) : 0; + e.hp = row[29] ? static_cast(atoi(row[29])) : 0; + e.mana = row[30] ? static_cast(atoi(row[30])) : 0; + e.str = row[31] ? static_cast(atoi(row[31])) : 75; + e.sta = row[32] ? static_cast(atoi(row[32])) : 75; + e.cha = row[33] ? static_cast(atoi(row[33])) : 75; + e.dex = row[34] ? static_cast(atoi(row[34])) : 75; + e.int_ = row[35] ? static_cast(atoi(row[35])) : 75; + e.agi = row[36] ? static_cast(atoi(row[36])) : 75; + e.wis = row[37] ? static_cast(atoi(row[37])) : 75; + e.fire = row[38] ? static_cast(atoi(row[38])) : 0; + e.cold = row[39] ? static_cast(atoi(row[39])) : 0; + e.magic = row[40] ? static_cast(atoi(row[40])) : 0; + e.poison = row[41] ? static_cast(atoi(row[41])) : 0; + e.disease = row[42] ? static_cast(atoi(row[42])) : 0; + e.corruption = row[43] ? static_cast(atoi(row[43])) : 0; + e.show_helm = row[44] ? static_cast(strtoul(row[44], nullptr, 10)) : 0; + e.follow_distance = row[45] ? static_cast(strtoul(row[45], nullptr, 10)) : 200; + e.stop_melee_level = row[46] ? static_cast(strtoul(row[46], nullptr, 10)) : 255; + e.expansion_bitmask = row[47] ? static_cast(atoi(row[47])) : -1; + e.enforce_spell_settings = row[48] ? static_cast(strtoul(row[48], nullptr, 10)) : 0; + e.archery_setting = row[49] ? static_cast(strtoul(row[49], nullptr, 10)) : 0; + e.caster_range = row[50] ? static_cast(strtoul(row[50], nullptr, 10)) : 300; all_entries.push_back(e); } @@ -818,6 +818,162 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotData &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.bot_id)); + v.push_back(std::to_string(e.owner_id)); + v.push_back(std::to_string(e.spells_id)); + v.push_back("'" + Strings::Escape(e.name) + "'"); + v.push_back("'" + Strings::Escape(e.last_name) + "'"); + v.push_back("'" + Strings::Escape(e.title) + "'"); + v.push_back("'" + Strings::Escape(e.suffix) + "'"); + v.push_back(std::to_string(e.zone_id)); + v.push_back(std::to_string(e.gender)); + v.push_back(std::to_string(e.race)); + v.push_back(std::to_string(e.class_)); + v.push_back(std::to_string(e.level)); + v.push_back(std::to_string(e.deity)); + v.push_back(std::to_string(e.creation_day)); + v.push_back(std::to_string(e.last_spawn)); + v.push_back(std::to_string(e.time_spawned)); + v.push_back(std::to_string(e.size)); + v.push_back(std::to_string(e.face)); + v.push_back(std::to_string(e.hair_color)); + v.push_back(std::to_string(e.hair_style)); + v.push_back(std::to_string(e.beard)); + v.push_back(std::to_string(e.beard_color)); + v.push_back(std::to_string(e.eye_color_1)); + v.push_back(std::to_string(e.eye_color_2)); + v.push_back(std::to_string(e.drakkin_heritage)); + v.push_back(std::to_string(e.drakkin_tattoo)); + v.push_back(std::to_string(e.drakkin_details)); + v.push_back(std::to_string(e.ac)); + v.push_back(std::to_string(e.atk)); + v.push_back(std::to_string(e.hp)); + v.push_back(std::to_string(e.mana)); + v.push_back(std::to_string(e.str)); + v.push_back(std::to_string(e.sta)); + v.push_back(std::to_string(e.cha)); + v.push_back(std::to_string(e.dex)); + v.push_back(std::to_string(e.int_)); + v.push_back(std::to_string(e.agi)); + v.push_back(std::to_string(e.wis)); + v.push_back(std::to_string(e.fire)); + v.push_back(std::to_string(e.cold)); + v.push_back(std::to_string(e.magic)); + v.push_back(std::to_string(e.poison)); + v.push_back(std::to_string(e.disease)); + v.push_back(std::to_string(e.corruption)); + v.push_back(std::to_string(e.show_helm)); + v.push_back(std::to_string(e.follow_distance)); + v.push_back(std::to_string(e.stop_melee_level)); + v.push_back(std::to_string(e.expansion_bitmask)); + v.push_back(std::to_string(e.enforce_spell_settings)); + v.push_back(std::to_string(e.archery_setting)); + v.push_back(std::to_string(e.caster_range)); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.bot_id)); + v.push_back(std::to_string(e.owner_id)); + v.push_back(std::to_string(e.spells_id)); + v.push_back("'" + Strings::Escape(e.name) + "'"); + v.push_back("'" + Strings::Escape(e.last_name) + "'"); + v.push_back("'" + Strings::Escape(e.title) + "'"); + v.push_back("'" + Strings::Escape(e.suffix) + "'"); + v.push_back(std::to_string(e.zone_id)); + v.push_back(std::to_string(e.gender)); + v.push_back(std::to_string(e.race)); + v.push_back(std::to_string(e.class_)); + v.push_back(std::to_string(e.level)); + v.push_back(std::to_string(e.deity)); + v.push_back(std::to_string(e.creation_day)); + v.push_back(std::to_string(e.last_spawn)); + v.push_back(std::to_string(e.time_spawned)); + v.push_back(std::to_string(e.size)); + v.push_back(std::to_string(e.face)); + v.push_back(std::to_string(e.hair_color)); + v.push_back(std::to_string(e.hair_style)); + v.push_back(std::to_string(e.beard)); + v.push_back(std::to_string(e.beard_color)); + v.push_back(std::to_string(e.eye_color_1)); + v.push_back(std::to_string(e.eye_color_2)); + v.push_back(std::to_string(e.drakkin_heritage)); + v.push_back(std::to_string(e.drakkin_tattoo)); + v.push_back(std::to_string(e.drakkin_details)); + v.push_back(std::to_string(e.ac)); + v.push_back(std::to_string(e.atk)); + v.push_back(std::to_string(e.hp)); + v.push_back(std::to_string(e.mana)); + v.push_back(std::to_string(e.str)); + v.push_back(std::to_string(e.sta)); + v.push_back(std::to_string(e.cha)); + v.push_back(std::to_string(e.dex)); + v.push_back(std::to_string(e.int_)); + v.push_back(std::to_string(e.agi)); + v.push_back(std::to_string(e.wis)); + v.push_back(std::to_string(e.fire)); + v.push_back(std::to_string(e.cold)); + v.push_back(std::to_string(e.magic)); + v.push_back(std::to_string(e.poison)); + v.push_back(std::to_string(e.disease)); + v.push_back(std::to_string(e.corruption)); + v.push_back(std::to_string(e.show_helm)); + v.push_back(std::to_string(e.follow_distance)); + v.push_back(std::to_string(e.stop_melee_level)); + v.push_back(std::to_string(e.expansion_bitmask)); + v.push_back(std::to_string(e.enforce_spell_settings)); + v.push_back(std::to_string(e.archery_setting)); + v.push_back(std::to_string(e.caster_range)); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_DATA_REPOSITORY_H diff --git a/common/repositories/base/base_bot_heal_rotation_members_repository.h b/common/repositories/base/base_bot_heal_rotation_members_repository.h index af89601d6..240161360 100644 --- a/common/repositories/base/base_bot_heal_rotation_members_repository.h +++ b/common/repositories/base/base_bot_heal_rotation_members_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_HEAL_ROTATION_MEMBERS_REPOSITORY_H @@ -112,8 +112,9 @@ public: { auto results = db.QueryDatabase( fmt::format( - "{} WHERE id = {} LIMIT 1", + "{} WHERE {} = {} LIMIT 1", BaseSelect(), + PrimaryKey(), bot_heal_rotation_members_id ) ); @@ -122,9 +123,9 @@ public: if (results.RowCount() == 1) { BotHealRotationMembers e{}; - e.member_index = static_cast(strtoul(row[0], nullptr, 10)); - e.heal_rotation_index = static_cast(strtoul(row[1], nullptr, 10)); - e.bot_id = static_cast(strtoul(row[2], nullptr, 10)); + e.member_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.heal_rotation_index = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.bot_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; return e; } @@ -249,9 +250,9 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotHealRotationMembers e{}; - e.member_index = static_cast(strtoul(row[0], nullptr, 10)); - e.heal_rotation_index = static_cast(strtoul(row[1], nullptr, 10)); - e.bot_id = static_cast(strtoul(row[2], nullptr, 10)); + e.member_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.heal_rotation_index = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.bot_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -276,9 +277,9 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotHealRotationMembers e{}; - e.member_index = static_cast(strtoul(row[0], nullptr, 10)); - e.heal_rotation_index = static_cast(strtoul(row[1], nullptr, 10)); - e.bot_id = static_cast(strtoul(row[2], nullptr, 10)); + e.member_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.heal_rotation_index = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.bot_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -337,6 +338,66 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotHealRotationMembers &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.member_index)); + v.push_back(std::to_string(e.heal_rotation_index)); + v.push_back(std::to_string(e.bot_id)); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.member_index)); + v.push_back(std::to_string(e.heal_rotation_index)); + v.push_back(std::to_string(e.bot_id)); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_HEAL_ROTATION_MEMBERS_REPOSITORY_H diff --git a/common/repositories/base/base_bot_heal_rotation_targets_repository.h b/common/repositories/base/base_bot_heal_rotation_targets_repository.h index b5bef9c2b..6d8c144c1 100644 --- a/common/repositories/base/base_bot_heal_rotation_targets_repository.h +++ b/common/repositories/base/base_bot_heal_rotation_targets_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_HEAL_ROTATION_TARGETS_REPOSITORY_H @@ -112,8 +112,9 @@ public: { auto results = db.QueryDatabase( fmt::format( - "{} WHERE id = {} LIMIT 1", + "{} WHERE {} = {} LIMIT 1", BaseSelect(), + PrimaryKey(), bot_heal_rotation_targets_id ) ); @@ -122,8 +123,8 @@ public: if (results.RowCount() == 1) { BotHealRotationTargets e{}; - e.target_index = static_cast(strtoul(row[0], nullptr, 10)); - e.heal_rotation_index = static_cast(strtoul(row[1], nullptr, 10)); + e.target_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.heal_rotation_index = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; e.target_name = row[2] ? row[2] : ""; return e; @@ -249,8 +250,8 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotHealRotationTargets e{}; - e.target_index = static_cast(strtoul(row[0], nullptr, 10)); - e.heal_rotation_index = static_cast(strtoul(row[1], nullptr, 10)); + e.target_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.heal_rotation_index = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; e.target_name = row[2] ? row[2] : ""; all_entries.push_back(e); @@ -276,8 +277,8 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotHealRotationTargets e{}; - e.target_index = static_cast(strtoul(row[0], nullptr, 10)); - e.heal_rotation_index = static_cast(strtoul(row[1], nullptr, 10)); + e.target_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.heal_rotation_index = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; e.target_name = row[2] ? row[2] : ""; all_entries.push_back(e); @@ -337,6 +338,66 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotHealRotationTargets &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.target_index)); + v.push_back(std::to_string(e.heal_rotation_index)); + v.push_back("'" + Strings::Escape(e.target_name) + "'"); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.target_index)); + v.push_back(std::to_string(e.heal_rotation_index)); + v.push_back("'" + Strings::Escape(e.target_name) + "'"); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_HEAL_ROTATION_TARGETS_REPOSITORY_H diff --git a/common/repositories/base/base_bot_heal_rotations_repository.h b/common/repositories/base/base_bot_heal_rotations_repository.h index f39e0b403..d0fef3823 100644 --- a/common/repositories/base/base_bot_heal_rotations_repository.h +++ b/common/repositories/base/base_bot_heal_rotations_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_HEAL_ROTATIONS_REPOSITORY_H @@ -19,22 +19,22 @@ class BaseBotHealRotationsRepository { public: struct BotHealRotations { - uint32_t heal_rotation_index; - uint32_t bot_id; - uint32_t interval; - uint32_t fast_heals; - uint32_t adaptive_targeting; - uint32_t casting_override; - std::string safe_hp_base; - std::string safe_hp_cloth; - std::string safe_hp_leather; - std::string safe_hp_chain; - std::string safe_hp_plate; - std::string critical_hp_base; - std::string critical_hp_cloth; - std::string critical_hp_leather; - std::string critical_hp_chain; - std::string critical_hp_plate; + uint32_t heal_rotation_index; + uint32_t bot_id; + uint32_t interval_; + uint32_t fast_heals; + uint32_t adaptive_targeting; + uint32_t casting_override; + float safe_hp_base; + float safe_hp_cloth; + float safe_hp_leather; + float safe_hp_chain; + float safe_hp_plate; + float critical_hp_base; + float critical_hp_cloth; + float critical_hp_leather; + float critical_hp_chain; + float critical_hp_plate; }; static std::string PrimaryKey() @@ -47,7 +47,7 @@ public: return { "heal_rotation_index", "bot_id", - "interval", + "`interval`", "fast_heals", "adaptive_targeting", "casting_override", @@ -69,7 +69,7 @@ public: return { "heal_rotation_index", "bot_id", - "interval", + "`interval`", "fast_heals", "adaptive_targeting", "casting_override", @@ -125,7 +125,7 @@ public: e.heal_rotation_index = 0; e.bot_id = 0; - e.interval = 0; + e.interval_ = 0; e.fast_heals = 0; e.adaptive_targeting = 0; e.casting_override = 0; @@ -164,8 +164,9 @@ public: { auto results = db.QueryDatabase( fmt::format( - "{} WHERE id = {} LIMIT 1", + "{} WHERE {} = {} LIMIT 1", BaseSelect(), + PrimaryKey(), bot_heal_rotations_id ) ); @@ -174,12 +175,12 @@ public: if (results.RowCount() == 1) { BotHealRotations e{}; - e.heal_rotation_index = static_cast(strtoul(row[0], nullptr, 10)); - e.bot_id = static_cast(strtoul(row[1], nullptr, 10)); - e.interval = static_cast(strtoul(row[2], nullptr, 10)); - e.fast_heals = static_cast(strtoul(row[3], nullptr, 10)); - e.adaptive_targeting = static_cast(strtoul(row[4], nullptr, 10)); - e.casting_override = static_cast(strtoul(row[5], nullptr, 10)); + e.heal_rotation_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.bot_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.interval_ = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.fast_heals = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.adaptive_targeting = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.casting_override = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; return e; } @@ -214,7 +215,7 @@ public: auto columns = Columns(); v.push_back(columns[1] + " = " + std::to_string(e.bot_id)); - v.push_back(columns[2] + " = " + std::to_string(e.interval)); + v.push_back(columns[2] + " = " + std::to_string(e.interval_)); v.push_back(columns[3] + " = " + std::to_string(e.fast_heals)); v.push_back(columns[4] + " = " + std::to_string(e.adaptive_targeting)); v.push_back(columns[5] + " = " + std::to_string(e.casting_override)); @@ -251,7 +252,7 @@ public: v.push_back(std::to_string(e.heal_rotation_index)); v.push_back(std::to_string(e.bot_id)); - v.push_back(std::to_string(e.interval)); + v.push_back(std::to_string(e.interval_)); v.push_back(std::to_string(e.fast_heals)); v.push_back(std::to_string(e.adaptive_targeting)); v.push_back(std::to_string(e.casting_override)); @@ -296,7 +297,7 @@ public: v.push_back(std::to_string(e.heal_rotation_index)); v.push_back(std::to_string(e.bot_id)); - v.push_back(std::to_string(e.interval)); + v.push_back(std::to_string(e.interval_)); v.push_back(std::to_string(e.fast_heals)); v.push_back(std::to_string(e.adaptive_targeting)); v.push_back(std::to_string(e.casting_override)); @@ -343,12 +344,12 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotHealRotations e{}; - e.heal_rotation_index = static_cast(strtoul(row[0], nullptr, 10)); - e.bot_id = static_cast(strtoul(row[1], nullptr, 10)); - e.interval = static_cast(strtoul(row[2], nullptr, 10)); - e.fast_heals = static_cast(strtoul(row[3], nullptr, 10)); - e.adaptive_targeting = static_cast(strtoul(row[4], nullptr, 10)); - e.casting_override = static_cast(strtoul(row[5], nullptr, 10)); + e.heal_rotation_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.bot_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.interval_ = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.fast_heals = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.adaptive_targeting = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.casting_override = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -373,12 +374,12 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotHealRotations e{}; - e.heal_rotation_index = static_cast(strtoul(row[0], nullptr, 10)); - e.bot_id = static_cast(strtoul(row[1], nullptr, 10)); - e.interval = static_cast(strtoul(row[2], nullptr, 10)); - e.fast_heals = static_cast(strtoul(row[3], nullptr, 10)); - e.adaptive_targeting = static_cast(strtoul(row[4], nullptr, 10)); - e.casting_override = static_cast(strtoul(row[5], nullptr, 10)); + e.heal_rotation_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.bot_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.interval_ = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.fast_heals = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.adaptive_targeting = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.casting_override = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -437,6 +438,92 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotHealRotations &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.heal_rotation_index)); + v.push_back(std::to_string(e.bot_id)); + v.push_back(std::to_string(e.interval_)); + v.push_back(std::to_string(e.fast_heals)); + v.push_back(std::to_string(e.adaptive_targeting)); + v.push_back(std::to_string(e.casting_override)); + v.push_back(std::to_string(e.safe_hp_base)); + v.push_back(std::to_string(e.safe_hp_cloth)); + v.push_back(std::to_string(e.safe_hp_leather)); + v.push_back(std::to_string(e.safe_hp_chain)); + v.push_back(std::to_string(e.safe_hp_plate)); + v.push_back(std::to_string(e.critical_hp_base)); + v.push_back(std::to_string(e.critical_hp_cloth)); + v.push_back(std::to_string(e.critical_hp_leather)); + v.push_back(std::to_string(e.critical_hp_chain)); + v.push_back(std::to_string(e.critical_hp_plate)); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.heal_rotation_index)); + v.push_back(std::to_string(e.bot_id)); + v.push_back(std::to_string(e.interval_)); + v.push_back(std::to_string(e.fast_heals)); + v.push_back(std::to_string(e.adaptive_targeting)); + v.push_back(std::to_string(e.casting_override)); + v.push_back(std::to_string(e.safe_hp_base)); + v.push_back(std::to_string(e.safe_hp_cloth)); + v.push_back(std::to_string(e.safe_hp_leather)); + v.push_back(std::to_string(e.safe_hp_chain)); + v.push_back(std::to_string(e.safe_hp_plate)); + v.push_back(std::to_string(e.critical_hp_base)); + v.push_back(std::to_string(e.critical_hp_cloth)); + v.push_back(std::to_string(e.critical_hp_leather)); + v.push_back(std::to_string(e.critical_hp_chain)); + v.push_back(std::to_string(e.critical_hp_plate)); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_HEAL_ROTATIONS_REPOSITORY_H diff --git a/common/repositories/base/base_bot_inspect_messages_repository.h b/common/repositories/base/base_bot_inspect_messages_repository.h index bcf19437e..58f672743 100644 --- a/common/repositories/base/base_bot_inspect_messages_repository.h +++ b/common/repositories/base/base_bot_inspect_messages_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_INSPECT_MESSAGES_REPOSITORY_H @@ -108,8 +108,9 @@ public: { auto results = db.QueryDatabase( fmt::format( - "{} WHERE id = {} LIMIT 1", + "{} WHERE {} = {} LIMIT 1", BaseSelect(), + PrimaryKey(), bot_inspect_messages_id ) ); @@ -118,7 +119,7 @@ public: if (results.RowCount() == 1) { BotInspectMessages e{}; - e.bot_id = static_cast(strtoul(row[0], nullptr, 10)); + e.bot_id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; e.inspect_message = row[1] ? row[1] : ""; return e; @@ -242,7 +243,7 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotInspectMessages e{}; - e.bot_id = static_cast(strtoul(row[0], nullptr, 10)); + e.bot_id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; e.inspect_message = row[1] ? row[1] : ""; all_entries.push_back(e); @@ -268,7 +269,7 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotInspectMessages e{}; - e.bot_id = static_cast(strtoul(row[0], nullptr, 10)); + e.bot_id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; e.inspect_message = row[1] ? row[1] : ""; all_entries.push_back(e); @@ -328,6 +329,64 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotInspectMessages &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.bot_id)); + v.push_back("'" + Strings::Escape(e.inspect_message) + "'"); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.bot_id)); + v.push_back("'" + Strings::Escape(e.inspect_message) + "'"); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_INSPECT_MESSAGES_REPOSITORY_H diff --git a/common/repositories/base/base_bot_inventories_repository.h b/common/repositories/base/base_bot_inventories_repository.h index 4f0545148..ef8aeb793 100644 --- a/common/repositories/base/base_bot_inventories_repository.h +++ b/common/repositories/base/base_bot_inventories_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_INVENTORIES_REPOSITORY_H @@ -168,8 +168,9 @@ public: { auto results = db.QueryDatabase( fmt::format( - "{} WHERE id = {} LIMIT 1", + "{} WHERE {} = {} LIMIT 1", BaseSelect(), + PrimaryKey(), bot_inventories_id ) ); @@ -178,23 +179,23 @@ public: if (results.RowCount() == 1) { BotInventories e{}; - e.inventories_index = static_cast(strtoul(row[0], nullptr, 10)); - e.bot_id = static_cast(strtoul(row[1], nullptr, 10)); - e.slot_id = static_cast(strtoul(row[2], nullptr, 10)); - e.item_id = static_cast(strtoul(row[3], nullptr, 10)); - e.inst_charges = static_cast(strtoul(row[4], nullptr, 10)); - e.inst_color = static_cast(strtoul(row[5], nullptr, 10)); - e.inst_no_drop = static_cast(strtoul(row[6], nullptr, 10)); + e.inventories_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.bot_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.slot_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.item_id = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.inst_charges = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.inst_color = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; + e.inst_no_drop = row[6] ? static_cast(strtoul(row[6], nullptr, 10)) : 0; e.inst_custom_data = row[7] ? row[7] : ""; - e.ornament_icon = static_cast(strtoul(row[8], nullptr, 10)); - e.ornament_id_file = static_cast(strtoul(row[9], nullptr, 10)); - e.ornament_hero_model = static_cast(atoi(row[10])); - e.augment_1 = static_cast(strtoul(row[11], nullptr, 10)); - e.augment_2 = static_cast(strtoul(row[12], nullptr, 10)); - e.augment_3 = static_cast(strtoul(row[13], nullptr, 10)); - e.augment_4 = static_cast(strtoul(row[14], nullptr, 10)); - e.augment_5 = static_cast(strtoul(row[15], nullptr, 10)); - e.augment_6 = static_cast(strtoul(row[16], nullptr, 10)); + e.ornament_icon = row[8] ? static_cast(strtoul(row[8], nullptr, 10)) : 0; + e.ornament_id_file = row[9] ? static_cast(strtoul(row[9], nullptr, 10)) : 0; + e.ornament_hero_model = row[10] ? static_cast(atoi(row[10])) : 0; + e.augment_1 = row[11] ? static_cast(strtoul(row[11], nullptr, 10)) : 0; + e.augment_2 = row[12] ? static_cast(strtoul(row[12], nullptr, 10)) : 0; + e.augment_3 = row[13] ? static_cast(strtoul(row[13], nullptr, 10)) : 0; + e.augment_4 = row[14] ? static_cast(strtoul(row[14], nullptr, 10)) : 0; + e.augment_5 = row[15] ? static_cast(strtoul(row[15], nullptr, 10)) : 0; + e.augment_6 = row[16] ? static_cast(strtoul(row[16], nullptr, 10)) : 0; return e; } @@ -361,23 +362,23 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotInventories e{}; - e.inventories_index = static_cast(strtoul(row[0], nullptr, 10)); - e.bot_id = static_cast(strtoul(row[1], nullptr, 10)); - e.slot_id = static_cast(strtoul(row[2], nullptr, 10)); - e.item_id = static_cast(strtoul(row[3], nullptr, 10)); - e.inst_charges = static_cast(strtoul(row[4], nullptr, 10)); - e.inst_color = static_cast(strtoul(row[5], nullptr, 10)); - e.inst_no_drop = static_cast(strtoul(row[6], nullptr, 10)); + e.inventories_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.bot_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.slot_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.item_id = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.inst_charges = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.inst_color = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; + e.inst_no_drop = row[6] ? static_cast(strtoul(row[6], nullptr, 10)) : 0; e.inst_custom_data = row[7] ? row[7] : ""; - e.ornament_icon = static_cast(strtoul(row[8], nullptr, 10)); - e.ornament_id_file = static_cast(strtoul(row[9], nullptr, 10)); - e.ornament_hero_model = static_cast(atoi(row[10])); - e.augment_1 = static_cast(strtoul(row[11], nullptr, 10)); - e.augment_2 = static_cast(strtoul(row[12], nullptr, 10)); - e.augment_3 = static_cast(strtoul(row[13], nullptr, 10)); - e.augment_4 = static_cast(strtoul(row[14], nullptr, 10)); - e.augment_5 = static_cast(strtoul(row[15], nullptr, 10)); - e.augment_6 = static_cast(strtoul(row[16], nullptr, 10)); + e.ornament_icon = row[8] ? static_cast(strtoul(row[8], nullptr, 10)) : 0; + e.ornament_id_file = row[9] ? static_cast(strtoul(row[9], nullptr, 10)) : 0; + e.ornament_hero_model = row[10] ? static_cast(atoi(row[10])) : 0; + e.augment_1 = row[11] ? static_cast(strtoul(row[11], nullptr, 10)) : 0; + e.augment_2 = row[12] ? static_cast(strtoul(row[12], nullptr, 10)) : 0; + e.augment_3 = row[13] ? static_cast(strtoul(row[13], nullptr, 10)) : 0; + e.augment_4 = row[14] ? static_cast(strtoul(row[14], nullptr, 10)) : 0; + e.augment_5 = row[15] ? static_cast(strtoul(row[15], nullptr, 10)) : 0; + e.augment_6 = row[16] ? static_cast(strtoul(row[16], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -402,23 +403,23 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotInventories e{}; - e.inventories_index = static_cast(strtoul(row[0], nullptr, 10)); - e.bot_id = static_cast(strtoul(row[1], nullptr, 10)); - e.slot_id = static_cast(strtoul(row[2], nullptr, 10)); - e.item_id = static_cast(strtoul(row[3], nullptr, 10)); - e.inst_charges = static_cast(strtoul(row[4], nullptr, 10)); - e.inst_color = static_cast(strtoul(row[5], nullptr, 10)); - e.inst_no_drop = static_cast(strtoul(row[6], nullptr, 10)); + e.inventories_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.bot_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.slot_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.item_id = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.inst_charges = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.inst_color = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; + e.inst_no_drop = row[6] ? static_cast(strtoul(row[6], nullptr, 10)) : 0; e.inst_custom_data = row[7] ? row[7] : ""; - e.ornament_icon = static_cast(strtoul(row[8], nullptr, 10)); - e.ornament_id_file = static_cast(strtoul(row[9], nullptr, 10)); - e.ornament_hero_model = static_cast(atoi(row[10])); - e.augment_1 = static_cast(strtoul(row[11], nullptr, 10)); - e.augment_2 = static_cast(strtoul(row[12], nullptr, 10)); - e.augment_3 = static_cast(strtoul(row[13], nullptr, 10)); - e.augment_4 = static_cast(strtoul(row[14], nullptr, 10)); - e.augment_5 = static_cast(strtoul(row[15], nullptr, 10)); - e.augment_6 = static_cast(strtoul(row[16], nullptr, 10)); + e.ornament_icon = row[8] ? static_cast(strtoul(row[8], nullptr, 10)) : 0; + e.ornament_id_file = row[9] ? static_cast(strtoul(row[9], nullptr, 10)) : 0; + e.ornament_hero_model = row[10] ? static_cast(atoi(row[10])) : 0; + e.augment_1 = row[11] ? static_cast(strtoul(row[11], nullptr, 10)) : 0; + e.augment_2 = row[12] ? static_cast(strtoul(row[12], nullptr, 10)) : 0; + e.augment_3 = row[13] ? static_cast(strtoul(row[13], nullptr, 10)) : 0; + e.augment_4 = row[14] ? static_cast(strtoul(row[14], nullptr, 10)) : 0; + e.augment_5 = row[15] ? static_cast(strtoul(row[15], nullptr, 10)) : 0; + e.augment_6 = row[16] ? static_cast(strtoul(row[16], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -477,6 +478,94 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotInventories &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.inventories_index)); + v.push_back(std::to_string(e.bot_id)); + v.push_back(std::to_string(e.slot_id)); + v.push_back(std::to_string(e.item_id)); + v.push_back(std::to_string(e.inst_charges)); + v.push_back(std::to_string(e.inst_color)); + v.push_back(std::to_string(e.inst_no_drop)); + v.push_back("'" + Strings::Escape(e.inst_custom_data) + "'"); + v.push_back(std::to_string(e.ornament_icon)); + v.push_back(std::to_string(e.ornament_id_file)); + v.push_back(std::to_string(e.ornament_hero_model)); + v.push_back(std::to_string(e.augment_1)); + v.push_back(std::to_string(e.augment_2)); + v.push_back(std::to_string(e.augment_3)); + v.push_back(std::to_string(e.augment_4)); + v.push_back(std::to_string(e.augment_5)); + v.push_back(std::to_string(e.augment_6)); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.inventories_index)); + v.push_back(std::to_string(e.bot_id)); + v.push_back(std::to_string(e.slot_id)); + v.push_back(std::to_string(e.item_id)); + v.push_back(std::to_string(e.inst_charges)); + v.push_back(std::to_string(e.inst_color)); + v.push_back(std::to_string(e.inst_no_drop)); + v.push_back("'" + Strings::Escape(e.inst_custom_data) + "'"); + v.push_back(std::to_string(e.ornament_icon)); + v.push_back(std::to_string(e.ornament_id_file)); + v.push_back(std::to_string(e.ornament_hero_model)); + v.push_back(std::to_string(e.augment_1)); + v.push_back(std::to_string(e.augment_2)); + v.push_back(std::to_string(e.augment_3)); + v.push_back(std::to_string(e.augment_4)); + v.push_back(std::to_string(e.augment_5)); + v.push_back(std::to_string(e.augment_6)); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_INVENTORIES_REPOSITORY_H diff --git a/common/repositories/base/base_bot_owner_options_repository.h b/common/repositories/base/base_bot_owner_options_repository.h index 3bc31c539..acf10a04e 100644 --- a/common/repositories/base/base_bot_owner_options_repository.h +++ b/common/repositories/base/base_bot_owner_options_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_OWNER_OPTIONS_REPOSITORY_H @@ -112,8 +112,9 @@ public: { auto results = db.QueryDatabase( fmt::format( - "{} WHERE id = {} LIMIT 1", + "{} WHERE {} = {} LIMIT 1", BaseSelect(), + PrimaryKey(), bot_owner_options_id ) ); @@ -122,9 +123,9 @@ public: if (results.RowCount() == 1) { BotOwnerOptions e{}; - e.owner_id = static_cast(strtoul(row[0], nullptr, 10)); - e.option_type = static_cast(strtoul(row[1], nullptr, 10)); - e.option_value = static_cast(strtoul(row[2], nullptr, 10)); + e.owner_id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.option_type = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.option_value = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; return e; } @@ -250,9 +251,9 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotOwnerOptions e{}; - e.owner_id = static_cast(strtoul(row[0], nullptr, 10)); - e.option_type = static_cast(strtoul(row[1], nullptr, 10)); - e.option_value = static_cast(strtoul(row[2], nullptr, 10)); + e.owner_id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.option_type = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.option_value = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -277,9 +278,9 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotOwnerOptions e{}; - e.owner_id = static_cast(strtoul(row[0], nullptr, 10)); - e.option_type = static_cast(strtoul(row[1], nullptr, 10)); - e.option_value = static_cast(strtoul(row[2], nullptr, 10)); + e.owner_id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.option_type = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.option_value = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -338,6 +339,66 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotOwnerOptions &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.owner_id)); + v.push_back(std::to_string(e.option_type)); + v.push_back(std::to_string(e.option_value)); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.owner_id)); + v.push_back(std::to_string(e.option_type)); + v.push_back(std::to_string(e.option_value)); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_OWNER_OPTIONS_REPOSITORY_H diff --git a/common/repositories/base/base_bot_pet_buffs_repository.h b/common/repositories/base/base_bot_pet_buffs_repository.h index e5b8fb92c..0d807c8b6 100644 --- a/common/repositories/base/base_bot_pet_buffs_repository.h +++ b/common/repositories/base/base_bot_pet_buffs_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_PET_BUFFS_REPOSITORY_H @@ -120,8 +120,9 @@ public: { auto results = db.QueryDatabase( fmt::format( - "{} WHERE id = {} LIMIT 1", + "{} WHERE {} = {} LIMIT 1", BaseSelect(), + PrimaryKey(), bot_pet_buffs_id ) ); @@ -130,11 +131,11 @@ public: if (results.RowCount() == 1) { BotPetBuffs e{}; - e.pet_buffs_index = static_cast(strtoul(row[0], nullptr, 10)); - e.pets_index = static_cast(strtoul(row[1], nullptr, 10)); - e.spell_id = static_cast(strtoul(row[2], nullptr, 10)); - e.caster_level = static_cast(strtoul(row[3], nullptr, 10)); - e.duration = static_cast(strtoul(row[4], nullptr, 10)); + e.pet_buffs_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.pets_index = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.spell_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.caster_level = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.duration = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; return e; } @@ -265,11 +266,11 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotPetBuffs e{}; - e.pet_buffs_index = static_cast(strtoul(row[0], nullptr, 10)); - e.pets_index = static_cast(strtoul(row[1], nullptr, 10)); - e.spell_id = static_cast(strtoul(row[2], nullptr, 10)); - e.caster_level = static_cast(strtoul(row[3], nullptr, 10)); - e.duration = static_cast(strtoul(row[4], nullptr, 10)); + e.pet_buffs_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.pets_index = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.spell_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.caster_level = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.duration = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -294,11 +295,11 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotPetBuffs e{}; - e.pet_buffs_index = static_cast(strtoul(row[0], nullptr, 10)); - e.pets_index = static_cast(strtoul(row[1], nullptr, 10)); - e.spell_id = static_cast(strtoul(row[2], nullptr, 10)); - e.caster_level = static_cast(strtoul(row[3], nullptr, 10)); - e.duration = static_cast(strtoul(row[4], nullptr, 10)); + e.pet_buffs_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.pets_index = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.spell_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.caster_level = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.duration = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -357,6 +358,70 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotPetBuffs &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.pet_buffs_index)); + v.push_back(std::to_string(e.pets_index)); + v.push_back(std::to_string(e.spell_id)); + v.push_back(std::to_string(e.caster_level)); + v.push_back(std::to_string(e.duration)); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.pet_buffs_index)); + v.push_back(std::to_string(e.pets_index)); + v.push_back(std::to_string(e.spell_id)); + v.push_back(std::to_string(e.caster_level)); + v.push_back(std::to_string(e.duration)); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_PET_BUFFS_REPOSITORY_H diff --git a/common/repositories/base/base_bot_pet_inventories_repository.h b/common/repositories/base/base_bot_pet_inventories_repository.h index f8c9e918f..0899cedd0 100644 --- a/common/repositories/base/base_bot_pet_inventories_repository.h +++ b/common/repositories/base/base_bot_pet_inventories_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_PET_INVENTORIES_REPOSITORY_H @@ -112,8 +112,9 @@ public: { auto results = db.QueryDatabase( fmt::format( - "{} WHERE id = {} LIMIT 1", + "{} WHERE {} = {} LIMIT 1", BaseSelect(), + PrimaryKey(), bot_pet_inventories_id ) ); @@ -122,9 +123,9 @@ public: if (results.RowCount() == 1) { BotPetInventories e{}; - e.pet_inventories_index = static_cast(strtoul(row[0], nullptr, 10)); - e.pets_index = static_cast(strtoul(row[1], nullptr, 10)); - e.item_id = static_cast(strtoul(row[2], nullptr, 10)); + e.pet_inventories_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.pets_index = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.item_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; return e; } @@ -249,9 +250,9 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotPetInventories e{}; - e.pet_inventories_index = static_cast(strtoul(row[0], nullptr, 10)); - e.pets_index = static_cast(strtoul(row[1], nullptr, 10)); - e.item_id = static_cast(strtoul(row[2], nullptr, 10)); + e.pet_inventories_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.pets_index = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.item_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -276,9 +277,9 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotPetInventories e{}; - e.pet_inventories_index = static_cast(strtoul(row[0], nullptr, 10)); - e.pets_index = static_cast(strtoul(row[1], nullptr, 10)); - e.item_id = static_cast(strtoul(row[2], nullptr, 10)); + e.pet_inventories_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.pets_index = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.item_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -337,6 +338,66 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotPetInventories &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.pet_inventories_index)); + v.push_back(std::to_string(e.pets_index)); + v.push_back(std::to_string(e.item_id)); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.pet_inventories_index)); + v.push_back(std::to_string(e.pets_index)); + v.push_back(std::to_string(e.item_id)); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_PET_INVENTORIES_REPOSITORY_H diff --git a/common/repositories/base/base_bot_pets_repository.h b/common/repositories/base/base_bot_pets_repository.h index 59e43a6dc..d98af748c 100644 --- a/common/repositories/base/base_bot_pets_repository.h +++ b/common/repositories/base/base_bot_pets_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_PETS_REPOSITORY_H @@ -124,8 +124,9 @@ public: { auto results = db.QueryDatabase( fmt::format( - "{} WHERE id = {} LIMIT 1", + "{} WHERE {} = {} LIMIT 1", BaseSelect(), + PrimaryKey(), bot_pets_id ) ); @@ -134,12 +135,12 @@ public: if (results.RowCount() == 1) { BotPets e{}; - e.pets_index = static_cast(strtoul(row[0], nullptr, 10)); - e.spell_id = static_cast(strtoul(row[1], nullptr, 10)); - e.bot_id = static_cast(strtoul(row[2], nullptr, 10)); + e.pets_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.spell_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.bot_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; e.name = row[3] ? row[3] : ""; - e.mana = static_cast(atoi(row[4])); - e.hp = static_cast(atoi(row[5])); + e.mana = row[4] ? static_cast(atoi(row[4])) : 0; + e.hp = row[5] ? static_cast(atoi(row[5])) : 0; return e; } @@ -273,12 +274,12 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotPets e{}; - e.pets_index = static_cast(strtoul(row[0], nullptr, 10)); - e.spell_id = static_cast(strtoul(row[1], nullptr, 10)); - e.bot_id = static_cast(strtoul(row[2], nullptr, 10)); + e.pets_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.spell_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.bot_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; e.name = row[3] ? row[3] : ""; - e.mana = static_cast(atoi(row[4])); - e.hp = static_cast(atoi(row[5])); + e.mana = row[4] ? static_cast(atoi(row[4])) : 0; + e.hp = row[5] ? static_cast(atoi(row[5])) : 0; all_entries.push_back(e); } @@ -303,12 +304,12 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotPets e{}; - e.pets_index = static_cast(strtoul(row[0], nullptr, 10)); - e.spell_id = static_cast(strtoul(row[1], nullptr, 10)); - e.bot_id = static_cast(strtoul(row[2], nullptr, 10)); + e.pets_index = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.spell_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.bot_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; e.name = row[3] ? row[3] : ""; - e.mana = static_cast(atoi(row[4])); - e.hp = static_cast(atoi(row[5])); + e.mana = row[4] ? static_cast(atoi(row[4])) : 0; + e.hp = row[5] ? static_cast(atoi(row[5])) : 0; all_entries.push_back(e); } @@ -367,6 +368,72 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotPets &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.pets_index)); + v.push_back(std::to_string(e.spell_id)); + v.push_back(std::to_string(e.bot_id)); + v.push_back("'" + Strings::Escape(e.name) + "'"); + v.push_back(std::to_string(e.mana)); + v.push_back(std::to_string(e.hp)); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.pets_index)); + v.push_back(std::to_string(e.spell_id)); + v.push_back(std::to_string(e.bot_id)); + v.push_back("'" + Strings::Escape(e.name) + "'"); + v.push_back(std::to_string(e.mana)); + v.push_back(std::to_string(e.hp)); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_PETS_REPOSITORY_H diff --git a/common/repositories/base/base_bot_spell_casting_chances_repository.h b/common/repositories/base/base_bot_spell_casting_chances_repository.h index 544c08d29..cd42f4965 100644 --- a/common/repositories/base/base_bot_spell_casting_chances_repository.h +++ b/common/repositories/base/base_bot_spell_casting_chances_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_SPELL_CASTING_CHANCES_REPOSITORY_H @@ -180,8 +180,9 @@ public: { auto results = db.QueryDatabase( fmt::format( - "{} WHERE id = {} LIMIT 1", + "{} WHERE {} = {} LIMIT 1", BaseSelect(), + PrimaryKey(), bot_spell_casting_chances_id ) ); @@ -190,26 +191,26 @@ public: if (results.RowCount() == 1) { BotSpellCastingChances e{}; - e.id = static_cast(atoi(row[0])); - e.spell_type_index = static_cast(strtoul(row[1], nullptr, 10)); - e.class_id = static_cast(strtoul(row[2], nullptr, 10)); - e.stance_index = static_cast(strtoul(row[3], nullptr, 10)); - e.nHSND_value = static_cast(strtoul(row[4], nullptr, 10)); - e.pH_value = static_cast(strtoul(row[5], nullptr, 10)); - e.pS_value = static_cast(strtoul(row[6], nullptr, 10)); - e.pHS_value = static_cast(strtoul(row[7], nullptr, 10)); - e.pN_value = static_cast(strtoul(row[8], nullptr, 10)); - e.pHN_value = static_cast(strtoul(row[9], nullptr, 10)); - e.pSN_value = static_cast(strtoul(row[10], nullptr, 10)); - e.pHSN_value = static_cast(strtoul(row[11], nullptr, 10)); - e.pD_value = static_cast(strtoul(row[12], nullptr, 10)); - e.pHD_value = static_cast(strtoul(row[13], nullptr, 10)); - e.pSD_value = static_cast(strtoul(row[14], nullptr, 10)); - e.pHSD_value = static_cast(strtoul(row[15], nullptr, 10)); - e.pND_value = static_cast(strtoul(row[16], nullptr, 10)); - e.pHND_value = static_cast(strtoul(row[17], nullptr, 10)); - e.pSND_value = static_cast(strtoul(row[18], nullptr, 10)); - e.pHSND_value = static_cast(strtoul(row[19], nullptr, 10)); + e.id = row[0] ? static_cast(atoi(row[0])) : 0; + e.spell_type_index = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.class_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.stance_index = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.nHSND_value = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.pH_value = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; + e.pS_value = row[6] ? static_cast(strtoul(row[6], nullptr, 10)) : 0; + e.pHS_value = row[7] ? static_cast(strtoul(row[7], nullptr, 10)) : 0; + e.pN_value = row[8] ? static_cast(strtoul(row[8], nullptr, 10)) : 0; + e.pHN_value = row[9] ? static_cast(strtoul(row[9], nullptr, 10)) : 0; + e.pSN_value = row[10] ? static_cast(strtoul(row[10], nullptr, 10)) : 0; + e.pHSN_value = row[11] ? static_cast(strtoul(row[11], nullptr, 10)) : 0; + e.pD_value = row[12] ? static_cast(strtoul(row[12], nullptr, 10)) : 0; + e.pHD_value = row[13] ? static_cast(strtoul(row[13], nullptr, 10)) : 0; + e.pSD_value = row[14] ? static_cast(strtoul(row[14], nullptr, 10)) : 0; + e.pHSD_value = row[15] ? static_cast(strtoul(row[15], nullptr, 10)) : 0; + e.pND_value = row[16] ? static_cast(strtoul(row[16], nullptr, 10)) : 0; + e.pHND_value = row[17] ? static_cast(strtoul(row[17], nullptr, 10)) : 0; + e.pSND_value = row[18] ? static_cast(strtoul(row[18], nullptr, 10)) : 0; + e.pHSND_value = row[19] ? static_cast(strtoul(row[19], nullptr, 10)) : 0; return e; } @@ -385,26 +386,26 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotSpellCastingChances e{}; - e.id = static_cast(atoi(row[0])); - e.spell_type_index = static_cast(strtoul(row[1], nullptr, 10)); - e.class_id = static_cast(strtoul(row[2], nullptr, 10)); - e.stance_index = static_cast(strtoul(row[3], nullptr, 10)); - e.nHSND_value = static_cast(strtoul(row[4], nullptr, 10)); - e.pH_value = static_cast(strtoul(row[5], nullptr, 10)); - e.pS_value = static_cast(strtoul(row[6], nullptr, 10)); - e.pHS_value = static_cast(strtoul(row[7], nullptr, 10)); - e.pN_value = static_cast(strtoul(row[8], nullptr, 10)); - e.pHN_value = static_cast(strtoul(row[9], nullptr, 10)); - e.pSN_value = static_cast(strtoul(row[10], nullptr, 10)); - e.pHSN_value = static_cast(strtoul(row[11], nullptr, 10)); - e.pD_value = static_cast(strtoul(row[12], nullptr, 10)); - e.pHD_value = static_cast(strtoul(row[13], nullptr, 10)); - e.pSD_value = static_cast(strtoul(row[14], nullptr, 10)); - e.pHSD_value = static_cast(strtoul(row[15], nullptr, 10)); - e.pND_value = static_cast(strtoul(row[16], nullptr, 10)); - e.pHND_value = static_cast(strtoul(row[17], nullptr, 10)); - e.pSND_value = static_cast(strtoul(row[18], nullptr, 10)); - e.pHSND_value = static_cast(strtoul(row[19], nullptr, 10)); + e.id = row[0] ? static_cast(atoi(row[0])) : 0; + e.spell_type_index = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.class_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.stance_index = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.nHSND_value = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.pH_value = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; + e.pS_value = row[6] ? static_cast(strtoul(row[6], nullptr, 10)) : 0; + e.pHS_value = row[7] ? static_cast(strtoul(row[7], nullptr, 10)) : 0; + e.pN_value = row[8] ? static_cast(strtoul(row[8], nullptr, 10)) : 0; + e.pHN_value = row[9] ? static_cast(strtoul(row[9], nullptr, 10)) : 0; + e.pSN_value = row[10] ? static_cast(strtoul(row[10], nullptr, 10)) : 0; + e.pHSN_value = row[11] ? static_cast(strtoul(row[11], nullptr, 10)) : 0; + e.pD_value = row[12] ? static_cast(strtoul(row[12], nullptr, 10)) : 0; + e.pHD_value = row[13] ? static_cast(strtoul(row[13], nullptr, 10)) : 0; + e.pSD_value = row[14] ? static_cast(strtoul(row[14], nullptr, 10)) : 0; + e.pHSD_value = row[15] ? static_cast(strtoul(row[15], nullptr, 10)) : 0; + e.pND_value = row[16] ? static_cast(strtoul(row[16], nullptr, 10)) : 0; + e.pHND_value = row[17] ? static_cast(strtoul(row[17], nullptr, 10)) : 0; + e.pSND_value = row[18] ? static_cast(strtoul(row[18], nullptr, 10)) : 0; + e.pHSND_value = row[19] ? static_cast(strtoul(row[19], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -429,26 +430,26 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotSpellCastingChances e{}; - e.id = static_cast(atoi(row[0])); - e.spell_type_index = static_cast(strtoul(row[1], nullptr, 10)); - e.class_id = static_cast(strtoul(row[2], nullptr, 10)); - e.stance_index = static_cast(strtoul(row[3], nullptr, 10)); - e.nHSND_value = static_cast(strtoul(row[4], nullptr, 10)); - e.pH_value = static_cast(strtoul(row[5], nullptr, 10)); - e.pS_value = static_cast(strtoul(row[6], nullptr, 10)); - e.pHS_value = static_cast(strtoul(row[7], nullptr, 10)); - e.pN_value = static_cast(strtoul(row[8], nullptr, 10)); - e.pHN_value = static_cast(strtoul(row[9], nullptr, 10)); - e.pSN_value = static_cast(strtoul(row[10], nullptr, 10)); - e.pHSN_value = static_cast(strtoul(row[11], nullptr, 10)); - e.pD_value = static_cast(strtoul(row[12], nullptr, 10)); - e.pHD_value = static_cast(strtoul(row[13], nullptr, 10)); - e.pSD_value = static_cast(strtoul(row[14], nullptr, 10)); - e.pHSD_value = static_cast(strtoul(row[15], nullptr, 10)); - e.pND_value = static_cast(strtoul(row[16], nullptr, 10)); - e.pHND_value = static_cast(strtoul(row[17], nullptr, 10)); - e.pSND_value = static_cast(strtoul(row[18], nullptr, 10)); - e.pHSND_value = static_cast(strtoul(row[19], nullptr, 10)); + e.id = row[0] ? static_cast(atoi(row[0])) : 0; + e.spell_type_index = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.class_id = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.stance_index = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.nHSND_value = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.pH_value = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; + e.pS_value = row[6] ? static_cast(strtoul(row[6], nullptr, 10)) : 0; + e.pHS_value = row[7] ? static_cast(strtoul(row[7], nullptr, 10)) : 0; + e.pN_value = row[8] ? static_cast(strtoul(row[8], nullptr, 10)) : 0; + e.pHN_value = row[9] ? static_cast(strtoul(row[9], nullptr, 10)) : 0; + e.pSN_value = row[10] ? static_cast(strtoul(row[10], nullptr, 10)) : 0; + e.pHSN_value = row[11] ? static_cast(strtoul(row[11], nullptr, 10)) : 0; + e.pD_value = row[12] ? static_cast(strtoul(row[12], nullptr, 10)) : 0; + e.pHD_value = row[13] ? static_cast(strtoul(row[13], nullptr, 10)) : 0; + e.pSD_value = row[14] ? static_cast(strtoul(row[14], nullptr, 10)) : 0; + e.pHSD_value = row[15] ? static_cast(strtoul(row[15], nullptr, 10)) : 0; + e.pND_value = row[16] ? static_cast(strtoul(row[16], nullptr, 10)) : 0; + e.pHND_value = row[17] ? static_cast(strtoul(row[17], nullptr, 10)) : 0; + e.pSND_value = row[18] ? static_cast(strtoul(row[18], nullptr, 10)) : 0; + e.pHSND_value = row[19] ? static_cast(strtoul(row[19], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -507,6 +508,100 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotSpellCastingChances &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.id)); + v.push_back(std::to_string(e.spell_type_index)); + v.push_back(std::to_string(e.class_id)); + v.push_back(std::to_string(e.stance_index)); + v.push_back(std::to_string(e.nHSND_value)); + v.push_back(std::to_string(e.pH_value)); + v.push_back(std::to_string(e.pS_value)); + v.push_back(std::to_string(e.pHS_value)); + v.push_back(std::to_string(e.pN_value)); + v.push_back(std::to_string(e.pHN_value)); + v.push_back(std::to_string(e.pSN_value)); + v.push_back(std::to_string(e.pHSN_value)); + v.push_back(std::to_string(e.pD_value)); + v.push_back(std::to_string(e.pHD_value)); + v.push_back(std::to_string(e.pSD_value)); + v.push_back(std::to_string(e.pHSD_value)); + v.push_back(std::to_string(e.pND_value)); + v.push_back(std::to_string(e.pHND_value)); + v.push_back(std::to_string(e.pSND_value)); + v.push_back(std::to_string(e.pHSND_value)); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.id)); + v.push_back(std::to_string(e.spell_type_index)); + v.push_back(std::to_string(e.class_id)); + v.push_back(std::to_string(e.stance_index)); + v.push_back(std::to_string(e.nHSND_value)); + v.push_back(std::to_string(e.pH_value)); + v.push_back(std::to_string(e.pS_value)); + v.push_back(std::to_string(e.pHS_value)); + v.push_back(std::to_string(e.pN_value)); + v.push_back(std::to_string(e.pHN_value)); + v.push_back(std::to_string(e.pSN_value)); + v.push_back(std::to_string(e.pHSN_value)); + v.push_back(std::to_string(e.pD_value)); + v.push_back(std::to_string(e.pHD_value)); + v.push_back(std::to_string(e.pSD_value)); + v.push_back(std::to_string(e.pHSD_value)); + v.push_back(std::to_string(e.pND_value)); + v.push_back(std::to_string(e.pHND_value)); + v.push_back(std::to_string(e.pSND_value)); + v.push_back(std::to_string(e.pHSND_value)); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_SPELL_CASTING_CHANCES_REPOSITORY_H diff --git a/common/repositories/base/base_bot_spell_settings_repository.h b/common/repositories/base/base_bot_spell_settings_repository.h index 91fbeabd1..3cea77636 100644 --- a/common/repositories/base/base_bot_spell_settings_repository.h +++ b/common/repositories/base/base_bot_spell_settings_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_SPELL_SETTINGS_REPOSITORY_H @@ -128,8 +128,9 @@ public: { auto results = db.QueryDatabase( fmt::format( - "{} WHERE id = {} LIMIT 1", + "{} WHERE {} = {} LIMIT 1", BaseSelect(), + PrimaryKey(), bot_spell_settings_id ) ); @@ -138,13 +139,13 @@ public: if (results.RowCount() == 1) { BotSpellSettings e{}; - e.id = static_cast(strtoul(row[0], nullptr, 10)); - e.bot_id = static_cast(atoi(row[1])); - e.spell_id = static_cast(atoi(row[2])); - e.priority = static_cast(atoi(row[3])); - e.min_hp = static_cast(atoi(row[4])); - e.max_hp = static_cast(atoi(row[5])); - e.is_enabled = static_cast(strtoul(row[6], nullptr, 10)); + e.id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.bot_id = row[1] ? static_cast(atoi(row[1])) : 0; + e.spell_id = row[2] ? static_cast(atoi(row[2])) : 0; + e.priority = row[3] ? static_cast(atoi(row[3])) : 0; + e.min_hp = row[4] ? static_cast(atoi(row[4])) : 0; + e.max_hp = row[5] ? static_cast(atoi(row[5])) : 0; + e.is_enabled = row[6] ? static_cast(strtoul(row[6], nullptr, 10)) : 1; return e; } @@ -281,13 +282,13 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotSpellSettings e{}; - e.id = static_cast(strtoul(row[0], nullptr, 10)); - e.bot_id = static_cast(atoi(row[1])); - e.spell_id = static_cast(atoi(row[2])); - e.priority = static_cast(atoi(row[3])); - e.min_hp = static_cast(atoi(row[4])); - e.max_hp = static_cast(atoi(row[5])); - e.is_enabled = static_cast(strtoul(row[6], nullptr, 10)); + e.id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.bot_id = row[1] ? static_cast(atoi(row[1])) : 0; + e.spell_id = row[2] ? static_cast(atoi(row[2])) : 0; + e.priority = row[3] ? static_cast(atoi(row[3])) : 0; + e.min_hp = row[4] ? static_cast(atoi(row[4])) : 0; + e.max_hp = row[5] ? static_cast(atoi(row[5])) : 0; + e.is_enabled = row[6] ? static_cast(strtoul(row[6], nullptr, 10)) : 1; all_entries.push_back(e); } @@ -312,13 +313,13 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotSpellSettings e{}; - e.id = static_cast(strtoul(row[0], nullptr, 10)); - e.bot_id = static_cast(atoi(row[1])); - e.spell_id = static_cast(atoi(row[2])); - e.priority = static_cast(atoi(row[3])); - e.min_hp = static_cast(atoi(row[4])); - e.max_hp = static_cast(atoi(row[5])); - e.is_enabled = static_cast(strtoul(row[6], nullptr, 10)); + e.id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.bot_id = row[1] ? static_cast(atoi(row[1])) : 0; + e.spell_id = row[2] ? static_cast(atoi(row[2])) : 0; + e.priority = row[3] ? static_cast(atoi(row[3])) : 0; + e.min_hp = row[4] ? static_cast(atoi(row[4])) : 0; + e.max_hp = row[5] ? static_cast(atoi(row[5])) : 0; + e.is_enabled = row[6] ? static_cast(strtoul(row[6], nullptr, 10)) : 1; all_entries.push_back(e); } @@ -377,6 +378,74 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotSpellSettings &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.id)); + v.push_back(std::to_string(e.bot_id)); + v.push_back(std::to_string(e.spell_id)); + v.push_back(std::to_string(e.priority)); + v.push_back(std::to_string(e.min_hp)); + v.push_back(std::to_string(e.max_hp)); + v.push_back(std::to_string(e.is_enabled)); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.id)); + v.push_back(std::to_string(e.bot_id)); + v.push_back(std::to_string(e.spell_id)); + v.push_back(std::to_string(e.priority)); + v.push_back(std::to_string(e.min_hp)); + v.push_back(std::to_string(e.max_hp)); + v.push_back(std::to_string(e.is_enabled)); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_SPELL_SETTINGS_REPOSITORY_H diff --git a/common/repositories/base/base_bot_spells_entries_repository.h b/common/repositories/base/base_bot_spells_entries_repository.h index 72a7d837a..b8c1fe5e1 100644 --- a/common/repositories/base/base_bot_spells_entries_repository.h +++ b/common/repositories/base/base_bot_spells_entries_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_SPELLS_ENTRIES_REPOSITORY_H @@ -160,8 +160,9 @@ public: { auto results = db.QueryDatabase( fmt::format( - "{} WHERE id = {} LIMIT 1", + "{} WHERE {} = {} LIMIT 1", BaseSelect(), + PrimaryKey(), bot_spells_entries_id ) ); @@ -170,21 +171,21 @@ public: if (results.RowCount() == 1) { BotSpellsEntries e{}; - e.id = static_cast(strtoul(row[0], nullptr, 10)); - e.npc_spells_id = static_cast(atoi(row[1])); - e.spellid = static_cast(atoi(row[2])); - e.type = static_cast(strtoul(row[3], nullptr, 10)); - e.minlevel = static_cast(strtoul(row[4], nullptr, 10)); - e.maxlevel = static_cast(strtoul(row[5], nullptr, 10)); - e.manacost = static_cast(atoi(row[6])); - e.recast_delay = static_cast(atoi(row[7])); - e.priority = static_cast(atoi(row[8])); - e.resist_adjust = static_cast(atoi(row[9])); - e.min_hp = static_cast(atoi(row[10])); - e.max_hp = static_cast(atoi(row[11])); + e.id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.npc_spells_id = row[1] ? static_cast(atoi(row[1])) : 0; + e.spellid = row[2] ? static_cast(atoi(row[2])) : 0; + e.type = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.minlevel = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.maxlevel = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 255; + e.manacost = row[6] ? static_cast(atoi(row[6])) : -1; + e.recast_delay = row[7] ? static_cast(atoi(row[7])) : -1; + e.priority = row[8] ? static_cast(atoi(row[8])) : 0; + e.resist_adjust = row[9] ? static_cast(atoi(row[9])) : 0; + e.min_hp = row[10] ? static_cast(atoi(row[10])) : 0; + e.max_hp = row[11] ? static_cast(atoi(row[11])) : 0; e.bucket_name = row[12] ? row[12] : ""; e.bucket_value = row[13] ? row[13] : ""; - e.bucket_comparison = static_cast(strtoul(row[14], nullptr, 10)); + e.bucket_comparison = row[14] ? static_cast(strtoul(row[14], nullptr, 10)) : 0; return e; } @@ -345,21 +346,21 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotSpellsEntries e{}; - e.id = static_cast(strtoul(row[0], nullptr, 10)); - e.npc_spells_id = static_cast(atoi(row[1])); - e.spellid = static_cast(atoi(row[2])); - e.type = static_cast(strtoul(row[3], nullptr, 10)); - e.minlevel = static_cast(strtoul(row[4], nullptr, 10)); - e.maxlevel = static_cast(strtoul(row[5], nullptr, 10)); - e.manacost = static_cast(atoi(row[6])); - e.recast_delay = static_cast(atoi(row[7])); - e.priority = static_cast(atoi(row[8])); - e.resist_adjust = static_cast(atoi(row[9])); - e.min_hp = static_cast(atoi(row[10])); - e.max_hp = static_cast(atoi(row[11])); + e.id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.npc_spells_id = row[1] ? static_cast(atoi(row[1])) : 0; + e.spellid = row[2] ? static_cast(atoi(row[2])) : 0; + e.type = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.minlevel = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.maxlevel = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 255; + e.manacost = row[6] ? static_cast(atoi(row[6])) : -1; + e.recast_delay = row[7] ? static_cast(atoi(row[7])) : -1; + e.priority = row[8] ? static_cast(atoi(row[8])) : 0; + e.resist_adjust = row[9] ? static_cast(atoi(row[9])) : 0; + e.min_hp = row[10] ? static_cast(atoi(row[10])) : 0; + e.max_hp = row[11] ? static_cast(atoi(row[11])) : 0; e.bucket_name = row[12] ? row[12] : ""; e.bucket_value = row[13] ? row[13] : ""; - e.bucket_comparison = static_cast(strtoul(row[14], nullptr, 10)); + e.bucket_comparison = row[14] ? static_cast(strtoul(row[14], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -384,21 +385,21 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotSpellsEntries e{}; - e.id = static_cast(strtoul(row[0], nullptr, 10)); - e.npc_spells_id = static_cast(atoi(row[1])); - e.spellid = static_cast(atoi(row[2])); - e.type = static_cast(strtoul(row[3], nullptr, 10)); - e.minlevel = static_cast(strtoul(row[4], nullptr, 10)); - e.maxlevel = static_cast(strtoul(row[5], nullptr, 10)); - e.manacost = static_cast(atoi(row[6])); - e.recast_delay = static_cast(atoi(row[7])); - e.priority = static_cast(atoi(row[8])); - e.resist_adjust = static_cast(atoi(row[9])); - e.min_hp = static_cast(atoi(row[10])); - e.max_hp = static_cast(atoi(row[11])); + e.id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.npc_spells_id = row[1] ? static_cast(atoi(row[1])) : 0; + e.spellid = row[2] ? static_cast(atoi(row[2])) : 0; + e.type = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.minlevel = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.maxlevel = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 255; + e.manacost = row[6] ? static_cast(atoi(row[6])) : -1; + e.recast_delay = row[7] ? static_cast(atoi(row[7])) : -1; + e.priority = row[8] ? static_cast(atoi(row[8])) : 0; + e.resist_adjust = row[9] ? static_cast(atoi(row[9])) : 0; + e.min_hp = row[10] ? static_cast(atoi(row[10])) : 0; + e.max_hp = row[11] ? static_cast(atoi(row[11])) : 0; e.bucket_name = row[12] ? row[12] : ""; e.bucket_value = row[13] ? row[13] : ""; - e.bucket_comparison = static_cast(strtoul(row[14], nullptr, 10)); + e.bucket_comparison = row[14] ? static_cast(strtoul(row[14], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -457,6 +458,90 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotSpellsEntries &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.id)); + v.push_back(std::to_string(e.npc_spells_id)); + v.push_back(std::to_string(e.spellid)); + v.push_back(std::to_string(e.type)); + v.push_back(std::to_string(e.minlevel)); + v.push_back(std::to_string(e.maxlevel)); + v.push_back(std::to_string(e.manacost)); + v.push_back(std::to_string(e.recast_delay)); + v.push_back(std::to_string(e.priority)); + v.push_back(std::to_string(e.resist_adjust)); + v.push_back(std::to_string(e.min_hp)); + v.push_back(std::to_string(e.max_hp)); + v.push_back("'" + Strings::Escape(e.bucket_name) + "'"); + v.push_back("'" + Strings::Escape(e.bucket_value) + "'"); + v.push_back(std::to_string(e.bucket_comparison)); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.id)); + v.push_back(std::to_string(e.npc_spells_id)); + v.push_back(std::to_string(e.spellid)); + v.push_back(std::to_string(e.type)); + v.push_back(std::to_string(e.minlevel)); + v.push_back(std::to_string(e.maxlevel)); + v.push_back(std::to_string(e.manacost)); + v.push_back(std::to_string(e.recast_delay)); + v.push_back(std::to_string(e.priority)); + v.push_back(std::to_string(e.resist_adjust)); + v.push_back(std::to_string(e.min_hp)); + v.push_back(std::to_string(e.max_hp)); + v.push_back("'" + Strings::Escape(e.bucket_name) + "'"); + v.push_back("'" + Strings::Escape(e.bucket_value) + "'"); + v.push_back(std::to_string(e.bucket_comparison)); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_SPELLS_ENTRIES_REPOSITORY_H diff --git a/common/repositories/base/base_bot_stances_repository.h b/common/repositories/base/base_bot_stances_repository.h index 045203d63..8cb6dad57 100644 --- a/common/repositories/base/base_bot_stances_repository.h +++ b/common/repositories/base/base_bot_stances_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_STANCES_REPOSITORY_H @@ -108,8 +108,9 @@ public: { auto results = db.QueryDatabase( fmt::format( - "{} WHERE id = {} LIMIT 1", + "{} WHERE {} = {} LIMIT 1", BaseSelect(), + PrimaryKey(), bot_stances_id ) ); @@ -118,8 +119,8 @@ public: if (results.RowCount() == 1) { BotStances e{}; - e.bot_id = static_cast(strtoul(row[0], nullptr, 10)); - e.stance_id = static_cast(strtoul(row[1], nullptr, 10)); + e.bot_id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.stance_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; return e; } @@ -242,8 +243,8 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotStances e{}; - e.bot_id = static_cast(strtoul(row[0], nullptr, 10)); - e.stance_id = static_cast(strtoul(row[1], nullptr, 10)); + e.bot_id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.stance_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -268,8 +269,8 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotStances e{}; - e.bot_id = static_cast(strtoul(row[0], nullptr, 10)); - e.stance_id = static_cast(strtoul(row[1], nullptr, 10)); + e.bot_id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.stance_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -328,6 +329,64 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotStances &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.bot_id)); + v.push_back(std::to_string(e.stance_id)); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.bot_id)); + v.push_back(std::to_string(e.stance_id)); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_STANCES_REPOSITORY_H diff --git a/common/repositories/base/base_bot_starting_items_repository.h b/common/repositories/base/base_bot_starting_items_repository.h index da0ad2ccc..2042b99fd 100644 --- a/common/repositories/base/base_bot_starting_items_repository.h +++ b/common/repositories/base/base_bot_starting_items_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_STARTING_ITEMS_REPOSITORY_H @@ -16,7 +16,6 @@ #include "../../strings.h" #include - class BaseBotStartingItemsRepository { public: struct BotStartingItems { @@ -25,6 +24,7 @@ public: uint32_t classes; uint32_t item_id; uint8_t item_charges; + uint8_t min_status; int32_t slot_id; int8_t min_expansion; int8_t max_expansion; @@ -45,6 +45,7 @@ public: "classes", "item_id", "item_charges", + "min_status", "slot_id", "min_expansion", "max_expansion", @@ -61,6 +62,7 @@ public: "classes", "item_id", "item_charges", + "min_status", "slot_id", "min_expansion", "max_expansion", @@ -111,6 +113,7 @@ public: e.classes = 0; e.item_id = 0; e.item_charges = 1; + e.min_status = 0; e.slot_id = -1; e.min_expansion = -1; e.max_expansion = -1; @@ -152,16 +155,17 @@ public: if (results.RowCount() == 1) { BotStartingItems e{}; - e.id = static_cast(strtoul(row[0], nullptr, 10)); - e.races = static_cast(strtoul(row[1], nullptr, 10)); - e.classes = static_cast(strtoul(row[2], nullptr, 10)); - e.item_id = static_cast(strtoul(row[3], nullptr, 10)); - e.item_charges = static_cast(strtoul(row[4], nullptr, 10)); - e.slot_id = static_cast(atoi(row[5])); - e.min_expansion = static_cast(atoi(row[6])); - e.max_expansion = static_cast(atoi(row[7])); - e.content_flags = row[8] ? row[8] : ""; - e.content_flags_disabled = row[9] ? row[9] : ""; + e.id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.races = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.classes = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.item_id = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.item_charges = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 1; + e.min_status = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; + e.slot_id = row[6] ? static_cast(atoi(row[6])) : -1; + e.min_expansion = row[7] ? static_cast(atoi(row[7])) : -1; + e.max_expansion = row[8] ? static_cast(atoi(row[8])) : -1; + e.content_flags = row[9] ? row[9] : ""; + e.content_flags_disabled = row[10] ? row[10] : ""; return e; } @@ -199,11 +203,12 @@ public: v.push_back(columns[2] + " = " + std::to_string(e.classes)); v.push_back(columns[3] + " = " + std::to_string(e.item_id)); v.push_back(columns[4] + " = " + std::to_string(e.item_charges)); - v.push_back(columns[5] + " = " + std::to_string(e.slot_id)); - v.push_back(columns[6] + " = " + std::to_string(e.min_expansion)); - v.push_back(columns[7] + " = " + std::to_string(e.max_expansion)); - v.push_back(columns[8] + " = '" + Strings::Escape(e.content_flags) + "'"); - v.push_back(columns[9] + " = '" + Strings::Escape(e.content_flags_disabled) + "'"); + v.push_back(columns[5] + " = " + std::to_string(e.min_status)); + v.push_back(columns[6] + " = " + std::to_string(e.slot_id)); + v.push_back(columns[7] + " = " + std::to_string(e.min_expansion)); + v.push_back(columns[8] + " = " + std::to_string(e.max_expansion)); + v.push_back(columns[9] + " = '" + Strings::Escape(e.content_flags) + "'"); + v.push_back(columns[10] + " = '" + Strings::Escape(e.content_flags_disabled) + "'"); auto results = db.QueryDatabase( fmt::format( @@ -230,6 +235,7 @@ public: v.push_back(std::to_string(e.classes)); v.push_back(std::to_string(e.item_id)); v.push_back(std::to_string(e.item_charges)); + v.push_back(std::to_string(e.min_status)); v.push_back(std::to_string(e.slot_id)); v.push_back(std::to_string(e.min_expansion)); v.push_back(std::to_string(e.max_expansion)); @@ -269,6 +275,7 @@ public: v.push_back(std::to_string(e.classes)); v.push_back(std::to_string(e.item_id)); v.push_back(std::to_string(e.item_charges)); + v.push_back(std::to_string(e.min_status)); v.push_back(std::to_string(e.slot_id)); v.push_back(std::to_string(e.min_expansion)); v.push_back(std::to_string(e.max_expansion)); @@ -307,16 +314,17 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotStartingItems e{}; - e.id = static_cast(strtoul(row[0], nullptr, 10)); - e.races = static_cast(strtoul(row[1], nullptr, 10)); - e.classes = static_cast(strtoul(row[2], nullptr, 10)); - e.item_id = static_cast(strtoul(row[3], nullptr, 10)); - e.item_charges = static_cast(strtoul(row[4], nullptr, 10)); - e.slot_id = static_cast(atoi(row[5])); - e.min_expansion = static_cast(atoi(row[6])); - e.max_expansion = static_cast(atoi(row[7])); - e.content_flags = row[8] ? row[8] : ""; - e.content_flags_disabled = row[9] ? row[9] : ""; + e.id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.races = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.classes = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.item_id = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.item_charges = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 1; + e.min_status = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; + e.slot_id = row[6] ? static_cast(atoi(row[6])) : -1; + e.min_expansion = row[7] ? static_cast(atoi(row[7])) : -1; + e.max_expansion = row[8] ? static_cast(atoi(row[8])) : -1; + e.content_flags = row[9] ? row[9] : ""; + e.content_flags_disabled = row[10] ? row[10] : ""; all_entries.push_back(e); } @@ -341,16 +349,17 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotStartingItems e{}; - e.id = static_cast(strtoul(row[0], nullptr, 10)); - e.races = static_cast(strtoul(row[1], nullptr, 10)); - e.classes = static_cast(strtoul(row[2], nullptr, 10)); - e.item_id = static_cast(strtoul(row[3], nullptr, 10)); - e.item_charges = static_cast(strtoul(row[4], nullptr, 10)); - e.slot_id = static_cast(atoi(row[5])); - e.min_expansion = static_cast(atoi(row[6])); - e.max_expansion = static_cast(atoi(row[7])); - e.content_flags = row[8] ? row[8] : ""; - e.content_flags_disabled = row[9] ? row[9] : ""; + e.id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.races = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.classes = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.item_id = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.item_charges = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 1; + e.min_status = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; + e.slot_id = row[6] ? static_cast(atoi(row[6])) : -1; + e.min_expansion = row[7] ? static_cast(atoi(row[7])) : -1; + e.max_expansion = row[8] ? static_cast(atoi(row[8])) : -1; + e.content_flags = row[9] ? row[9] : ""; + e.content_flags_disabled = row[10] ? row[10] : ""; all_entries.push_back(e); } @@ -409,6 +418,82 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotStartingItems &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.id)); + v.push_back(std::to_string(e.races)); + v.push_back(std::to_string(e.classes)); + v.push_back(std::to_string(e.item_id)); + v.push_back(std::to_string(e.item_charges)); + v.push_back(std::to_string(e.min_status)); + v.push_back(std::to_string(e.slot_id)); + v.push_back(std::to_string(e.min_expansion)); + v.push_back(std::to_string(e.max_expansion)); + v.push_back("'" + Strings::Escape(e.content_flags) + "'"); + v.push_back("'" + Strings::Escape(e.content_flags_disabled) + "'"); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.id)); + v.push_back(std::to_string(e.races)); + v.push_back(std::to_string(e.classes)); + v.push_back(std::to_string(e.item_id)); + v.push_back(std::to_string(e.item_charges)); + v.push_back(std::to_string(e.min_status)); + v.push_back(std::to_string(e.slot_id)); + v.push_back(std::to_string(e.min_expansion)); + v.push_back(std::to_string(e.max_expansion)); + v.push_back("'" + Strings::Escape(e.content_flags) + "'"); + v.push_back("'" + Strings::Escape(e.content_flags_disabled) + "'"); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_STARTING_ITEMS_REPOSITORY_H diff --git a/common/repositories/base/base_bot_timers_repository.h b/common/repositories/base/base_bot_timers_repository.h index 45bb495be..7fc3ccff8 100644 --- a/common/repositories/base/base_bot_timers_repository.h +++ b/common/repositories/base/base_bot_timers_repository.h @@ -6,7 +6,7 @@ * Any modifications to base repositories are to be made by the generator only * * @generator ./utils/scripts/generators/repository-generator.pl - * @docs https://eqemu.gitbook.io/server/in-development/developer-area/repositories + * @docs https://docs.eqemu.io/developer/repositories */ #ifndef EQEMU_BASE_BOT_TIMERS_REPOSITORY_H @@ -16,7 +16,6 @@ #include "../../strings.h" #include - class BaseBotTimersRepository { public: struct BotTimers { @@ -148,15 +147,15 @@ public: if (results.RowCount() == 1) { BotTimers e{}; - e.bot_id = static_cast(strtoul(row[0], nullptr, 10)); - e.timer_id = static_cast(strtoul(row[1], nullptr, 10)); - e.timer_value = static_cast(strtoul(row[2], nullptr, 10)); - e.recast_time = static_cast(strtoul(row[3], nullptr, 10)); - e.is_spell = static_cast(strtoul(row[4], nullptr, 10)); - e.is_disc = static_cast(strtoul(row[5], nullptr, 10)); - e.spell_id = static_cast(strtoul(row[6], nullptr, 10)); - e.is_item = static_cast(strtoul(row[7], nullptr, 10)); - e.item_id = static_cast(strtoul(row[8], nullptr, 10)); + e.bot_id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.timer_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.timer_value = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.recast_time = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.is_spell = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.is_disc = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; + e.spell_id = row[6] ? static_cast(strtoul(row[6], nullptr, 10)) : 0; + e.is_item = row[7] ? static_cast(strtoul(row[7], nullptr, 10)) : 0; + e.item_id = row[8] ? static_cast(strtoul(row[8], nullptr, 10)) : 0; return e; } @@ -300,15 +299,15 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotTimers e{}; - e.bot_id = static_cast(strtoul(row[0], nullptr, 10)); - e.timer_id = static_cast(strtoul(row[1], nullptr, 10)); - e.timer_value = static_cast(strtoul(row[2], nullptr, 10)); - e.recast_time = static_cast(strtoul(row[3], nullptr, 10)); - e.is_spell = static_cast(strtoul(row[4], nullptr, 10)); - e.is_disc = static_cast(strtoul(row[5], nullptr, 10)); - e.spell_id = static_cast(strtoul(row[6], nullptr, 10)); - e.is_item = static_cast(strtoul(row[7], nullptr, 10)); - e.item_id = static_cast(strtoul(row[8], nullptr, 10)); + e.bot_id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.timer_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.timer_value = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.recast_time = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.is_spell = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.is_disc = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; + e.spell_id = row[6] ? static_cast(strtoul(row[6], nullptr, 10)) : 0; + e.is_item = row[7] ? static_cast(strtoul(row[7], nullptr, 10)) : 0; + e.item_id = row[8] ? static_cast(strtoul(row[8], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -333,15 +332,15 @@ public: for (auto row = results.begin(); row != results.end(); ++row) { BotTimers e{}; - e.bot_id = static_cast(strtoul(row[0], nullptr, 10)); - e.timer_id = static_cast(strtoul(row[1], nullptr, 10)); - e.timer_value = static_cast(strtoul(row[2], nullptr, 10)); - e.recast_time = static_cast(strtoul(row[3], nullptr, 10)); - e.is_spell = static_cast(strtoul(row[4], nullptr, 10)); - e.is_disc = static_cast(strtoul(row[5], nullptr, 10)); - e.spell_id = static_cast(strtoul(row[6], nullptr, 10)); - e.is_item = static_cast(strtoul(row[7], nullptr, 10)); - e.item_id = static_cast(strtoul(row[8], nullptr, 10)); + e.bot_id = row[0] ? static_cast(strtoul(row[0], nullptr, 10)) : 0; + e.timer_id = row[1] ? static_cast(strtoul(row[1], nullptr, 10)) : 0; + e.timer_value = row[2] ? static_cast(strtoul(row[2], nullptr, 10)) : 0; + e.recast_time = row[3] ? static_cast(strtoul(row[3], nullptr, 10)) : 0; + e.is_spell = row[4] ? static_cast(strtoul(row[4], nullptr, 10)) : 0; + e.is_disc = row[5] ? static_cast(strtoul(row[5], nullptr, 10)) : 0; + e.spell_id = row[6] ? static_cast(strtoul(row[6], nullptr, 10)) : 0; + e.is_item = row[7] ? static_cast(strtoul(row[7], nullptr, 10)) : 0; + e.item_id = row[8] ? static_cast(strtoul(row[8], nullptr, 10)) : 0; all_entries.push_back(e); } @@ -400,6 +399,78 @@ public: return (results.Success() && results.begin()[0] ? strtoll(results.begin()[0], nullptr, 10) : 0); } + static std::string BaseReplace() + { + return fmt::format( + "REPLACE INTO {} ({}) ", + TableName(), + ColumnsRaw() + ); + } + + static int ReplaceOne( + Database& db, + const BotTimers &e + ) + { + std::vector v; + + v.push_back(std::to_string(e.bot_id)); + v.push_back(std::to_string(e.timer_id)); + v.push_back(std::to_string(e.timer_value)); + v.push_back(std::to_string(e.recast_time)); + v.push_back(std::to_string(e.is_spell)); + v.push_back(std::to_string(e.is_disc)); + v.push_back(std::to_string(e.spell_id)); + v.push_back(std::to_string(e.is_item)); + v.push_back(std::to_string(e.item_id)); + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES ({})", + BaseReplace(), + Strings::Implode(",", v) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } + + static int ReplaceMany( + Database& db, + const std::vector &entries + ) + { + std::vector insert_chunks; + + for (auto &e: entries) { + std::vector v; + + v.push_back(std::to_string(e.bot_id)); + v.push_back(std::to_string(e.timer_id)); + v.push_back(std::to_string(e.timer_value)); + v.push_back(std::to_string(e.recast_time)); + v.push_back(std::to_string(e.is_spell)); + v.push_back(std::to_string(e.is_disc)); + v.push_back(std::to_string(e.spell_id)); + v.push_back(std::to_string(e.is_item)); + v.push_back(std::to_string(e.item_id)); + + insert_chunks.push_back("(" + Strings::Implode(",", v) + ")"); + } + + std::vector v; + + auto results = db.QueryDatabase( + fmt::format( + "{} VALUES {}", + BaseReplace(), + Strings::Implode(",", insert_chunks) + ) + ); + + return (results.Success() ? results.RowsAffected() : 0); + } }; #endif //EQEMU_BASE_BOT_TIMERS_REPOSITORY_H diff --git a/common/repositories/bot_data_repository.h b/common/repositories/bot_data_repository.h index e26781118..f6508479f 100644 --- a/common/repositories/bot_data_repository.h +++ b/common/repositories/bot_data_repository.h @@ -44,7 +44,46 @@ public: */ // Custom extended repository methods here + static bool SaveAllHelmAppearances(Database& db, const uint32 owner_id, const bool show_flag) + { + auto results = db.QueryDatabase( + fmt::format( + "UPDATE `{}` SET `show_helm` = {} WHERE `owner_id` = {}", + TableName(), + show_flag ? 1 : 0, + owner_id + ) + ); + return results.Success(); + } + + static bool ToggleAllHelmAppearances(Database& db, const uint32 owner_id) + { + auto results = db.QueryDatabase( + fmt::format( + "UPDATE `{}` SET `show_helm` = (`show_helm` XOR '1') WHERE `owner_id` = {}", + TableName(), + owner_id + ) + ); + + return results.Success(); + } + + static bool SaveAllFollowDistances(Database& db, const uint32 owner_id, const uint32 follow_distance) + { + auto results = db.QueryDatabase( + fmt::format( + "UPDATE `{}` SET `follow_distance` = {} WHERE `owner_id` = {}", + TableName(), + follow_distance, + owner_id + ) + ); + + return results.Success(); + } }; #endif //EQEMU_BOT_DATA_REPOSITORY_H diff --git a/common/repositories/bot_inspect_messages_repository.h b/common/repositories/bot_inspect_messages_repository.h index 27d486a57..bf9bef710 100644 --- a/common/repositories/bot_inspect_messages_repository.h +++ b/common/repositories/bot_inspect_messages_repository.h @@ -44,7 +44,36 @@ public: */ // Custom extended repository methods here + static bool SaveAllInspectMessages(Database& db, const uint32 owner_id, const std::string& inspect_message) + { + auto results = db.QueryDatabase( + fmt::format( + SQL( + INSERT INTO `bot_inspect_messages` (`bot_id`, `inspect_message`) VALUES + (SELECT `bot_id`, '{}' inspect_message FROM `bot_data` WHERE `owner_id` = {}) + ), + inspect_message, + owner_id + ) + ); + return results.Success(); + } + + static bool DeleteAllInspectMessages(Database& db, const uint32 owner_id) + { + auto results = db.QueryDatabase( + fmt::format( + SQL( + DELETE FROM `bot_inspect_messages` + WHERE `bot_id` IN (SELECT `bot_id` FROM `bot_data` WHERE `owner_id` = {}) + ), + owner_id + ) + ); + + return results.Success(); + } }; #endif //EQEMU_BOT_INSPECT_MESSAGES_REPOSITORY_H diff --git a/common/repositories/bot_inventories_repository.h b/common/repositories/bot_inventories_repository.h index 84123fc22..b16a1237f 100644 --- a/common/repositories/bot_inventories_repository.h +++ b/common/repositories/bot_inventories_repository.h @@ -44,7 +44,57 @@ public: */ // Custom extended repository methods here + static bool UpdateItemColors(Database& db, const uint32 bot_id, const uint32 color, const std::string& where_clause) + { + auto results = db.QueryDatabase( + fmt::format( + "UPDATE `{}` SET `inst_color` = {} WHERE `bot_id` = {} AND `slot_id` {}", + TableName(), + color, + bot_id, + where_clause + ) + ); + return results.Success(); + } + + static bool SaveAllArmorColors(Database& db, const uint32 owner_id, const uint32 color) + { + auto results = db.QueryDatabase( + fmt::format( + "UPDATE `{}` SET `inst_color` = {} WHERE `slot_id` IN ({}, {}, {}, {}, {}, {}, {}) AND `bot_id` IN (SELECT `bot_id` FROM `bot_data` WHERE `owner_id` = {})", + TableName(), + color, + EQ::invslot::slotHead, + EQ::invslot::slotChest, + EQ::invslot::slotArms, + EQ::invslot::slotWrist1, + EQ::invslot::slotWrist2, + EQ::invslot::slotHands, + EQ::invslot::slotLegs, + EQ::invslot::slotFeet, + owner_id + ) + ); + + return results.Success(); + } + + static bool SaveAllArmorColorsBySlot(Database& db, const uint32 owner_id, const int16 slot_id, const uint32 color) + { + auto results = db.QueryDatabase( + fmt::format( + "UPDATE `{}` SET `inst_color` = {} WHERE `slot_id` = {} AND `bot_id` IN (SELECT `bot_id` FROM `bot_data` WHERE `owner_id` = {})", + TableName(), + color, + slot_id, + owner_id + ) + ); + + return results.Success(); + } }; #endif //EQEMU_BOT_INVENTORIES_REPOSITORY_H diff --git a/common/version.h b/common/version.h index bdd54791a..66a0b9dfe 100644 --- a/common/version.h +++ b/common/version.h @@ -44,7 +44,7 @@ #define CURRENT_BINARY_DATABASE_VERSION 9256 -#define CURRENT_BINARY_BOTS_DATABASE_VERSION 9041 +#define CURRENT_BINARY_BOTS_DATABASE_VERSION 9042 #endif diff --git a/utils/scripts/generators/repository-generator.pl b/utils/scripts/generators/repository-generator.pl index 6d7554f59..5b40885b1 100644 --- a/utils/scripts/generators/repository-generator.pl +++ b/utils/scripts/generators/repository-generator.pl @@ -566,6 +566,9 @@ sub translate_mysql_data_type_to_c elsif ($mysql_data_type =~ /int/) { $struct_data_type = 'uint32_t'; } + elsif ($mysql_data_type =~ /float|decimal/) { + $struct_data_type = 'float'; + } } elsif ($mysql_data_type =~ /bigint/) { $struct_data_type = 'int64_t'; @@ -600,7 +603,8 @@ sub get_reserved_cpp_variable_names "int", "key", "rank", - "range" + "range", + "interval" ); } diff --git a/zone/bot.cpp b/zone/bot.cpp index fb3fda203..283f03840 100644 --- a/zone/bot.cpp +++ b/zone/bot.cpp @@ -228,17 +228,10 @@ Bot::Bot( strcpy(name, GetCleanName()); memset(&_botInspectMessage, 0, sizeof(InspectMessage_Struct)); - if (!database.botdb.LoadInspectMessage(GetBotID(), _botInspectMessage) && bot_owner) - bot_owner->Message(Chat::White, "%s for '%s'", BotDatabase::fail::LoadInspectMessage(), GetCleanName()); - std::string error_message; + database.botdb.LoadInspectMessage(GetBotID(), _botInspectMessage); - EquipBot(&error_message); - if (!error_message.empty()) { - if (bot_owner) - bot_owner->Message(Chat::White, error_message.c_str()); - error_message.clear(); - } + EquipBot(); if (GetClass() == Class::Rogue) { m_evade_timer.Start(); @@ -252,17 +245,12 @@ Bot::Bot( GenerateBaseStats(); bot_timers.clear(); - if (!database.botdb.LoadTimers(this) && bot_owner) { - bot_owner->Message(Chat::White, "%s for '%s'", BotDatabase::fail::LoadTimers(), GetCleanName()); - } + + database.botdb.LoadTimers(this); LoadAAs(); - if (!database.botdb.LoadBuffs(this)) { - if (bot_owner) { - bot_owner->Message(Chat::White, "&s for '%s'", BotDatabase::fail::LoadBuffs(), GetCleanName()); - } - } else { + if (database.botdb.LoadBuffs(this)) { //reapply some buffs uint32 buff_count = GetMaxBuffSlots(); for (uint32 j1 = 0; j1 < buff_count; j1++) { @@ -1335,38 +1323,23 @@ bool Bot::Save() if (!bot_owner) return false; - std::string error_message; - if (!GetBotID()) { // New bot record uint32 bot_id = 0; if (!database.botdb.SaveNewBot(this, bot_id) || !bot_id) { - bot_owner->Message(Chat::White, "%s '%s'", BotDatabase::fail::SaveNewBot(), GetCleanName()); return false; } SetBotID(bot_id); } else { // Update existing bot record if (!database.botdb.SaveBot(this)) { - bot_owner->Message(Chat::White, "%s '%s'", BotDatabase::fail::SaveBot(), GetCleanName()); return false; } } // All of these continue to process if any fail - if (!database.botdb.SaveBuffs(this)) - bot_owner->Message(Chat::White, "%s for '%s'", BotDatabase::fail::SaveBuffs(), GetCleanName()); - if (!database.botdb.SaveTimers(this)) - bot_owner->Message(Chat::White, "%s for '%s'", BotDatabase::fail::SaveTimers(), GetCleanName()); - - if (!database.botdb.SaveStance(this)) { - bot_owner->Message( - Chat::White, - fmt::format( - "Failed to save stance for '{}'.", - GetCleanName() - ).c_str() - ); - } + database.botdb.SaveBuffs(this); + database.botdb.SaveTimers(this); + database.botdb.SaveStance(this); if (!SavePet()) bot_owner->Message(Chat::White, "Failed to save pet for '%s'", GetCleanName()); @@ -1382,7 +1355,6 @@ bool Bot::DeleteBot() } if (!database.botdb.DeleteHealRotation(GetBotID())) { - bot_owner->Message(Chat::White, "%s", BotDatabase::fail::DeleteHealRotation()); return false; } @@ -1413,65 +1385,23 @@ bool Bot::DeleteBot() RemoveBotFromRaid(this); } - std::string error_message; - if (!database.botdb.DeleteItems(GetBotID())) { - bot_owner->Message( - Chat::White, - fmt::format( - "{} for '{}'.", - BotDatabase::fail::DeleteItems(), - GetCleanName() - ).c_str() - ); return false; } if (!database.botdb.DeleteTimers(GetBotID())) { - bot_owner->Message( - Chat::White, - fmt::format( - "{} for '{}'.", - BotDatabase::fail::DeleteTimers(), - GetCleanName() - ).c_str() - ); return false; } if (!database.botdb.DeleteBuffs(GetBotID())) { - bot_owner->Message( - Chat::White, - fmt::format( - "{} for '{}'.", - BotDatabase::fail::DeleteBuffs(), - GetCleanName() - ).c_str() - ); return false; } if (!database.botdb.DeleteStance(GetBotID())) { - bot_owner->Message( - Chat::White, - fmt::format( - "{} for '{}'.", - BotDatabase::fail::DeleteStance(), - GetCleanName() - ).c_str() - ); return false; } if (!database.botdb.DeleteBot(GetBotID())) { - bot_owner->Message( - Chat::White, - fmt::format( - "{} '{}'", - BotDatabase::fail::DeleteBot(), - GetCleanName() - ).c_str() - ); return false; } @@ -1511,20 +1441,16 @@ bool Bot::LoadPet() } } - std::string error_message; - uint32 pet_index = 0; if (!database.botdb.LoadPetIndex(GetBotID(), pet_index)) { - bot_owner->Message(Chat::White, "%s for %s's pet", BotDatabase::fail::LoadPetIndex(), GetCleanName()); return false; } if (!pet_index) return true; uint32 saved_pet_spell_id = 0; - if (!database.botdb.LoadPetSpellID(GetBotID(), saved_pet_spell_id)) { - bot_owner->Message(Chat::White, "%s for %s's pet", BotDatabase::fail::LoadPetSpellID(), GetCleanName()); - } + database.botdb.LoadPetSpellID(GetBotID(), saved_pet_spell_id); + if (!IsValidSpell(saved_pet_spell_id)) { bot_owner->Message(Chat::White, "Invalid spell id for %s's pet", GetCleanName()); DeletePet(); @@ -1537,7 +1463,6 @@ bool Bot::LoadPet() uint32 pet_spell_id = 0; if (!database.botdb.LoadPetStats(GetBotID(), pet_name, pet_mana, pet_hp, pet_spell_id)) { - bot_owner->Message(Chat::White, "%s for %s's pet", BotDatabase::fail::LoadPetStats(), GetCleanName()); return false; } @@ -1551,13 +1476,11 @@ bool Bot::LoadPet() SpellBuff_Struct pet_buffs[PET_BUFF_COUNT]; memset(pet_buffs, 0, (sizeof(SpellBuff_Struct) * PET_BUFF_COUNT)); - if (!database.botdb.LoadPetBuffs(GetBotID(), pet_buffs)) - bot_owner->Message(Chat::White, "%s for %s's pet", BotDatabase::fail::LoadPetBuffs(), GetCleanName()); + database.botdb.LoadPetBuffs(GetBotID(), pet_buffs); uint32 pet_items[EQ::invslot::EQUIPMENT_COUNT]; memset(pet_items, 0, (sizeof(uint32) * EQ::invslot::EQUIPMENT_COUNT)); - if (!database.botdb.LoadPetItems(GetBotID(), pet_items)) - bot_owner->Message(Chat::White, "%s for %s's pet", BotDatabase::fail::LoadPetItems(), GetCleanName()); + database.botdb.LoadPetItems(GetBotID(), pet_items); pet_inst->SetPetState(pet_buffs, pet_items); pet_inst->CalcBonuses(); @@ -1596,17 +1519,12 @@ bool Bot::SavePet() std::string pet_name_str = pet_name; safe_delete_array(pet_name) - std::string error_message; - if (!database.botdb.SavePetStats(GetBotID(), pet_name_str, pet_inst->GetMana(), pet_inst->GetHP(), pet_inst->GetPetSpellID())) { - bot_owner->Message(Chat::White, "%s for %s's pet", BotDatabase::fail::SavePetStats(), GetCleanName()); return false; } - if (!database.botdb.SavePetBuffs(GetBotID(), pet_buffs)) - bot_owner->Message(Chat::White, "%s for %s's pet", BotDatabase::fail::SavePetBuffs(), GetCleanName()); - if (!database.botdb.SavePetItems(GetBotID(), pet_items)) - bot_owner->Message(Chat::White, "%s for %s's pet", BotDatabase::fail::SavePetItems(), GetCleanName()); + database.botdb.SavePetBuffs(GetBotID(), pet_buffs); + database.botdb.SavePetItems(GetBotID(), pet_items); return true; } @@ -1617,18 +1535,13 @@ bool Bot::DeletePet() if (!bot_owner) return false; - std::string error_message; - if (!database.botdb.DeletePetItems(GetBotID())) { - bot_owner->Message(Chat::White, "%s for %s's pet", BotDatabase::fail::DeletePetItems(), GetCleanName()); return false; } if (!database.botdb.DeletePetBuffs(GetBotID())) { - bot_owner->Message(Chat::White, "%s for %s's pet", BotDatabase::fail::DeletePetBuffs(), GetCleanName()); return false; } if (!database.botdb.DeletePetStats(GetBotID())) { - bot_owner->Message(Chat::White, "%s for %s's pet", BotDatabase::fail::DeletePetStats(), GetCleanName()); return false; } @@ -3379,29 +3292,26 @@ bool Bot::Spawn(Client* botCharacterOwner) { } // Deletes the inventory record for the specified item from the database for this bot. -void Bot::RemoveBotItemBySlot(uint16 slot_id, std::string *error_message) +void Bot::RemoveBotItemBySlot(uint16 slot_id) { if (!GetBotID()) { return; } - if (!database.botdb.DeleteItemBySlot(GetBotID(), slot_id)) { - *error_message = BotDatabase::fail::DeleteItemBySlot(); - } + database.botdb.DeleteItemBySlot(GetBotID(), slot_id); m_inv.DeleteItem(slot_id); UpdateEquipmentLight(); } // Retrieves all the inventory records from the database for this bot. -void Bot::GetBotItems(EQ::InventoryProfile &inv, std::string* error_message) +void Bot::GetBotItems(EQ::InventoryProfile &inv) { if (!GetBotID()) { return; } if (!database.botdb.LoadItems(GetBotID(), inv)) { - *error_message = BotDatabase::fail::LoadItems(); return; } @@ -3732,7 +3642,7 @@ void Bot::BotRemoveEquipItem(uint16 slot_id) } } -void Bot::BotTradeAddItem(const EQ::ItemInstance* inst, uint16 slot_id, std::string* error_message, bool save_to_database) +void Bot::BotTradeAddItem(const EQ::ItemInstance* inst, uint16 slot_id, bool save_to_database) { if (!inst) { return; @@ -3740,7 +3650,6 @@ void Bot::BotTradeAddItem(const EQ::ItemInstance* inst, uint16 slot_id, std::str if (save_to_database) { if (!database.botdb.SaveItemBySlot(this, slot_id, inst)) { - *error_message = BotDatabase::fail::SaveItemBySlot(); return; } @@ -3848,21 +3757,7 @@ void Bot::RemoveBotItem(uint32 item_id) { if (inst->GetID() == item_id) { - std::string error_message; - RemoveBotItemBySlot(slot_id, &error_message); - if (!error_message.empty()) { - if (GetOwner()) { - GetOwner()->CastToClient()->Message( - Chat::White, - fmt::format( - "Database Error: {}", - error_message - ).c_str() - ); - } - return; - } - + RemoveBotItemBySlot(slot_id); BotRemoveEquipItem(slot_id); CalcBotStats(GetOwner()->CastToClient()->GetBotOption(Client::booStatsUpdate)); return; @@ -5389,18 +5284,15 @@ bool Bot::IsBotAttackAllowed(Mob* attacker, Mob* target, bool& hasRuleDefined) { return Result; } -void Bot::EquipBot(std::string* error_message) { - GetBotItems(m_inv, error_message); +void Bot::EquipBot() { + GetBotItems(m_inv); const EQ::ItemInstance* inst = nullptr; const EQ::ItemData* item = nullptr; for (int slot_id = EQ::invslot::EQUIPMENT_BEGIN; slot_id <= EQ::invslot::EQUIPMENT_END; ++slot_id) { inst = GetBotItem(slot_id); if (inst) { item = inst->GetItem(); - BotTradeAddItem(inst, slot_id, error_message, false); - if (!error_message->empty()) { - return; - } + BotTradeAddItem(inst, slot_id, false); } } UpdateEquipmentLight(); @@ -8131,8 +8023,6 @@ bool Bot::DyeArmor(int16 slot_id, uint32 rgb, bool all_flag, bool save_flag) save_slot = -2; if (!database.botdb.SaveEquipmentColor(GetBotID(), save_slot, rgb)) { - if (GetBotOwner() && GetBotOwner()->IsClient()) - GetBotOwner()->CastToClient()->Message(Chat::White, "%s", BotDatabase::fail::SaveEquipmentColor()); return false; } } diff --git a/zone/bot.h b/zone/bot.h index b4a3cdc72..473eef291 100644 --- a/zone/bot.h +++ b/zone/bot.h @@ -386,8 +386,8 @@ public: bool CheckDataBucket(std::string bucket_name, const std::string& bucket_value, uint8 bucket_comparison); // Bot Equipment & Inventory Class Methods - void BotTradeAddItem(const EQ::ItemInstance* inst, uint16 slot_id, std::string* error_message, bool save_to_database = true); - void EquipBot(std::string* error_message); + void BotTradeAddItem(const EQ::ItemInstance* inst, uint16 slot_id, bool save_to_database = true); + void EquipBot(); bool CheckLoreConflict(const EQ::ItemData* item); void UpdateEquipmentLight() override { @@ -704,7 +704,8 @@ public: uint32 attack ); void BotRemoveEquipItem(uint16 slot_id); - void RemoveBotItemBySlot(uint16 slot_id, std::string* error_message); + void RemoveBotItemBySlot(uint16 slot_id +); void AddBotItem( uint16 slot_id, uint32 item_id, @@ -938,7 +939,7 @@ private: void SetReturningFlag(bool flag = true) { m_returning_flag = flag; } // Private "Inventory" Methods - void GetBotItems(EQ::InventoryProfile &inv, std::string* error_message); + void GetBotItems(EQ::InventoryProfile &inv); void BotAddEquipItem(uint16 slot_id, uint32 item_id); // Private "Pet" Methods diff --git a/zone/bot_command.cpp b/zone/bot_command.cpp index 23cd81f13..95dc420ee 100644 --- a/zone/bot_command.cpp +++ b/zone/bot_command.cpp @@ -5843,7 +5843,7 @@ void bot_subcommand_bot_clone(Client *c, const Seperator *sep) } uint32 clone_id = 0; - if (!database.botdb.CreateCloneBot(c->CharacterID(), my_bot->GetBotID(), bot_name, clone_id) || !clone_id) { + if (!database.botdb.CreateCloneBot(my_bot->GetBotID(), bot_name, clone_id) || !clone_id) { c->Message( Chat::White, fmt::format( @@ -5875,7 +5875,7 @@ void bot_subcommand_bot_clone(Client *c, const Seperator *sep) ); } - if (!database.botdb.CreateCloneBotInventory(c->CharacterID(), my_bot->GetBotID(), clone_id)) { + if (!database.botdb.CreateCloneBotInventory(my_bot->GetBotID(), clone_id)) { c->Message( Chat::White, fmt::format( @@ -6361,25 +6361,9 @@ void bot_subcommand_bot_dye_armor(Client *c, const Seperator *sep) if (ab_type == ActionableBots::ABT_All) { if (dye_all) { - if (!database.botdb.SaveAllArmorColors(c->CharacterID(), rgb_value)) { - c->Message( - Chat::White, - fmt::format( - "{}", - BotDatabase::fail::SaveAllArmorColors() - ).c_str() - ); - } + database.botdb.SaveAllArmorColors(c->CharacterID(), rgb_value); } else { - if (!database.botdb.SaveAllArmorColorBySlot(c->CharacterID(), slot_id, rgb_value)) { - c->Message( - Chat::White, - fmt::format( - "{}", - BotDatabase::fail::SaveAllArmorColorBySlot() - ).c_str() - ); - } + database.botdb.SaveAllArmorColorBySlot(c->CharacterID(), slot_id, rgb_value); } } } @@ -6527,8 +6511,7 @@ void bot_subcommand_bot_follow_distance(Client *c, const Seperator *sep) continue; bot_iter->SetFollowDistance(bfd); - if (ab_type != ActionableBots::ABT_All && !database.botdb.SaveFollowDistance(c->CharacterID(), bot_iter->GetBotID(), bfd)) { - c->Message(Chat::White, "%s for '%s'", BotDatabase::fail::SaveFollowDistance(), bot_iter->GetCleanName()); + if (ab_type != ActionableBots::ABT_All && !database.botdb.SaveFollowDistance(bot_iter->GetBotID(), bfd)) { return; } @@ -6537,7 +6520,6 @@ void bot_subcommand_bot_follow_distance(Client *c, const Seperator *sep) if (ab_type == ActionableBots::ABT_All) { if (!database.botdb.SaveAllFollowDistances(c->CharacterID(), bfd)) { - c->Message(Chat::White, "%s", BotDatabase::fail::SaveAllFollowDistances()); return; } @@ -6706,7 +6688,6 @@ void bot_subcommand_bot_inspect_message(Client *c, const Seperator *sep) memcpy(bot_message_struct, client_message_struct, sizeof(InspectMessage_Struct)); if (ab_type != ActionableBots::ABT_All && !database.botdb.SaveInspectMessage(bot_iter->GetBotID(), *bot_message_struct)) { - c->Message(Chat::White, "%s for '%s'", BotDatabase::fail::SaveInspectMessage(), bot_iter->GetCleanName()); return; } @@ -6720,7 +6701,6 @@ void bot_subcommand_bot_inspect_message(Client *c, const Seperator *sep) memcpy(&bot_message_struct, client_message_struct, sizeof(InspectMessage_Struct)); if (!database.botdb.SaveAllInspectMessages(c->CharacterID(), bot_message_struct)) { - c->Message(Chat::White, "%s", BotDatabase::fail::SaveAllInspectMessages()); return; } @@ -6800,7 +6780,6 @@ void bot_subcommand_bot_list(Client *c, const Seperator *sep) std::list bots_list; if (!database.botdb.LoadBotsList(c->CharacterID(), bots_list, Account)) { - c->Message(Chat::White, "%s", BotDatabase::fail::LoadBotsList()); return; } @@ -6814,18 +6793,18 @@ void bot_subcommand_bot_list(Client *c, const Seperator *sep) auto bot_number = 1; for (auto bots_iter : bots_list) { if (filter_mask) { - if ((filter_mask & MaskClass) && filter_value[FilterClass] != bots_iter.Class) { + if ((filter_mask & MaskClass) && filter_value[FilterClass] != bots_iter.class_) { continue; } - if ((filter_mask & MaskRace) && filter_value[FilterRace] != bots_iter.Race) { + if ((filter_mask & MaskRace) && filter_value[FilterRace] != bots_iter.race) { continue; } if (filter_mask & MaskName) { std::string name_criteria = sep->arg[name_criteria_arg]; std::transform(name_criteria.begin(), name_criteria.end(), name_criteria.begin(), ::tolower); - std::string name_check = bots_iter.Name; + std::string name_check = bots_iter.bot_name; std::transform(name_check.begin(), name_check.end(), name_check.begin(), ::tolower); if (name_check.find(name_criteria) == std::string::npos) { continue; @@ -6833,7 +6812,7 @@ void bot_subcommand_bot_list(Client *c, const Seperator *sep) } } - auto* bot = entity_list.GetBotByBotName(bots_iter.Name); + auto* bot = entity_list.GetBotByBotName(bots_iter.bot_name); c->Message( Chat::White, @@ -6841,22 +6820,22 @@ void bot_subcommand_bot_list(Client *c, const Seperator *sep) "Bot {} | {} is a Level {} {} {} {} owned by {}.", bot_number, ( - (c->CharacterID() == bots_iter.Owner_ID && !bot) ? + (c->CharacterID() == bots_iter.owner_id && !bot) ? Saylink::Silent( - fmt::format("^spawn {}", bots_iter.Name), - bots_iter.Name + fmt::format("^spawn {}", bots_iter.bot_name), + bots_iter.bot_name ) : - bots_iter.Name + bots_iter.bot_name ), - bots_iter.Level, - GetGenderName(bots_iter.Gender), - GetRaceIDName(bots_iter.Race), - GetClassIDName(bots_iter.Class), - bots_iter.Owner + bots_iter.level, + GetGenderName(bots_iter.gender), + GetRaceIDName(bots_iter.race), + GetClassIDName(bots_iter.class_), + bots_iter.owner_name ).c_str() ); - if (c->CharacterID() == bots_iter.Owner_ID) { + if (c->CharacterID() == bots_iter.owner_id) { bots_owned++; } @@ -6975,10 +6954,7 @@ void bot_subcommand_bot_surname(Client *c, const Seperator *sep) std::replace(bot_surname.begin(), bot_surname.end(), '_', ' '); my_bot->SetSurname(bot_surname); - if (!database.botdb.SaveBot(my_bot)) { - c->Message(Chat::White, BotDatabase::fail::SaveBot()); - } - else { + if (database.botdb.SaveBot(my_bot)) { c->Message(Chat::White, "Bot Surname Saved."); } } @@ -7003,10 +6979,7 @@ void bot_subcommand_bot_title(Client *c, const Seperator *sep) std::replace(bot_title.begin(), bot_title.end(), '_', ' '); my_bot->SetTitle(bot_title); - if (!database.botdb.SaveBot(my_bot)) { - c->Message(Chat::White, BotDatabase::fail::SaveBot()); - } - else { + if (database.botdb.SaveBot(my_bot)) { c->Message(Chat::White, "Bot Title Saved."); } } @@ -7031,10 +7004,7 @@ void bot_subcommand_bot_suffix(Client *c, const Seperator *sep) std::replace(bot_suffix.begin(), bot_suffix.end(), '_', ' '); my_bot->SetSuffix(bot_suffix); - if (!database.botdb.SaveBot(my_bot)) { - c->Message(Chat::White, BotDatabase::fail::SaveBot()); - } - else { + if (database.botdb.SaveBot(my_bot)) { c->Message(Chat::White, "Bot Suffix Saved."); } } @@ -7149,7 +7119,7 @@ void bot_subcommand_bot_spawn(Client *c, const Seperator *sep) uint32 bot_id = 0; uint8 bot_class = Class::None; - if (!database.botdb.LoadBotID(c->CharacterID(), bot_name, bot_id, bot_class)) { + if (!database.botdb.LoadBotID(bot_name, bot_id, bot_class)) { c->Message( Chat::White, fmt::format( @@ -7387,8 +7357,7 @@ void bot_subcommand_bot_stop_melee_level(Client *c, const Seperator *sep) // [reset] falls through with initialization value my_bot->SetStopMeleeLevel(sml); - if (!database.botdb.SaveStopMeleeLevel(c->CharacterID(), my_bot->GetBotID(), sml)) - c->Message(Chat::White, "%s for '%s'", BotDatabase::fail::SaveStopMeleeLevel(), my_bot->GetCleanName()); + database.botdb.SaveStopMeleeLevel(my_bot->GetBotID(), sml); c->Message(Chat::White, "Successfully set stop melee level for %s to %u", my_bot->GetCleanName(), sml); } @@ -7587,8 +7556,7 @@ void bot_subcommand_bot_toggle_helm(Client *c, const Seperator *sep) bot_iter->SetShowHelm(helm_state); if (ab_type != ActionableBots::ABT_All) { - if (!database.botdb.SaveHelmAppearance(c->CharacterID(), bot_iter->GetBotID(), bot_iter->GetShowHelm())) { - c->Message(Chat::White, "%s for '%s'", bot_iter->GetCleanName()); + if (!database.botdb.SaveHelmAppearance(bot_iter->GetBotID(), bot_iter->GetShowHelm())) { return; } @@ -7608,12 +7576,10 @@ void bot_subcommand_bot_toggle_helm(Client *c, const Seperator *sep) if (ab_type == ActionableBots::ABT_All) { if (toggle_helm) { - if (!database.botdb.ToggleAllHelmAppearances(c->CharacterID())) - c->Message(Chat::White, "%s", BotDatabase::fail::ToggleAllHelmAppearances()); + database.botdb.ToggleAllHelmAppearances(c->CharacterID()); } else { - if (!database.botdb.SaveAllHelmAppearances(c->CharacterID(), helm_state)) - c->Message(Chat::White, "%s", BotDatabase::fail::SaveAllHelmAppearances()); + database.botdb.SaveAllHelmAppearances(c->CharacterID(), helm_state); } c->Message(Chat::White, "%s all of your bot show helm flags", toggle_helm ? "Toggled" : (helm_state ? "Set" : "Cleared")); @@ -8357,8 +8323,7 @@ void bot_subcommand_heal_rotation_create(Client *c, const Seperator *sep) bool member_fail = false; bool target_fail = false; - if (!database.botdb.LoadHealRotation(creator_member, member_list, target_list, load_flag, member_fail, target_fail)) - c->Message(Chat::White, "%s", BotDatabase::fail::LoadHealRotation()); + database.botdb.LoadHealRotation(creator_member, member_list, target_list, load_flag, member_fail, target_fail); if (!load_flag) { c->Message(Chat::White, "Successfully added %s as a current member to a new Heal Rotation", creator_member->GetCleanName()); @@ -8387,9 +8352,6 @@ void bot_subcommand_heal_rotation_create(Client *c, const Seperator *sep) c->Message(Chat::White, "Could not locate member with bot id '%u'", member_iter); } } - else { - c->Message(Chat::White, "%s", BotDatabase::fail::LoadHealRotationMembers()); - } if (!target_fail) { for (auto target_iter : target_list) { @@ -8406,9 +8368,6 @@ void bot_subcommand_heal_rotation_create(Client *c, const Seperator *sep) c->Message(Chat::White, "Failed to add target '%s'", target_mob->GetCleanName()); } } - else { - c->Message(Chat::White, "%s", BotDatabase::fail::LoadHealRotationTargets()); - } c->Message(Chat::White, "Successfully loaded %s's Heal Rotation", creator_member->GetCleanName()); } @@ -8430,11 +8389,7 @@ void bot_subcommand_heal_rotation_delete(Client *c, const Seperator *sep) } if (all_flag) { - if (database.botdb.DeleteAllHealRotations(c->CharacterID())) - c->Message(Chat::White, "Succeeded in deleting all heal rotations"); - else - c->Message(Chat::White, "%s", BotDatabase::fail::DeleteAllHealRotations()); - + database.botdb.DeleteAllHealRotations(c->CharacterID()); return; } @@ -8454,7 +8409,6 @@ void bot_subcommand_heal_rotation_delete(Client *c, const Seperator *sep) } if (!database.botdb.DeleteHealRotation(current_member->GetBotID())) { - c->Message(Chat::White, "%s", BotDatabase::fail::DeleteHealRotation()); return; } @@ -8741,7 +8695,6 @@ void bot_subcommand_heal_rotation_save(Client *c, const Seperator *sep) bool member_fail = false; bool target_fail = false; if (!database.botdb.SaveHealRotation(current_member, member_fail, target_fail)) { - c->Message(Chat::White, "%s", BotDatabase::fail::SaveHealRotation()); return; } if (member_fail) @@ -8997,15 +8950,7 @@ void bot_subcommand_inventory_list(Client *c, const Seperator *sep) } uint32 database_count = 0; - if (!database.botdb.QueryInventoryCount(my_bot->GetBotID(), database_count)) { - c->Message( - Chat::White, - fmt::format( - "{}", - BotDatabase::fail::QueryInventoryCount() - ).c_str() - ); - } + database.botdb.QueryInventoryCount(my_bot->GetBotID(), database_count); if (inventory_count != database_count) { c->Message( @@ -9114,7 +9059,6 @@ void bot_subcommand_inventory_remove(Client *c, const Seperator *sep) return; } - std::string error_message; if (itm) { EQ::SayLinkEngine linker; linker.SetLinkType(EQ::saylink::SayLinkItemInst); @@ -9128,18 +9072,7 @@ void bot_subcommand_inventory_remove(Client *c, const Seperator *sep) my_bot->SetBotArcherySetting(false, true); } - my_bot->RemoveBotItemBySlot(slot_id, &error_message); - if (!error_message.empty()) { - c->Message( - Chat::White, - fmt::format( - "Database Error: {}", - error_message - ).c_str() - ); - return; - } - + my_bot->RemoveBotItemBySlot(slot_id); my_bot->BotRemoveEquipItem(slot_id); my_bot->CalcBotStats(c->GetBotOption(Client::booStatsUpdate)); @@ -10671,16 +10604,7 @@ void bot_command_caster_range(Client* c, const Seperator* sep) my_bot->SetBotCasterRange(crange); ++success_count; - if (!database.botdb.SaveBotCasterRange(c->CharacterID(), my_bot->GetBotID(), crange)) { - c->Message( - Chat::White, - fmt::format( - "{} for '{}'", - BotDatabase::fail::SaveBotCasterRange(), - my_bot->GetCleanName() - ).c_str() - ); - } + database.botdb.SaveBotCasterRange(my_bot->GetBotID(), crange); } } if (!current_check) { diff --git a/zone/bot_database.cpp b/zone/bot_database.cpp index f4dd96816..dd23cf1a9 100644 --- a/zone/bot_database.cpp +++ b/zone/bot_database.cpp @@ -22,9 +22,23 @@ #include "../common/strings.h" #include "../common/eqemu_logsys.h" +#include "../common/repositories/bot_buffs_repository.h" +#include "../common/repositories/bot_create_combinations_repository.h" #include "../common/repositories/bot_data_repository.h" +#include "../common/repositories/bot_heal_rotations_repository.h" +#include "../common/repositories/bot_heal_rotation_members_repository.h" +#include "../common/repositories/bot_heal_rotation_targets_repository.h" +#include "../common/repositories/bot_inspect_messages_repository.h" #include "../common/repositories/bot_inventories_repository.h" +#include "../common/repositories/bot_owner_options_repository.h" +#include "../common/repositories/bot_pets_repository.h" +#include "../common/repositories/bot_pet_buffs_repository.h" +#include "../common/repositories/bot_pet_inventories_repository.h" +#include "../common/repositories/bot_spell_casting_chances_repository.h" +#include "../common/repositories/bot_stances_repository.h" #include "../common/repositories/bot_timers_repository.h" +#include "../common/repositories/character_data_repository.h" +#include "../common/repositories/group_id_repository.h" #include "zonedb.h" #include "bot.h" @@ -109,93 +123,94 @@ bool BotDatabase::UpdateOrphanedBotCommandSettings(const std::vector= Bot::SPELL_TYPE_COUNT) - continue; - uint8 class_index = Strings::ToInt(row[1]); - if (class_index < Class::Warrior || class_index > Class::Berserker) - continue; - --class_index; - uint8 stance_index = Strings::ToInt(row[2]); - if (stance_index >= EQ::constants::STANCE_TYPE_COUNT) - continue; + std::vector conditions = { }; - for (uint8 conditional_index = nHSND; conditional_index < cntHSND; ++conditional_index) { - uint8 value = Strings::ToInt(row[3 + conditional_index]); - if (!value) + for (const auto& e : l) { + if ( + e.spell_type_index >= Bot::SPELL_TYPE_COUNT || + !IsPlayerClass(e.class_id) || + e.stance_index >= EQ::constants::STANCE_TYPE_COUNT + ) { + continue; + } + + const uint8 class_index = (e.class_id - 1); + + conditions = { + e.nHSND_value, + e.pH_value, + e.pS_value, + e.pHS_value, + e.pN_value, + e.pHN_value, + e.pSN_value, + e.pHSN_value, + e.pD_value, + e.pHD_value, + e.pSD_value, + e.pHSD_value, + e.pND_value, + e.pHND_value, + e.pSND_value, + e.pHSN_value + }; + + for (uint8 index = 0; index < conditions.size(); index++) { + uint8 value = conditions[index]; + + if (!value) { continue; - if (value > 100) - value = 100; + } - Bot::spell_casting_chances[spell_type_index][class_index][stance_index][conditional_index] = value; + if (value > 100) { + value = 100; + } + + Bot::spell_casting_chances[e.spell_type_index][class_index][e.stance_index][index] = value; } } return true; } - -/* Bot functions */ bool BotDatabase::QueryNameAvailablity(const std::string& bot_name, bool& available_flag) { - if (bot_name.empty() || bot_name.size() > 60 || !database.CheckUsedName(bot_name)) { + if ( + bot_name.empty() || + bot_name.size() > 60 || + !database.CheckUsedName(bot_name) + ) { return false; } - query = fmt::format( - "SELECT b.bot_id FROM bot_data b " - "WHERE b.`name` LIKE '{}' " - "LIMIT 1", - bot_name + const auto& bot_data = BotDataRepository::GetWhere( + database, + fmt::format( + "`name` LIKE '{}' LIMIT 1", + bot_name + ) ); - auto results = database.QueryDatabase(query); - - if (!results.RowCount()) { - query = fmt::format( - "SELECT c.id FROM character_data c " - "WHERE c.`name` LIKE '{}' " - "LIMIT 1", - bot_name - ); - results = database.QueryDatabase(query); - } - - if (!results.Success()) { + if (!bot_data.empty()) { return false; } - if (results.RowCount()) { - return true; + const auto& character_data = CharacterDataRepository::GetWhere( + database, + fmt::format( + "`name` LIKE '{}' LIMIT 1", + bot_name + ) + ); + + if (!character_data.empty()) { + return false; } available_flag = true; @@ -209,127 +224,103 @@ bool BotDatabase::QueryBotCount(const uint32 owner_id, int class_id, uint32& bot return false; } - query = fmt::format( - "SELECT COUNT(`bot_id`) FROM `bot_data` WHERE `owner_id` = {}", - owner_id + bot_count = BotDataRepository::Count( + database, + fmt::format( + "`owner_id` = {}", + owner_id + ) ); - auto results = database.QueryDatabase(query); - if (!results.Success()) { + + if (IsPlayerClass(class_id)) { + bot_class_count = BotDataRepository::Count( + database, + fmt::format( + "`owner_id` = {} AND `class` = {}", + owner_id, + class_id + ) + ); + } + + return true; +} + +bool BotDatabase::LoadBotsList(const uint32 owner_id, std::list& bots_list, bool by_account) +{ + if (!owner_id) { return false; } - if (!results.RowCount()) { - return true; - } + BotsAvailableList ble; - auto row = results.begin(); - bot_count = Strings::ToUnsignedInt(row[0]); + if (by_account) { + const std::string& owner_name = database.GetCharNameByID(owner_id); - if (EQ::ValueWithin(class_id, Class::Warrior, Class::Berserker)) { - query = fmt::format( - "SELECT COUNT(`bot_id`) FROM `bot_data` WHERE `owner_id` = {} AND `class` = {}", - owner_id, - class_id + const auto& l = BotDataRepository::GetWhere( + database, + fmt::format( + SQL( + `owner_id` IN + ( + SELECT `id` FROM `character_data` WHERE `account_id` = + ( + SELECT `account_id` FROM `character_data` WHERE `id` = {} + ) + ) + ), + owner_id + ) ); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - return false; - } - if (!results.RowCount()) { + if (l.empty()) { return true; } - auto row = results.begin(); - bot_class_count = Strings::ToUnsignedInt(row[0]); + for (const auto& e : l) { + ble.bot_id = e.bot_id; + ble.class_ = e.class_; + ble.level = e.level; + ble.race = e.race; + ble.gender = e.gender; + ble.owner_id = e.owner_id; + + strn0cpy(ble.bot_name, e.name.c_str(), sizeof(ble.bot_name)); + strn0cpy(ble.owner_name, owner_name.c_str(), sizeof(ble.owner_name)); + + bots_list.emplace_back(ble); + } + } else { + const auto& l = BotDataRepository::GetWhere( + database, + fmt::format( + "`owner_id` = {}", + owner_id + ) + ); + + if (l.empty()) { + return true; + } + + for (const auto& e : l) { + ble.bot_id = e.bot_id; + ble.class_ = e.class_; + ble.level = e.level; + ble.race = e.race; + ble.gender = e.gender; + ble.owner_id = e.owner_id; + + strn0cpy(ble.bot_name, e.name.c_str(), sizeof(ble.bot_name)); + strn0cpy(ble.owner_name, "You", sizeof(ble.owner_name)); + + bots_list.emplace_back(ble); + } } return true; } -bool BotDatabase::LoadBotsList(const uint32 owner_id, std::list& bots_list, bool ByAccount) -{ - if (!owner_id) - return false; - - if (ByAccount == true) - query = StringFormat("SELECT bot_id, bd.`name`, bd.class, bd.`level`, bd.race, bd.gender, cd.`name` as owner, bd.owner_id, cd.account_id, cd.id" - " FROM bot_data as bd inner join character_data as cd on bd.owner_id = cd.id" - " WHERE cd.account_id = (select account_id from bot_data bd inner join character_data as cd on bd.owner_id = cd.id where bd.owner_id = '%u' LIMIT 1)" - " ORDER BY bd.owner_id", owner_id); - else - query = StringFormat("SELECT `bot_id`, `name`, `class`, `level`, `race`, `gender`, 'You' as owner, owner_id FROM `bot_data` WHERE `owner_id` = '%u'", owner_id); - - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - if (!results.RowCount()) - return true; - - for (auto row = results.begin(); row != results.end(); ++row) { - BotsAvailableList bot_entry; - - bot_entry.ID = Strings::ToInt(row[0]); - - memset(&bot_entry.Name, 0, sizeof(bot_entry.Name)); - std::string bot_name = row[1]; - if (bot_name.size() > 63) - bot_name = bot_name.substr(0, 63); - if (!bot_name.empty()) - strcpy(bot_entry.Name, bot_name.c_str()); - memset(&bot_entry.Owner, 0, sizeof(bot_entry.Owner)); - std::string bot_owner = row[6]; - if (bot_owner.size() > 63) - bot_owner = bot_owner.substr(0, 63); - if (!bot_owner.empty()) - strcpy(bot_entry.Owner, bot_owner.c_str()); - bot_entry.Class = Strings::ToInt(row[2]); - bot_entry.Level = Strings::ToInt(row[3]); - bot_entry.Race = Strings::ToInt(row[4]); - bot_entry.Gender = Strings::ToInt(row[5]); - bot_entry.Owner_ID = Strings::ToInt(row[7]); - bots_list.push_back(bot_entry); - } - - return true; -} - -bool BotDatabase::LoadOwnerID(const std::string& bot_name, uint32& owner_id) -{ - if (bot_name.empty()) - return false; - - query = StringFormat("SELECT `owner_id` FROM `bot_data` WHERE `name` = '%s' LIMIT 1", bot_name.c_str()); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - if (!results.RowCount()) - return true; - - auto row = results.begin(); - owner_id = Strings::ToInt(row[0]); - - return true; -} - -bool BotDatabase::LoadOwnerID(const uint32 bot_id, uint32& owner_id) -{ - if (!bot_id) - return false; - - query = StringFormat("SELECT `owner_id` FROM `bot_data` WHERE `bot_id` = '%u' LIMIT 1", bot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - if (!results.RowCount()) - return true; - - auto row = results.begin(); - owner_id = Strings::ToInt(row[0]); - - return true; -} - uint32 BotDatabase::GetOwnerID(const uint32 bot_id) { if (!bot_id) { @@ -337,64 +328,32 @@ uint32 BotDatabase::GetOwnerID(const uint32 bot_id) } const auto& l = BotDataRepository::FindOne(database, bot_id); - if (!l.bot_id) { - return 0; - } - return l.owner_id; + return l.bot_id ? l.owner_id : 0; } -bool BotDatabase::LoadBotID(const uint32 owner_id, const std::string& bot_name, uint32& bot_id) +bool BotDatabase::LoadBotID(const std::string& bot_name, uint32& bot_id, uint8& bot_class_id) { - if (!owner_id || bot_name.empty()) { + if (bot_name.empty()) { return false; } - query = fmt::format( - "SELECT `bot_id` FROM `bot_data` WHERE `owner_id` = {} AND `name` = '{}' LIMIT 1", - owner_id, - bot_name + const auto& l = BotDataRepository::GetWhere( + database, + fmt::format( + "`name` = '{}' LIMIT 1", + Strings::Escape(bot_name) + ) ); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - return false; - } - - if (!results.RowCount()) { + if (l.empty()) { return true; } - auto row = results.begin(); - bot_id = Strings::ToUnsignedInt(row[0]); + auto e = l.front(); - return true; -} - -bool BotDatabase::LoadBotID(const uint32 owner_id, const std::string& bot_name, uint32& bot_id, uint8& bot_class_id) -{ - if (!owner_id || bot_name.empty()) { - return false; - } - - query = fmt::format( - "SELECT `bot_id`, `class` FROM `bot_data` WHERE `owner_id` = {} AND `name` = '{}' LIMIT 1", - owner_id, - bot_name - ); - - auto results = database.QueryDatabase(query); - if (!results.Success()) { - return false; - } - - if (!results.RowCount()) { - return true; - } - - auto row = results.begin(); - bot_id = Strings::ToUnsignedInt(row[0]); - bot_class_id = static_cast(Strings::ToUnsignedInt(row[1])); + bot_id = e.bot_id; + bot_class_id = e.class_; return true; } @@ -405,41 +364,41 @@ bool BotDatabase::LoadBot(const uint32 bot_id, Bot*& loaded_bot) return false; } - const auto& l = BotDataRepository::FindOne(database, bot_id); - if (!l.bot_id) { + const auto& e = BotDataRepository::FindOne(database, bot_id); + if (!e.bot_id) { return false; } auto d = Bot::CreateDefaultNPCTypeStructForBot( - l.name, - l.last_name, - l.level, - l.race, - l.class_, - l.gender + e.name, + e.last_name, + e.level, + e.race, + e.class_, + e.gender ); auto t = Bot::FillNPCTypeStruct( - l.spells_id, - l.name, - l.last_name, - l.level, - l.race, - l.class_, - l.gender, - l.size, - l.face, - l.hair_style, - l.hair_color, - l.eye_color_1, - l.eye_color_2, - l.beard, - l.beard_color, - l.drakkin_heritage, - l.drakkin_tattoo, - l.drakkin_details, - l.hp, - l.mana, + e.spells_id, + e.name, + e.last_name, + e.level, + e.race, + e.class_, + e.gender, + e.size, + e.face, + e.hair_style, + e.hair_color, + e.eye_color_1, + e.eye_color_2, + e.beard, + e.beard_color, + e.drakkin_heritage, + e.drakkin_tattoo, + e.drakkin_details, + e.hp, + e.mana, d->MR, d->CR, d->DR, @@ -461,168 +420,165 @@ bool BotDatabase::LoadBot(const uint32 bot_id, Bot*& loaded_bot) loaded_bot = new Bot( bot_id, - l.owner_id, - l.spells_id, - l.time_spawned, - l.zone_id, + e.owner_id, + e.spells_id, + e.time_spawned, + e.zone_id, t, - l.expansion_bitmask + e.expansion_bitmask ); if (loaded_bot) { - loaded_bot->SetSurname(l.last_name); - loaded_bot->SetTitle(l.title); - loaded_bot->SetSuffix(l.suffix); + loaded_bot->SetSurname(e.last_name); + loaded_bot->SetTitle(e.title); + loaded_bot->SetSuffix(e.suffix); - loaded_bot->SetShowHelm((l.show_helm ? true : false)); + loaded_bot->SetShowHelm(e.show_helm); + + auto bfd = EQ::Clamp(e.follow_distance, static_cast(1), BOT_FOLLOW_DISTANCE_DEFAULT_MAX); - auto bfd = EQ::Clamp(l.follow_distance, static_cast(1), BOT_FOLLOW_DISTANCE_DEFAULT_MAX); loaded_bot->SetFollowDistance(bfd); - loaded_bot->SetStopMeleeLevel(l.stop_melee_level); + loaded_bot->SetStopMeleeLevel(e.stop_melee_level); - loaded_bot->SetBotEnforceSpellSetting((l.enforce_spell_settings ? true : false)); + loaded_bot->SetBotEnforceSpellSetting(e.enforce_spell_settings); - loaded_bot->SetBotArcherySetting((l.archery_setting ? true : false)); + loaded_bot->SetBotArcherySetting(e.archery_setting); - loaded_bot->SetBotCasterRange(l.caster_range); + loaded_bot->SetBotCasterRange(e.caster_range); } return true; } -bool BotDatabase::SaveNewBot(Bot* bot_inst, uint32& bot_id) +bool BotDatabase::SaveNewBot(Bot* b, uint32& bot_id) { - if (!bot_inst) { + if (!b) { return false; } auto e = BotDataRepository::NewEntity(); - e.owner_id = bot_inst->GetBotOwnerCharacterID(); - e.spells_id = bot_inst->GetBotSpellID(); - e.name = bot_inst->GetCleanName(); - e.last_name = bot_inst->GetLastName(); - e.title = bot_inst->GetTitle(); - e.suffix = bot_inst->GetSuffix(); - e.zone_id = bot_inst->GetLastZoneID(); - e.gender = bot_inst->GetGender(); - e.race = bot_inst->GetBaseRace(); - e.class_ = bot_inst->GetClass(); - e.level = bot_inst->GetLevel(); + e.owner_id = b->GetBotOwnerCharacterID(); + e.spells_id = b->GetBotSpellID(); + e.name = b->GetCleanName(); + e.last_name = b->GetLastName(); + e.title = b->GetTitle(); + e.suffix = b->GetSuffix(); + e.zone_id = b->GetLastZoneID(); + e.gender = b->GetGender(); + e.race = b->GetBaseRace(); + e.class_ = b->GetClass(); + e.level = b->GetLevel(); e.creation_day = std::time(nullptr); e.last_spawn = std::time(nullptr); - e.size = bot_inst->GetSize(); - e.face = bot_inst->GetLuclinFace(); - e.hair_color = bot_inst->GetHairColor(); - e.hair_style = bot_inst->GetHairStyle(); - e.beard = bot_inst->GetBeard(); - e.beard_color = bot_inst->GetBeardColor(); - e.eye_color_1 = bot_inst->GetEyeColor1(); - e.eye_color_2 = bot_inst->GetEyeColor2(); - e.drakkin_heritage = bot_inst->GetDrakkinHeritage(); - e.drakkin_tattoo = bot_inst->GetDrakkinTattoo(); - e.drakkin_details = bot_inst->GetDrakkinDetails(); - e.ac = bot_inst->GetBaseAC(); - e.atk = bot_inst->GetBaseATK(); - e.hp = bot_inst->GetHP(); - e.mana = bot_inst->GetMana(); - e.str = bot_inst->GetBaseSTR(); - e.sta = bot_inst->GetBaseSTA(); - e.cha = bot_inst->GetBaseCHA(); - e.dex = bot_inst->GetBaseDEX(); - e.int_ = bot_inst->GetBaseINT(); - e.agi = bot_inst->GetBaseAGI(); - e.wis = bot_inst->GetBaseWIS(); - e.fire = bot_inst->GetBaseFR(); - e.cold = bot_inst->GetBaseCR(); - e.magic = bot_inst->GetBaseMR(); - e.poison = bot_inst->GetBasePR(); - e.disease = bot_inst->GetBaseDR(); - e.corruption = bot_inst->GetBaseCorrup(); - e.show_helm = bot_inst->GetShowHelm() ? 1 : 0; - e.follow_distance = bot_inst->GetFollowDistance(); - e.stop_melee_level = bot_inst->GetStopMeleeLevel(); - e.expansion_bitmask = bot_inst->GetExpansionBitmask(); - e.enforce_spell_settings = bot_inst->GetBotEnforceSpellSetting(); - e.archery_setting = bot_inst->IsBotArcher() ? 1 : 0; - e.caster_range = bot_inst->GetBotCasterRange(); + e.size = b->GetSize(); + e.face = b->GetLuclinFace(); + e.hair_color = b->GetHairColor(); + e.hair_style = b->GetHairStyle(); + e.beard = b->GetBeard(); + e.beard_color = b->GetBeardColor(); + e.eye_color_1 = b->GetEyeColor1(); + e.eye_color_2 = b->GetEyeColor2(); + e.drakkin_heritage = b->GetDrakkinHeritage(); + e.drakkin_tattoo = b->GetDrakkinTattoo(); + e.drakkin_details = b->GetDrakkinDetails(); + e.ac = b->GetBaseAC(); + e.atk = b->GetBaseATK(); + e.hp = b->GetHP(); + e.mana = b->GetMana(); + e.str = b->GetBaseSTR(); + e.sta = b->GetBaseSTA(); + e.cha = b->GetBaseCHA(); + e.dex = b->GetBaseDEX(); + e.int_ = b->GetBaseINT(); + e.agi = b->GetBaseAGI(); + e.wis = b->GetBaseWIS(); + e.fire = b->GetBaseFR(); + e.cold = b->GetBaseCR(); + e.magic = b->GetBaseMR(); + e.poison = b->GetBasePR(); + e.disease = b->GetBaseDR(); + e.corruption = b->GetBaseCorrup(); + e.show_helm = b->GetShowHelm() ? 1 : 0; + e.follow_distance = b->GetFollowDistance(); + e.stop_melee_level = b->GetStopMeleeLevel(); + e.expansion_bitmask = b->GetExpansionBitmask(); + e.enforce_spell_settings = b->GetBotEnforceSpellSetting(); + e.archery_setting = b->IsBotArcher() ? 1 : 0; + e.caster_range = b->GetBotCasterRange(); - auto b = BotDataRepository::InsertOne(database, e); - if (!b.bot_id) { + e = BotDataRepository::InsertOne(database, e); + + if (!e.bot_id) { return false; } - bot_id = b.bot_id; + bot_id = e.bot_id; return true; } -bool BotDatabase::SaveBot(Bot* bot_inst) +bool BotDatabase::SaveBot(Bot* b) { - if (!bot_inst) { + if (!b) { return false; } - auto l = BotDataRepository::FindOne(database, bot_inst->GetBotID()); - if (!l.bot_id) { + auto e = BotDataRepository::FindOne(database, b->GetBotID()); + if (!e.bot_id) { return false; } - l.owner_id = bot_inst->GetBotOwnerCharacterID(); - l.spells_id = bot_inst->GetBotSpellID(); - l.name = bot_inst->GetCleanName(); - l.last_name = bot_inst->GetLastName(); - l.title = bot_inst->GetTitle(); - l.suffix = bot_inst->GetSuffix(); - l.zone_id = bot_inst->GetLastZoneID(); - l.gender = bot_inst->GetBaseGender(); - l.race = bot_inst->GetBaseRace(); - l.class_ = bot_inst->GetClass(); - l.level = bot_inst->GetLevel(); - l.last_spawn = std::time(nullptr); - l.time_spawned = bot_inst->GetTotalPlayTime(); - l.size = bot_inst->GetSize(); - l.face = bot_inst->GetLuclinFace(); - l.hair_color = bot_inst->GetHairColor(); - l.hair_style = bot_inst->GetHairStyle(); - l.beard = bot_inst->GetBeard(); - l.beard_color = bot_inst->GetBeardColor(); - l.eye_color_1 = bot_inst->GetEyeColor1(); - l.eye_color_2 = bot_inst->GetEyeColor2(); - l.drakkin_heritage = bot_inst->GetDrakkinHeritage(); - l.drakkin_tattoo = bot_inst->GetDrakkinTattoo(); - l.drakkin_details = bot_inst->GetDrakkinDetails(); - l.ac = bot_inst->GetBaseAC(); - l.atk = bot_inst->GetBaseATK(); - l.hp = bot_inst->GetHP(); - l.mana = bot_inst->GetMana(); - l.str = bot_inst->GetBaseSTR(); - l.sta = bot_inst->GetBaseSTA(); - l.cha = bot_inst->GetBaseCHA(); - l.dex = bot_inst->GetBaseDEX(); - l.int_ = bot_inst->GetBaseINT(); - l.agi = bot_inst->GetBaseAGI(); - l.wis = bot_inst->GetBaseWIS(); - l.fire = bot_inst->GetBaseFR(); - l.cold = bot_inst->GetBaseCR(); - l.magic = bot_inst->GetBaseMR(); - l.poison = bot_inst->GetBasePR(); - l.disease = bot_inst->GetBaseDR(); - l.corruption = bot_inst->GetBaseCorrup(); - l.show_helm = bot_inst->GetShowHelm() ? 1 : 0; - l.follow_distance = bot_inst->GetFollowDistance(); - l.stop_melee_level = bot_inst->GetStopMeleeLevel(); - l.expansion_bitmask = bot_inst->GetExpansionBitmask(); - l.enforce_spell_settings = bot_inst->GetBotEnforceSpellSetting(); - l.archery_setting = bot_inst->IsBotArcher() ? 1 : 0; + e.owner_id = b->GetBotOwnerCharacterID(); + e.spells_id = b->GetBotSpellID(); + e.name = b->GetCleanName(); + e.last_name = b->GetLastName(); + e.title = b->GetTitle(); + e.suffix = b->GetSuffix(); + e.zone_id = b->GetLastZoneID(); + e.gender = b->GetBaseGender(); + e.race = b->GetBaseRace(); + e.class_ = b->GetClass(); + e.level = b->GetLevel(); + e.last_spawn = std::time(nullptr); + e.time_spawned = b->GetTotalPlayTime(); + e.size = b->GetSize(); + e.face = b->GetLuclinFace(); + e.hair_color = b->GetHairColor(); + e.hair_style = b->GetHairStyle(); + e.beard = b->GetBeard(); + e.beard_color = b->GetBeardColor(); + e.eye_color_1 = b->GetEyeColor1(); + e.eye_color_2 = b->GetEyeColor2(); + e.drakkin_heritage = b->GetDrakkinHeritage(); + e.drakkin_tattoo = b->GetDrakkinTattoo(); + e.drakkin_details = b->GetDrakkinDetails(); + e.ac = b->GetBaseAC(); + e.atk = b->GetBaseATK(); + e.hp = b->GetHP(); + e.mana = b->GetMana(); + e.str = b->GetBaseSTR(); + e.sta = b->GetBaseSTA(); + e.cha = b->GetBaseCHA(); + e.dex = b->GetBaseDEX(); + e.int_ = b->GetBaseINT(); + e.agi = b->GetBaseAGI(); + e.wis = b->GetBaseWIS(); + e.fire = b->GetBaseFR(); + e.cold = b->GetBaseCR(); + e.magic = b->GetBaseMR(); + e.poison = b->GetBasePR(); + e.disease = b->GetBaseDR(); + e.corruption = b->GetBaseCorrup(); + e.show_helm = b->GetShowHelm() ? 1 : 0; + e.follow_distance = b->GetFollowDistance(); + e.stop_melee_level = b->GetStopMeleeLevel(); + e.expansion_bitmask = b->GetExpansionBitmask(); + e.enforce_spell_settings = b->GetBotEnforceSpellSetting(); + e.archery_setting = b->IsBotArcher() ? 1 : 0; - const auto updated = BotDataRepository::UpdateOne(database, l); - if (!updated) { - return false; - } - - return true; + return BotDataRepository::UpdateOne(database, e); } bool BotDatabase::DeleteBot(const uint32 bot_id) @@ -631,180 +587,133 @@ bool BotDatabase::DeleteBot(const uint32 bot_id) return false; } - const auto deleted = BotDataRepository::DeleteOne(database, bot_id); - if (!deleted) { - return false; - } + BotDataRepository::DeleteOne(database, bot_id); return true; } -bool BotDatabase::LoadBuffs(Bot* bot_inst) +bool BotDatabase::LoadBuffs(Bot* b) { - if (!bot_inst) { + if (!b) { return false; } - query = fmt::format( - "SELECT" - " `spell_id`," - " `caster_level`," - " `duration_formula`," - " `tics_remaining`," - " `poison_counters`," - " `disease_counters`," - " `curse_counters`," - " `corruption_counters`," - " `numhits`," - " `melee_rune`," - " `magic_rune`," - " `dot_rune`," - " `persistent`," - " `caston_x`," - " `caston_y`," - " `caston_z`," - " `extra_di_chance`," - " `instrument_mod`" - " FROM `bot_buffs`" - " WHERE `bot_id` = {}", - bot_inst->GetBotID() + const auto& l = BotBuffsRepository::GetWhere( + database, + fmt::format( + "`bot_id` = {}", + b->GetBotID() + ) ); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - return false; - } - - if (!results.RowCount()) { + if (l.empty()) { return true; } - Buffs_Struct* bot_buffs = bot_inst->GetBuffs(); + auto buffs = b->GetBuffs(); - if (!bot_buffs) { + if (!buffs) { return false; } - uint32 max_slots = bot_inst->GetMaxBuffSlots(); + uint32 max_slots = b->GetMaxBuffSlots(); for (int index = 0; index < max_slots; index++) { - bot_buffs[index].spellid = SPELL_UNKNOWN; + buffs[index].spellid = SPELL_UNKNOWN; } - int buff_count = 0; - for (auto row = results.begin(); row != results.end() && buff_count < BUFF_COUNT; ++row) { - bot_buffs[buff_count].spellid = Strings::ToUnsignedInt(row[0]); - bot_buffs[buff_count].casterlevel = Strings::ToUnsignedInt(row[1]); - //row[2] (duration_formula) can probably be removed - bot_buffs[buff_count].ticsremaining = Strings::ToInt(row[3]); + uint32 buff_count = 0; - bot_buffs[buff_count].counters = 0; - if (CalculatePoisonCounters(bot_buffs[buff_count].spellid) > 0) { - bot_buffs[buff_count].counters = Strings::ToUnsignedInt(row[4]); - } else if (CalculateDiseaseCounters(bot_buffs[buff_count].spellid) > 0) { - bot_buffs[buff_count].counters = Strings::ToUnsignedInt(row[5]); - } else if (CalculateCurseCounters(bot_buffs[buff_count].spellid) > 0) { - bot_buffs[buff_count].counters = Strings::ToUnsignedInt(row[6]); - } else if (CalculateCorruptionCounters(bot_buffs[buff_count].spellid) > 0) { - bot_buffs[buff_count].counters = Strings::ToUnsignedInt(row[7]); + for (const auto& e : l) { + if (buff_count >= BUFF_COUNT) { + continue; } - bot_buffs[buff_count].hit_number = Strings::ToUnsignedInt(row[8]); - bot_buffs[buff_count].melee_rune = Strings::ToUnsignedInt(row[9]); - bot_buffs[buff_count].magic_rune = Strings::ToUnsignedInt(row[10]); - bot_buffs[buff_count].dot_rune = Strings::ToUnsignedInt(row[11]); - bot_buffs[buff_count].persistant_buff = (Strings::ToBool(row[12])) != 0; - bot_buffs[buff_count].caston_x = Strings::ToInt(row[13]); - bot_buffs[buff_count].caston_y = Strings::ToInt(row[14]); - bot_buffs[buff_count].caston_z = Strings::ToInt(row[15]); - bot_buffs[buff_count].ExtraDIChance = Strings::ToInt(row[16]); - bot_buffs[buff_count].instrument_mod = Strings::ToUnsignedInt(row[17]); - bot_buffs[buff_count].casterid = 0; + buffs[buff_count].spellid = e.spell_id; + buffs[buff_count].casterlevel = e.caster_level; + buffs[buff_count].ticsremaining = e.tics_remaining; + buffs[buff_count].counters = 0; + + if (CalculatePoisonCounters(buffs[buff_count].spellid) > 0) { + buffs[buff_count].counters = e.poison_counters; + } else if (CalculateDiseaseCounters(buffs[buff_count].spellid) > 0) { + buffs[buff_count].counters = e.disease_counters; + } else if (CalculateCurseCounters(buffs[buff_count].spellid) > 0) { + buffs[buff_count].counters = e.curse_counters; + } else if (CalculateCorruptionCounters(buffs[buff_count].spellid) > 0) { + buffs[buff_count].counters = e.corruption_counters; + } + + buffs[buff_count].hit_number = e.numhits; + buffs[buff_count].melee_rune = e.melee_rune; + buffs[buff_count].magic_rune = e.magic_rune; + buffs[buff_count].dot_rune = e.dot_rune; + buffs[buff_count].persistant_buff = e.persistent; + buffs[buff_count].caston_x = e.caston_x; + buffs[buff_count].caston_y = e.caston_y; + buffs[buff_count].caston_z = e.caston_z; + buffs[buff_count].ExtraDIChance = e.extra_di_chance; + buffs[buff_count].instrument_mod = e.instrument_mod; + buffs[buff_count].casterid = 0; + ++buff_count; } return true; } -bool BotDatabase::SaveBuffs(Bot* bot_inst) +bool BotDatabase::SaveBuffs(Bot* b) { - if (!bot_inst) + if (!b) { return false; + } - if (!DeleteBuffs(bot_inst->GetBotID())) + if (!DeleteBuffs(b->GetBotID())) { return false; + } - Buffs_Struct* bot_buffs = bot_inst->GetBuffs(); - if (!bot_buffs) + auto buffs = b->GetBuffs(); + + if (!buffs) { return false; + } + + auto e = BotBuffsRepository::NewEntity(); + + e.bot_id = b->GetBotID(); + + std::vector v = { }; for (int buff_index = 0; buff_index < BUFF_COUNT; ++buff_index) { - if (!IsValidSpell(bot_buffs[buff_index].spellid)) { + if (!IsValidSpell(buffs[buff_index].spellid)) { continue; } - query = StringFormat( - "INSERT INTO `bot_buffs` (" - "`bot_id`," - " `spell_id`," - " `caster_level`," - " `duration_formula`," - " `tics_remaining`," - " `poison_counters`," - " `disease_counters`," - " `curse_counters`," - " `corruption_counters`," - " `numhits`," - " `melee_rune`," - " `magic_rune`," - " `dot_rune`," - " `persistent`," - " `caston_x`," - " `caston_y`," - " `caston_z`," - " `extra_di_chance`" - ")" - " VALUES (" - "'%u'," /* bot_id */ - " '%u'," /* spell_id */ - " '%u'," /* caster_level */ - " '%u'," /* duration_formula */ - " '%u'," /* tics_remaining */ - " '%u'," /* poison_counters */ - " '%u'," /* disease_counters */ - " '%u'," /* curse_counters */ - " '%u'," /* corruption_counters */ - " '%u'," /* numhits */ - " '%u'," /* melee_rune */ - " '%u'," /* magic_rune */ - " '%u'," /* dot_rune */ - " '%u'," /* persistent */ - " '%i'," /* caston_x */ - " '%i'," /* caston_y */ - " '%i'," /* caston_z */ - " '%i'" /* extra_di_chance */ - ")", - bot_inst->GetBotID(), - bot_buffs[buff_index].spellid, - bot_buffs[buff_index].casterlevel, - spells[bot_buffs[buff_index].spellid].buff_duration_formula, - bot_buffs[buff_index].ticsremaining, - ((CalculatePoisonCounters(bot_buffs[buff_index].spellid) > 0) ? (bot_buffs[buff_index].counters) : (0)), - ((CalculateDiseaseCounters(bot_buffs[buff_index].spellid) > 0) ? (bot_buffs[buff_index].counters) : (0)), - ((CalculateCurseCounters(bot_buffs[buff_index].spellid) > 0) ? (bot_buffs[buff_index].counters) : (0)), - ((CalculateCorruptionCounters(bot_buffs[buff_index].spellid) > 0) ? (bot_buffs[buff_index].counters) : (0)), - bot_buffs[buff_index].hit_number, - bot_buffs[buff_index].melee_rune, - bot_buffs[buff_index].magic_rune, - bot_buffs[buff_index].dot_rune, - ((bot_buffs[buff_index].persistant_buff) ? (1) : (0)), - bot_buffs[buff_index].caston_x, - bot_buffs[buff_index].caston_y, - bot_buffs[buff_index].caston_z, - bot_buffs[buff_index].ExtraDIChance - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - DeleteBuffs(bot_inst->GetBotID()); + e.spell_id = buffs[buff_index].spellid; + e.caster_level = buffs[buff_index].casterlevel; + e.duration_formula = spells[buffs[buff_index].spellid].buff_duration_formula; + e.tics_remaining = buffs[buff_index].ticsremaining; + e.poison_counters = CalculatePoisonCounters(buffs[buff_index].spellid) > 0 ? buffs[buff_index].counters : 0; + e.disease_counters = CalculateDiseaseCounters(buffs[buff_index].spellid) > 0 ? buffs[buff_index].counters : 0; + e.curse_counters = CalculateCurseCounters(buffs[buff_index].spellid) > 0 ? buffs[buff_index].counters : 0; + e.corruption_counters = CalculateCorruptionCounters(buffs[buff_index].spellid) > 0 ? buffs[buff_index].counters : 0; + e.numhits = buffs[buff_index].hit_number; + e.melee_rune = buffs[buff_index].melee_rune; + e.magic_rune = buffs[buff_index].magic_rune; + e.dot_rune = buffs[buff_index].dot_rune; + e.persistent = buffs[buff_index].persistant_buff ? 1 : 0; + e.caston_x = buffs[buff_index].caston_x; + e.caston_y = buffs[buff_index].caston_y; + e.caston_z = buffs[buff_index].caston_z; + e.extra_di_chance = buffs[buff_index].ExtraDIChance; + + v.emplace_back(e); + } + + if (!v.empty()) { + const int inserted = BotBuffsRepository::InsertMany(database, v); + + if (!inserted) { + DeleteBuffs(b->GetBotID()); return false; } } @@ -814,51 +723,70 @@ bool BotDatabase::SaveBuffs(Bot* bot_inst) bool BotDatabase::DeleteBuffs(const uint32 bot_id) { - if (!bot_id) + if (!bot_id) { return false; + } - query = StringFormat("DELETE FROM `bot_buffs` WHERE `bot_id` = '%u'", bot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; + BotBuffsRepository::DeleteWhere( + database, + fmt::format( + "`bot_id` = {}", + bot_id + ) + ); return true; } bool BotDatabase::LoadStance(const uint32 bot_id, int& bot_stance) { - if (!bot_id) + if (!bot_id) { return false; + } - query = StringFormat("SELECT `stance_id` FROM `bot_stances` WHERE `bot_id` = '%u' LIMIT 1", bot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - if (!results.RowCount()) + const auto& l = BotStancesRepository::GetWhere( + database, + fmt::format( + "`bot_id` = {} LIMIT 1", + bot_id + ) + ); + + if (l.empty()) { return true; + } - auto row = results.begin(); - bot_stance = Strings::ToInt(row[0]); + auto e = l.front(); + + bot_stance = e.stance_id; return true; } -bool BotDatabase::LoadStance(Bot* bot_inst, bool& stance_flag) +bool BotDatabase::LoadStance(Bot* b, bool& stance_flag) { - if (!bot_inst) + if (!b) { return false; + } - bot_inst->SetDefaultBotStance(); + b->SetDefaultBotStance(); - query = StringFormat("SELECT `stance_id` FROM `bot_stances` WHERE `bot_id` = '%u' LIMIT 1", bot_inst->GetBotID()); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - if (!results.RowCount()) + const auto& l = BotStancesRepository::GetWhere( + database, + fmt::format( + "`bot_id` = {} LIMIT 1", + b->GetBotID() + ) + ); + + if (l.empty()) { return true; + } + + auto e = l.front(); + + b->SetBotStance(static_cast(e.stance_id)); - auto row = results.begin(); - bot_inst->SetBotStance((EQ::constants::StanceType)Strings::ToInt(row[0])); stance_flag = true; return true; @@ -866,149 +794,140 @@ bool BotDatabase::LoadStance(Bot* bot_inst, bool& stance_flag) bool BotDatabase::SaveStance(const uint32 bot_id, const int bot_stance) { - if (!bot_id) - return false; - - if (!DeleteStance(bot_id)) - return false; - - query = StringFormat("INSERT INTO `bot_stances` (`bot_id`, `stance_id`) VALUES ('%u', '%u')", bot_id, bot_stance); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - DeleteStance(bot_id); + if (!bot_id) { return false; } - return true; + return BotStancesRepository::ReplaceOne( + database, + BotStancesRepository::BotStances{ + .bot_id = bot_id, + .stance_id = static_cast(bot_stance) + } + ); } -bool BotDatabase::SaveStance(Bot* bot_inst) +bool BotDatabase::SaveStance(Bot* b) { - if (!bot_inst) - return false; - - if (!DeleteStance(bot_inst->GetBotID())) - return false; - - query = StringFormat("INSERT INTO `bot_stances` (`bot_id`, `stance_id`) VALUES ('%u', '%u')", bot_inst->GetBotID(), bot_inst->GetBotStance()); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - DeleteStance(bot_inst->GetBotID()); + if (!b) { return false; } - return true; + return BotStancesRepository::ReplaceOne( + database, + BotStancesRepository::BotStances{ + .bot_id = b->GetBotID(), + .stance_id = static_cast(b->GetBotStance()) + } + ); } bool BotDatabase::DeleteStance(const uint32 bot_id) { - if (!bot_id) + if (!bot_id) { return false; + } - query = StringFormat("DELETE FROM `bot_stances` WHERE `bot_id` = '%u'", bot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; + BotStancesRepository::DeleteOne(database, bot_id); return true; } -bool BotDatabase::LoadTimers(Bot* bot_inst) +bool BotDatabase::LoadTimers(Bot* b) { - if (!bot_inst) + if (!b) { return false; + } - auto timers = BotTimersRepository::GetWhere( + const auto& l = BotTimersRepository::GetWhere( database, - fmt::format("bot_id = {}", bot_inst->GetBotID()) + fmt::format( + "`bot_id` = {}", + b->GetBotID() + ) ); - std::vector bot_timers; + std::vector v; - BotTimer_Struct t{}; - t.timer_id = 0; - t.timer_value = 0; - t.recast_time = 0; - t.is_spell = false; - t.is_disc = false; - t.spell_id = 0; - t.is_item = false; - t.item_id = 0; + BotTimer_Struct t{ }; - for (auto& timer : timers) { + for (const auto& e : l) { if (t.timer_value < (Timer::GetCurrentTime() + t.recast_time)) { - t.timer_id = timer.timer_id; - t.timer_value = timer.timer_value; - t.recast_time = timer.recast_time; - t.is_spell = timer.is_spell ? true : false; - t.is_disc = timer.is_disc ? true : false; - t.spell_id = timer.spell_id; - t.is_item = timer.is_item ? true : false; - t.item_id = timer.item_id; - bot_timers.push_back(t); + t.timer_id = e.timer_id; + t.timer_value = e.timer_value; + t.recast_time = e.recast_time; + t.is_spell = e.is_spell; + t.is_disc = e.is_disc; + t.spell_id = e.spell_id; + t.is_item = e.is_item; + t.item_id = e.item_id; + + v.push_back(t); } } - if (!bot_timers.empty()) { - bot_inst->SetBotTimers(bot_timers); + if (!v.empty()) { + b->SetBotTimers(v); } return true; } -bool BotDatabase::SaveTimers(Bot* bot_inst) +bool BotDatabase::SaveTimers(Bot* b) { - if (!bot_inst) { + if (!b) { return false; } - if (!DeleteTimers(bot_inst->GetBotID())) { + if (!DeleteTimers(b->GetBotID())) { return false; } - std::vector bot_timers = bot_inst->GetBotTimers(); + std::vector v = b->GetBotTimers(); - if (bot_timers.empty()) { + if (v.empty()) { return true; } - std::vector timers; + std::vector l; - if (!bot_timers.empty()) { - for (auto & bot_timer : bot_timers) { + if (!v.empty()) { + for (auto & bot_timer : v) { if (bot_timer.timer_value <= Timer::GetCurrentTime()) { continue; } - auto t = BotTimersRepository::BotTimers{ - .bot_id = bot_inst->GetBotID(), + auto e = BotTimersRepository::BotTimers{ + .bot_id = b->GetBotID(), .timer_id = bot_timer.timer_id, .timer_value = bot_timer.timer_value, .recast_time = bot_timer.recast_time, - .is_spell = bot_timer.is_spell ? true : false, - .is_disc = bot_timer.is_disc ? true : false, + .is_spell = bot_timer.is_spell, + .is_disc = bot_timer.is_disc, .spell_id = bot_timer.spell_id, - .is_item = bot_timer.is_item ? true : false, + .is_item = bot_timer.is_item, .item_id = bot_timer.item_id }; - timers.push_back(t); + l.push_back(e); } - if (timers.empty()) { + if (l.empty()) { return true; } - // delete existing BotTimersRepository::DeleteWhere( database, - fmt::format("bot_id = {}", bot_inst->GetBotID()) + fmt::format( + "`bot_id` = {}", + b->GetBotID() + ) ); - // bulk insert current - auto success = BotTimersRepository::InsertMany(database, timers); - if (!success) { - DeleteTimers(bot_inst->GetBotID()); + const int inserted = BotTimersRepository::InsertMany(database, l); + + if (!inserted) { + DeleteTimers(b->GetBotID()); return false; } } @@ -1022,159 +941,158 @@ bool BotDatabase::DeleteTimers(const uint32 bot_id) return false; } - BotTimersRepository::DeleteWhere(database, fmt::format("bot_id = {}", bot_id)); + BotTimersRepository::DeleteWhere( + database, + fmt::format( + "`bot_id` = {}", + bot_id + ) + ); return true; } -/* Bot inventory functions */ bool BotDatabase::QueryInventoryCount(const uint32 bot_id, uint32& item_count) { - if (!bot_id) + if (!bot_id) { return false; + } - query = StringFormat("SELECT COUNT(`inventories_index`) FROM `bot_inventories` WHERE `bot_id` = '%u'", bot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - if (!results.RowCount()) - return true; - - auto row = results.begin(); - item_count = Strings::ToInt(row[0]); + item_count = BotInventoriesRepository::Count( + database, + fmt::format( + "`bot_id` = {}", + bot_id + ) + ); return true; } bool BotDatabase::LoadItems(const uint32 bot_id, EQ::InventoryProfile& inventory_inst) { - if (!bot_id) + if (!bot_id) { return false; + } - query = StringFormat( - "SELECT" - " `slot_id`," - " `item_id`," - " `inst_charges`," - " `inst_color`," - " `inst_no_drop`," - " `inst_custom_data`," - " `ornament_icon`," - " `ornament_id_file`," - " `ornament_hero_model`," - " `augment_1`," - " `augment_2`," - " `augment_3`," - " `augment_4`, " - " `augment_5`," - " `augment_6`" - " FROM `bot_inventories`" - " WHERE `bot_id` = '%i'" - " ORDER BY `slot_id`", - bot_id + const auto& l = BotInventoriesRepository::GetWhere( + database, + fmt::format( + "`bot_id` = {} ORDER BY `slot_id`", + bot_id + ) ); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - if (!results.RowCount()) + + if (l.empty()) { return true; + } - for (auto row = results.begin(); row != results.end(); ++row) { - int16 slot_id = Strings::ToInt(row[0]); - if (slot_id < EQ::invslot::EQUIPMENT_BEGIN || slot_id > EQ::invslot::EQUIPMENT_END) + for (const auto& e : l) { + if (!EQ::ValueWithin(e.slot_id, EQ::invslot::EQUIPMENT_BEGIN, EQ::invslot::EQUIPMENT_END)) { continue; + } - uint32 item_id = Strings::ToInt(row[1]); - uint16 item_charges = (uint16)Strings::ToInt(row[2]); - - EQ::ItemInstance* item_inst = database.CreateItem( - item_id, - item_charges, - (uint32)Strings::ToUnsignedInt(row[9]), - (uint32)Strings::ToUnsignedInt(row[10]), - (uint32)Strings::ToUnsignedInt(row[11]), - (uint32)Strings::ToUnsignedInt(row[12]), - (uint32)Strings::ToUnsignedInt(row[13]), - (uint32)Strings::ToUnsignedInt(row[14]) + auto inst = database.CreateItem( + e.item_id, + e.inst_charges, + e.augment_1, + e.augment_2, + e.augment_3, + e.augment_4, + e.augment_5, + e.augment_6 ); - if (!item_inst) { - LogError("Warning: bot_id [{}] has an invalid item_id [{}] in inventory slot [{}]", bot_id, item_id, slot_id); + + if (!inst) { + LogError( + "Warning: bot_id [{}] has an invalid item_id [{}] in slot_id [{}]", + bot_id, + e.item_id, + e.slot_id + ); + continue; } - if (item_charges == 0x7FFF) - item_inst->SetCharges(-1); - else if (item_charges == 0 && item_inst->IsStackable()) // Stackable items need a minimum charge of 1 remain moveable. - item_inst->SetCharges(1); - else - item_inst->SetCharges(item_charges); - - uint32 item_color = Strings::ToUnsignedInt(row[3]); - if (item_color > 0) - item_inst->SetColor(item_color); - - if (item_inst->GetItem()->Attuneable) { - if (Strings::ToInt(row[4])) - item_inst->SetAttuned(true); - else if (slot_id >= EQ::invslot::EQUIPMENT_BEGIN && slot_id <= EQ::invslot::EQUIPMENT_END) - item_inst->SetAttuned(true); + if (e.inst_charges == INT16_MAX) { + inst->SetCharges(-1); + } else if ( + e.inst_charges == 0 && + inst->IsStackable() + ) { // Stackable items need a minimum charge of 1 remain moveable. + inst->SetCharges(1); + } else { + inst->SetCharges(e.inst_charges); } - if (row[5]) { - std::string data_str(row[5]); - item_inst->SetCustomDataString(data_str); + if (e.inst_color) { + inst->SetColor(e.inst_color); } - item_inst->SetOrnamentIcon((uint32)Strings::ToUnsignedInt(row[6])); - item_inst->SetOrnamentationIDFile((uint32)Strings::ToUnsignedInt(row[7])); - item_inst->SetOrnamentHeroModel((uint32)Strings::ToUnsignedInt(row[8])); + if (inst->GetItem()->Attuneable) { + if (e.inst_no_drop) { + inst->SetAttuned(true); + } else if (EQ::ValueWithin(e.slot_id, EQ::invslot::EQUIPMENT_BEGIN, EQ::invslot::EQUIPMENT_END)) { + inst->SetAttuned(true); + } + } - if (inventory_inst.PutItem(slot_id, *item_inst) == INVALID_INDEX) - LogError("Warning: Invalid slot_id for item in inventory: bot_id = [{}], item_id = [{}], slot_id = [{}]", bot_id, item_id, slot_id); + if (!e.inst_custom_data.empty()) { + inst->SetCustomDataString(e.inst_custom_data); + } - safe_delete(item_inst); + inst->SetOrnamentIcon(e.ornament_icon); + inst->SetOrnamentationIDFile(e.ornament_id_file); + inst->SetOrnamentHeroModel(e.ornament_hero_model); + + if (inventory_inst.PutItem(e.slot_id, *inst) == INVALID_INDEX) { + LogError( + "Warning: Invalid slot_id for item in inventory: bot_id [{}] item_id [{}] slot_id [{}]", + bot_id, + e.item_id, + e.slot_id + ); + } + + safe_delete(inst); } return true; } -bool BotDatabase::SaveItems(Bot* bot_inst) -{ - return false; -} - bool BotDatabase::DeleteItems(const uint32 bot_id) { - if (!bot_id) + if (!bot_id) { return false; + } - query = StringFormat("DELETE FROM `bot_inventories` WHERE `bot_id` = '%u'", bot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; + BotInventoriesRepository::DeleteOne(database, bot_id); return true; } -bool BotDatabase::LoadItemBySlot(Bot* bot_inst) -{ - return false; -} - bool BotDatabase::LoadItemBySlot(const uint32 bot_id, const uint32 slot_id, uint32& item_id) { - if (!bot_id || slot_id > EQ::invslot::EQUIPMENT_END) + if (!bot_id || slot_id > EQ::invslot::EQUIPMENT_END) { return false; + } - query = StringFormat("SELECT `item_id` FROM `bot_inventories` WHERE `bot_id` = '%i' AND `slot_id` = '%i' LIMIT 1", bot_id, slot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - if (!results.RowCount()) + const auto& l = BotInventoriesRepository::GetWhere( + database, + fmt::format( + "`bot_id` = {} AND `slot_id` = {} LIMIT 1", + bot_id, + slot_id + ) + ); + + if (l.empty()) { return true; + } - auto row = results.begin(); - item_id = Strings::ToInt(row[0]); + auto e = l.front(); + + item_id = e.item_id; return true; } @@ -1188,328 +1106,307 @@ bool BotDatabase::LoadItemSlots(const uint32 bot_id, std::map& m const auto& l = BotInventoriesRepository::GetWhere( database, fmt::format( - "bot_id = {}", + "`bot_id` = {}", bot_id ) ); - if (!l.empty()) { - for (const auto& e : l) { - m.emplace(std::pair(e.slot_id, e.item_id)); - } + if (l.empty()) { + return true; + } + + for (const auto& e : l) { + m.emplace(std::pair(e.slot_id, e.item_id)); } return true; } -bool BotDatabase::SaveItemBySlot(Bot* bot_inst, const uint32 slot_id, const EQ::ItemInstance* item_inst) +bool BotDatabase::SaveItemBySlot(Bot* b, const uint32 slot_id, const EQ::ItemInstance* inst) { - if (!bot_inst || !bot_inst->GetBotID() || slot_id > EQ::invslot::EQUIPMENT_END) - return false; - - if (!DeleteItemBySlot(bot_inst->GetBotID(), slot_id)) - return false; - - if (!item_inst || !item_inst->GetID()) - return true; - uint32 augment_id[EQ::invaug::SOCKET_COUNT] = { 0, 0, 0, 0, 0, 0 }; - for (int augment_iter = EQ::invaug::SOCKET_BEGIN; augment_iter <= EQ::invaug::SOCKET_END; ++augment_iter) - augment_id[augment_iter] = item_inst->GetAugmentItemID(augment_iter); - - uint16 item_charges = 0; - if (item_inst->GetCharges() >= 0) - item_charges = item_inst->GetCharges(); - else - item_charges = 0x7FFF; - - query = StringFormat( - "INSERT INTO `bot_inventories` (" - "`bot_id`," - " `slot_id`," - " `item_id`," - " `inst_charges`," - " `inst_color`," - " `inst_no_drop`," - " `inst_custom_data`," - " `ornament_icon`," - " `ornament_id_file`," - " `ornament_hero_model`," - " `augment_1`," - " `augment_2`," - " `augment_3`," - " `augment_4`," - " `augment_5`," - " `augment_6`" - ")" - " VALUES (" - "'%lu'," /* bot_id */ - " '%lu'," /* slot_id */ - " '%lu'," /* item_id */ - " '%lu'," /* inst_charges */ - " '%lu'," /* inst_color */ - " '%lu'," /* inst_no_drop */ - " '%s'," /* inst_custom_data */ - " '%lu'," /* ornament_icon */ - " '%lu'," /* ornament_id_file */ - " '%lu'," /* ornament_hero_model */ - " '%lu'," /* augment_1 */ - " '%lu'," /* augment_2 */ - " '%lu'," /* augment_3 */ - " '%lu'," /* augment_4 */ - " '%lu'," /* augment_5 */ - " '%lu'" /* augment_6 */ - ")", - (unsigned long)bot_inst->GetBotID(), - (unsigned long)slot_id, - (unsigned long)item_inst->GetID(), - (unsigned long)item_charges, - (unsigned long)item_inst->GetColor(), - (unsigned long)(item_inst->IsAttuned() ? 1 : 0), - item_inst->GetCustomDataString().c_str(), - (unsigned long)item_inst->GetOrnamentationIcon(), - (unsigned long)item_inst->GetOrnamentationIDFile(), - (unsigned long)item_inst->GetOrnamentHeroModel(), - (unsigned long)augment_id[0], - (unsigned long)augment_id[1], - (unsigned long)augment_id[2], - (unsigned long)augment_id[3], - (unsigned long)augment_id[4], - (unsigned long)augment_id[5] - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - DeleteItemBySlot(bot_inst->GetBotID(), slot_id); + if ( + !b || + !b->GetBotID() || + slot_id > EQ::invslot::EQUIPMENT_END + ) { return false; } - return true; + if (!inst || !inst->GetID()) { + return true; + } + + DeleteItemBySlot(b->GetBotID(), slot_id); + + uint32 augment_id[EQ::invaug::SOCKET_COUNT] = { 0, 0, 0, 0, 0, 0 }; + + for (uint16 slot_id = EQ::invaug::SOCKET_BEGIN; slot_id <= EQ::invaug::SOCKET_END; ++slot_id) { + augment_id[slot_id] = inst->GetAugmentItemID(slot_id); + } + + uint16 item_charges = 0; + + if (inst->GetCharges() >= 0) { + item_charges = inst->GetCharges(); + } else { + item_charges = INT16_MAX; + } + + auto e = BotInventoriesRepository::NewEntity(); + + e.bot_id = b->GetBotID(); + e.slot_id = slot_id; + e.item_id = inst->GetID(); + e.inst_charges = item_charges; + e.inst_color = inst->GetColor(); + e.inst_no_drop = inst->IsAttuned() ? 1 : 0; + e.inst_custom_data = inst->GetCustomDataString(); + e.ornament_icon = inst->GetOrnamentationIcon(); + e.ornament_id_file = inst->GetOrnamentationIDFile(); + e.ornament_hero_model = inst->GetOrnamentHeroModel(); + e.augment_1 = augment_id[0]; + e.augment_2 = augment_id[1]; + e.augment_3 = augment_id[2]; + e.augment_4 = augment_id[3]; + e.augment_5 = augment_id[4]; + e.augment_6 = augment_id[5]; + + return BotInventoriesRepository::InsertOne(database, e).inventories_index; } bool BotDatabase::DeleteItemBySlot(const uint32 bot_id, const uint32 slot_id) { - if (!bot_id || slot_id > EQ::invslot::EQUIPMENT_END) + if (!bot_id || slot_id > EQ::invslot::EQUIPMENT_END) { return false; + } - query = StringFormat("DELETE FROM `bot_inventories` WHERE `bot_id` = '%u' AND `slot_id` = '%u'", bot_id, slot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; + BotInventoriesRepository::DeleteWhere( + database, + fmt::format( + "`bot_id` = {} AND `slot_id` = {}", + bot_id, + slot_id + ) + ); return true; } -bool BotDatabase::LoadEquipmentColor(const uint32 bot_id, const uint8 material_slot_id, uint32& rgb) +bool BotDatabase::SaveEquipmentColor(const uint32 bot_id, const int16 slot_id, const uint32 color) { - if (!bot_id) + if (!bot_id) { return false; + } - int16 slot_id = EQ::InventoryProfile::CalcSlotFromMaterial(material_slot_id); - if (slot_id == INVALID_INDEX) - return false; - - query = StringFormat("SELECT `inst_color` FROM `bot_inventories` WHERE `bot_id` = '%u' AND `slot_id` = '%u' LIMIT 1", bot_id, slot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - if (!results.RowCount()) - return true; - - auto row = results.begin(); - rgb = Strings::ToUnsignedInt(row[0]); - - return true; -} - -bool BotDatabase::SaveEquipmentColor(const uint32 bot_id, const int16 slot_id, const uint32 rgb) -{ - if (!bot_id) - return false; - - bool all_flag = (slot_id == -2); - if ((slot_id < EQ::invslot::EQUIPMENT_BEGIN || slot_id > EQ::invslot::EQUIPMENT_END) && !all_flag) + const bool all_flag = (slot_id == -2); + + if (!EQ::ValueWithin(slot_id, EQ::invslot::EQUIPMENT_BEGIN, EQ::invslot::EQUIPMENT_END) && !all_flag) { return false; + } std::string where_clause; - if (all_flag) - where_clause = StringFormat(" AND `slot_id` IN ('%u', '%u', '%u', '%u', '%u', '%u', '%u')", EQ::invslot::slotHead, EQ::invslot::slotArms, EQ::invslot::slotWrist1, EQ::invslot::slotHands, EQ::invslot::slotChest, EQ::invslot::slotLegs, EQ::invslot::slotFeet); - else - where_clause = StringFormat(" AND `slot_id` = '%u'", slot_id); + if (all_flag) { + where_clause = fmt::format( + "IN ({}, {}, {}, {}, {}, {}, {})", + EQ::invslot::slotHead, + EQ::invslot::slotArms, + EQ::invslot::slotWrist1, + EQ::invslot::slotHands, + EQ::invslot::slotChest, + EQ::invslot::slotLegs, + EQ::invslot::slotFeet + ); + } else { + where_clause = fmt::format( + "= {}", + slot_id + ); + } - query = StringFormat( - "UPDATE `bot_inventories`" - " SET `inst_color` = '%u'" - " WHERE `bot_id` = '%u'" - " %s", - rgb, - bot_id, - where_clause.c_str() - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - - return true; + return BotInventoriesRepository::UpdateItemColors(database, bot_id, color, where_clause); } - -/* Bot pet functions */ bool BotDatabase::LoadPetIndex(const uint32 bot_id, uint32& pet_index) { - if (!bot_id) + if (!bot_id) { return false; + } - query = StringFormat("SELECT `pets_index` FROM `bot_pets` WHERE `bot_id` = '%u' LIMIT 1", bot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - if (!results.RowCount()) + const auto& l = BotPetsRepository::GetWhere( + database, + fmt::format( + "`bot_id` = {} LIMIT 1", + bot_id + ) + ); + + if (l.empty()) { return true; + } - auto row = results.begin(); - pet_index = Strings::ToInt(row[0]); + auto e = l.front(); + + pet_index = e.pets_index; return true; } bool BotDatabase::LoadPetSpellID(const uint32 bot_id, uint32& pet_spell_id) { - if (!bot_id) + if (!bot_id) { return false; + } - query = StringFormat("SELECT `spell_id` FROM `bot_pets` WHERE `bot_id` = '%u' LIMIT 1", bot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - if (!results.RowCount()) + const auto& l = BotPetsRepository::GetWhere( + database, + fmt::format( + "`bot_id` = {} LIMIT 1", + bot_id + ) + ); + + if (l.empty()) { return true; + } - auto row = results.begin(); - pet_spell_id = Strings::ToInt(row[0]); + auto e = l.front(); + + pet_spell_id = e.spell_id; return true; } bool BotDatabase::LoadPetStats(const uint32 bot_id, std::string& pet_name, uint32& pet_mana, uint32& pet_hp, uint32& pet_spell_id) { - if (!bot_id) + if (!bot_id) { return false; + } uint32 saved_pet_index = 0; - if (!LoadPetIndex(bot_id, saved_pet_index)) - return false; - if (!saved_pet_index) - return true; - query = StringFormat("SELECT `spell_id`, `name`, `mana`, `hp` FROM `bot_pets` WHERE `pets_index` = '%u' LIMIT 1", saved_pet_index); - auto results = database.QueryDatabase(query); - if (!results.Success()) + if (!LoadPetIndex(bot_id, saved_pet_index)) { return false; - if (!results.RowCount()) - return true; + } - auto row = results.begin(); - pet_spell_id = Strings::ToInt(row[0]); - pet_name = row[1]; - pet_mana = Strings::ToInt(row[2]); - pet_hp = Strings::ToInt(row[3]); + if (!saved_pet_index) { + return true; + } + + const auto& l = BotPetsRepository::GetWhere( + database, + fmt::format( + "`pets_index` = {} LIMIT 1", + saved_pet_index + ) + ); + + if (l.empty()) { + return true; + } + + auto e = l.front(); + + pet_spell_id = e.spell_id; + pet_name = e.name; + pet_mana = e.mana; + pet_hp = e.hp; return true; } bool BotDatabase::SavePetStats(const uint32 bot_id, const std::string& pet_name, const uint32 pet_mana, const uint32 pet_hp, const uint32 pet_spell_id) { - if (!bot_id || pet_name.empty() || !pet_spell_id || pet_spell_id > SPDAT_RECORDS) - return false; - - if (!DeletePetItems(bot_id)) - return false; - if (!DeletePetBuffs(bot_id)) - return false; - if (!DeletePetStats(bot_id)) - return false; - - query = StringFormat( - "INSERT INTO `bot_pets` (" - "`spell_id`," - " `bot_id`," - " `name`," - " `mana`," - " `hp`" - ")" - " VALUES (" - "'%u'," - " '%u'," - " '%s'," - " '%u'," - " '%u'" - ")", - pet_spell_id, - bot_id, - pet_name.c_str(), - pet_mana, - pet_hp - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - DeletePetStats(bot_id); + if (!bot_id || pet_name.empty() || !pet_spell_id || pet_spell_id > SPDAT_RECORDS) { return false; } - return true; + if ( + !DeletePetItems(bot_id) || + !DeletePetBuffs(bot_id) || + !DeletePetStats(bot_id) + ) { + return false; + } + + return BotPetsRepository::InsertOne( + database, + BotPetsRepository::BotPets{ + .spell_id = pet_spell_id, + .bot_id = bot_id, + .name = pet_name, + .mana = static_cast(pet_mana), + .hp = static_cast(pet_hp) + } + ).pets_index; } bool BotDatabase::DeletePetStats(const uint32 bot_id) { - if (!bot_id) + if (!bot_id) { return false; + } uint32 saved_pet_index = 0; - if (!LoadPetIndex(bot_id, saved_pet_index)) + + if (!LoadPetIndex(bot_id, saved_pet_index)) { return false; - if (!saved_pet_index) + } + + if (!saved_pet_index) { return true; + } - query = StringFormat("DELETE FROM `bot_pets` WHERE `pets_index` = '%u'", saved_pet_index); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - - return true; + BotPetsRepository::DeleteOne(database, saved_pet_index); } bool BotDatabase::LoadPetBuffs(const uint32 bot_id, SpellBuff_Struct* pet_buffs) { - if (!bot_id) + if (!bot_id) { return false; + } uint32 saved_pet_index = 0; - if (!LoadPetIndex(bot_id, saved_pet_index)) + + if (!LoadPetIndex(bot_id, saved_pet_index)) { return false; - if (!saved_pet_index) + } + + if (!saved_pet_index) { return true; + } - query = StringFormat("SELECT `spell_id`, `caster_level`, `duration` FROM `bot_pet_buffs` WHERE `pets_index` = '%u'", saved_pet_index); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - if (!results.RowCount()) + const auto& l = BotPetBuffsRepository::GetWhere( + database, + fmt::format( + "`pets_index` = {}", + saved_pet_index + ) + ); + + if (l.empty()) { return true; + } - int buff_index = 0; - for (auto row = results.begin(); row != results.end() && buff_index < PET_BUFF_COUNT; ++row) { - pet_buffs[buff_index].spellid = Strings::ToInt(row[0]); - pet_buffs[buff_index].level = Strings::ToInt(row[1]); - pet_buffs[buff_index].duration = Strings::ToInt(row[2]); + uint16 buff_index = 0; - // Work around for loading the counters and setting them back to max. Need entry in DB for saved counters - if (CalculatePoisonCounters(pet_buffs[buff_index].spellid) > 0) + for (const auto& e : l) { + if (buff_index >= PET_BUFF_COUNT) { + break; + } + + pet_buffs[buff_index].spellid = e.spell_id; + pet_buffs[buff_index].level = e.caster_level; + pet_buffs[buff_index].duration = e.duration; + + if (CalculatePoisonCounters(pet_buffs[buff_index].spellid) > 0) { pet_buffs[buff_index].counters = CalculatePoisonCounters(pet_buffs[buff_index].spellid); - else if (CalculateDiseaseCounters(pet_buffs[buff_index].spellid) > 0) + } else if (CalculateDiseaseCounters(pet_buffs[buff_index].spellid) > 0) { pet_buffs[buff_index].counters = CalculateDiseaseCounters(pet_buffs[buff_index].spellid); - else if (CalculateCurseCounters(pet_buffs[buff_index].spellid) > 0) + } else if (CalculateCurseCounters(pet_buffs[buff_index].spellid) > 0) { pet_buffs[buff_index].counters = CalculateCurseCounters(pet_buffs[buff_index].spellid); - else if (CalculateCorruptionCounters(pet_buffs[buff_index].spellid) > 0) + } else if (CalculateCorruptionCounters(pet_buffs[buff_index].spellid) > 0) { pet_buffs[buff_index].counters = CalculateCorruptionCounters(pet_buffs[buff_index].spellid); + } ++buff_index; } @@ -1519,48 +1416,44 @@ bool BotDatabase::LoadPetBuffs(const uint32 bot_id, SpellBuff_Struct* pet_buffs) bool BotDatabase::SavePetBuffs(const uint32 bot_id, const SpellBuff_Struct* pet_buffs, bool delete_flag) { - // Only use 'delete_flag' if not invoked after a botdb.SavePetStats() call - - if (!bot_id || !pet_buffs) - return false; - - if (delete_flag && !DeletePetBuffs(bot_id)) + if ( + !bot_id || + !pet_buffs || + (delete_flag && !DeletePetBuffs(bot_id)) + ) { return false; + } uint32 saved_pet_index = 0; - if (!LoadPetIndex(bot_id, saved_pet_index)) - return false; - if (!saved_pet_index) - return true; - for (int buff_index = 0; buff_index < PET_BUFF_COUNT; ++buff_index) { + if (!LoadPetIndex(bot_id, saved_pet_index)) { + return false; + } + + if (!saved_pet_index) { + return true; + } + + auto e = BotPetBuffsRepository::NewEntity(); + + e.pets_index = saved_pet_index; + + std::vector v; + + for (uint16 buff_index = 0; buff_index < PET_BUFF_COUNT; ++buff_index) { if (!IsValidSpell(pet_buffs[buff_index].spellid)) { continue; } - query = StringFormat( - "INSERT INTO `bot_pet_buffs` (" - "`pets_index`," - " `spell_id`," - " `caster_level`," - " `duration`" - ")" - " VALUES (" - "'%u'," - " '%u'," - " '%u'," - " '%u'" - ")", - saved_pet_index, - pet_buffs[buff_index].spellid, - pet_buffs[buff_index].level, - pet_buffs[buff_index].duration - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - DeletePetBuffs(bot_id); - return false; - } + e.spell_id = pet_buffs[buff_index].spellid; + e.caster_level = pet_buffs[buff_index].level; + e.duration = pet_buffs[buff_index].duration; + + v.emplace_back(e); + } + + if (!v.empty()) { + BotPetBuffsRepository::InsertMany(database, v); } return true; @@ -1568,45 +1461,62 @@ bool BotDatabase::SavePetBuffs(const uint32 bot_id, const SpellBuff_Struct* pet_ bool BotDatabase::DeletePetBuffs(const uint32 bot_id) { - if (!bot_id) + if (!bot_id) { return false; + } uint32 saved_pet_index = 0; - if (!LoadPetIndex(bot_id, saved_pet_index)) - return false; - if (!saved_pet_index) - return true; - query = StringFormat("DELETE FROM `bot_pet_buffs` WHERE `pets_index` = '%u'", saved_pet_index); - auto results = database.QueryDatabase(query); - if (!results.Success()) + if (!LoadPetIndex(bot_id, saved_pet_index)) { return false; + } + + if (!saved_pet_index) { + return true; + } + + BotPetBuffsRepository::DeleteOne(database, saved_pet_index); return true; } bool BotDatabase::LoadPetItems(const uint32 bot_id, uint32* pet_items) { - if (!bot_id || !pet_items) + if (!bot_id || !pet_items) { return false; + } uint32 saved_pet_index = 0; - if (!LoadPetIndex(bot_id, saved_pet_index)) - return false; - if (!saved_pet_index) - return true; - query = StringFormat("SELECT `item_id` FROM `bot_pet_inventories` WHERE `pets_index` = '%u'", saved_pet_index); - auto results = database.QueryDatabase(query); - if (!results.Success()) + if (!LoadPetIndex(bot_id, saved_pet_index)) { return false; - if (!results.RowCount()) - return true; + } - int item_index = EQ::invslot::EQUIPMENT_BEGIN; - for (auto row = results.begin(); row != results.end() && (item_index >= EQ::invslot::EQUIPMENT_BEGIN && item_index <= EQ::invslot::EQUIPMENT_END); ++row) { - pet_items[item_index] = Strings::ToInt(row[0]); - ++item_index; + if (!saved_pet_index) { + return true; + } + + const auto& l = BotPetInventoriesRepository::GetWhere( + database, + fmt::format( + "`pets_index` = {}", + saved_pet_index + ) + ); + + if (l.empty()) { + return true; + } + + int16 slot_id = EQ::invslot::EQUIPMENT_BEGIN; + + for (const auto& e : l) { + if (!EQ::ValueWithin(slot_id, EQ::invslot::EQUIPMENT_BEGIN, EQ::invslot::EQUIPMENT_END)) { + break; + } + + pet_items[slot_id] = e.item_id; + ++slot_id; } return true; @@ -1616,28 +1526,42 @@ bool BotDatabase::SavePetItems(const uint32 bot_id, const uint32* pet_items, boo { // Only use 'delete_flag' if not invoked after a botdb.SavePetStats() call - if (!bot_id || !pet_items) - return false; - - if (delete_flag && !DeletePetItems(bot_id)) + if ( + !bot_id || + !pet_items || + (delete_flag && !DeletePetItems(bot_id)) + ) { return false; + } uint32 saved_pet_index = 0; - if (!LoadPetIndex(bot_id, saved_pet_index)) + + if (!LoadPetIndex(bot_id, saved_pet_index)) { return false; - if (!saved_pet_index) + } + + if (!saved_pet_index) { return true; + } - for (int item_index = EQ::invslot::EQUIPMENT_BEGIN; item_index <= EQ::invslot::EQUIPMENT_END; ++item_index) { - if (!pet_items[item_index]) + auto e = BotPetInventoriesRepository::NewEntity(); + + e.pets_index = saved_pet_index; + + std::vector v; + + for (int slot_id = EQ::invslot::EQUIPMENT_BEGIN; slot_id <= EQ::invslot::EQUIPMENT_END; ++slot_id) { + if (!pet_items[slot_id]) { continue; - - query = StringFormat("INSERT INTO `bot_pet_inventories` (`pets_index`, `item_id`) VALUES ('%u', '%u')", saved_pet_index, pet_items[item_index]); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - DeletePetItems(bot_id); - return false; } + + e.item_id = pet_items[slot_id]; + + v.emplace_back(e); + } + + if (!v.empty()) { + BotPetInventoriesRepository::InsertMany(database, v); } return true; @@ -1645,507 +1569,263 @@ bool BotDatabase::SavePetItems(const uint32 bot_id, const uint32* pet_items, boo bool BotDatabase::DeletePetItems(const uint32 bot_id) { - if (!bot_id) + if (!bot_id) { return false; + } uint32 saved_pet_index = 0; - if (!LoadPetIndex(bot_id, saved_pet_index)) - return false; - if (!saved_pet_index) - return true; - query = StringFormat("DELETE FROM `bot_pet_inventories` WHERE `pets_index` = '%u'", saved_pet_index); - auto results = database.QueryDatabase(query); - if (!results.Success()) + if (!LoadPetIndex(bot_id, saved_pet_index)) { return false; + } + + if (!saved_pet_index) { + return true; + } + + BotPetInventoriesRepository::DeleteOne(database, saved_pet_index); return true; } - -/* Bot command functions */ bool BotDatabase::LoadInspectMessage(const uint32 bot_id, InspectMessage_Struct& inspect_message) { - if (!bot_id) + if (!bot_id) { return false; + } - query = StringFormat("SELECT `inspect_message` FROM `bot_inspect_messages` WHERE `bot_id` = '%u' LIMIT 1", bot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) + const auto& e = BotInspectMessagesRepository::FindOne(database, bot_id); + + if (!e.bot_id) { return false; - if (!results.RowCount()) - return true; + } - auto row = results.begin(); - std::string bot_message = row[0]; - if (bot_message.size() > 255) - bot_message = bot_message.substr(0, 255); - if (bot_message.empty()) + if (e.inspect_message.empty()) { return true; + } - memcpy(inspect_message.text, bot_message.c_str(), bot_message.size()); + std::string bot_message = e.inspect_message; + + if (bot_message.size() > UINT8_MAX) { + bot_message = bot_message.substr(0, UINT8_MAX); + } + + strn0cpy(inspect_message.text, bot_message.c_str(), sizeof(inspect_message.text)); return true; } bool BotDatabase::SaveInspectMessage(const uint32 bot_id, const InspectMessage_Struct& inspect_message) { - if (!bot_id) - return false; - - if (!DeleteInspectMessage(bot_id)) - return false; - - std::string bot_message = inspect_message.text; - if (bot_message.size() > 255) - bot_message = bot_message.substr(0, 255); - if (bot_message.empty()) - return true; - - query = StringFormat("INSERT INTO `bot_inspect_messages` (`bot_id`, `inspect_message`) VALUES ('%u', '%s')", bot_id, bot_message.c_str()); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - DeleteInspectMessage(bot_id); + if (!bot_id || !DeleteInspectMessage(bot_id)) { return false; } - return true; + std::string bot_message = inspect_message.text; + + if (bot_message.empty()) { + return true; + } + + if (bot_message.size() > UINT8_MAX) { + bot_message = bot_message.substr(0, UINT8_MAX); + } } bool BotDatabase::DeleteInspectMessage(const uint32 bot_id) { - if (!bot_id) + if (!bot_id) { return false; + } - query = StringFormat("DELETE FROM `bot_inspect_messages` WHERE `bot_id` = '%u'", bot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; + BotInspectMessagesRepository::DeleteOne(database, bot_id); return true; } bool BotDatabase::SaveAllInspectMessages(const uint32 owner_id, const InspectMessage_Struct& inspect_message) { - if (!owner_id) - return false; - - if (!DeleteAllInspectMessages(owner_id)) - return false; - - std::string bot_message = inspect_message.text; - if (bot_message.size() > 255) - bot_message = bot_message.substr(0, 255); - if (bot_message.empty()) - return true; - - query = StringFormat("INSERT INTO `bot_inspect_messages` (`bot_id`, `inspect_message`) SELECT `bot_id`, '%s' inspect_message FROM `bot_data` WHERE `owner_id` = '%u'", bot_message.c_str(), owner_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - DeleteAllInspectMessages(owner_id); + if (!owner_id || !DeleteAllInspectMessages(owner_id)) { return false; } - return true; + std::string bot_message = inspect_message.text; + + if (bot_message.empty()) { + return true; + } + + if (bot_message.size() > UINT8_MAX) { + bot_message = bot_message.substr(0, UINT8_MAX); + } + + return BotInspectMessagesRepository::SaveAllInspectMessages(database, owner_id, bot_message); } bool BotDatabase::DeleteAllInspectMessages(const uint32 owner_id) { - if (!owner_id) + if (!owner_id) { return false; + } - query = StringFormat("DELETE FROM `bot_inspect_messages` WHERE `bot_id` IN (SELECT `bot_id` FROM `bot_data` WHERE `owner_id` = '%u')", owner_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; + BotInspectMessagesRepository::DeleteAllInspectMessages(database, owner_id); return true; } bool BotDatabase::SaveAllArmorColorBySlot(const uint32 owner_id, const int16 slot_id, const uint32 rgb_value) { - if (!owner_id) + if (!owner_id) { return false; + } - query = StringFormat( - "UPDATE `bot_inventories` bi" - " INNER JOIN `bot_data` bd" - " ON bd.`owner_id` = '%u'" - " SET bi.`inst_color` = '%u'" - " WHERE bi.`bot_id` = bd.`bot_id`" - " AND bi.`slot_id` IN ('%u', '%u', '%u', '%u', '%u', '%u', '%u', '%u')" - " AND bi.`slot_id` = '%i'", - owner_id, - rgb_value, - EQ::invslot::slotHead, EQ::invslot::slotChest, EQ::invslot::slotArms, EQ::invslot::slotWrist1, EQ::invslot::slotWrist2, EQ::invslot::slotHands, EQ::invslot::slotLegs, EQ::invslot::slotFeet, - slot_id - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; + BotInventoriesRepository::SaveAllArmorColorsBySlot(database, owner_id, slot_id, rgb_value); return true; } bool BotDatabase::SaveAllArmorColors(const uint32 owner_id, const uint32 rgb_value) { - if (!owner_id) + if (!owner_id) { return false; + } - query = StringFormat( - "UPDATE `bot_inventories` bi" - " INNER JOIN `bot_data` bd" - " ON bd.`owner_id` = '%u'" - " SET bi.`inst_color` = '%u'" - " WHERE bi.`bot_id` = bd.`bot_id`" - " AND bi.`slot_id` IN ('%u', '%u', '%u', '%u', '%u', '%u', '%u', '%u')", - owner_id, - rgb_value, - EQ::invslot::slotHead, EQ::invslot::slotChest, EQ::invslot::slotArms, EQ::invslot::slotWrist1, EQ::invslot::slotWrist2, EQ::invslot::slotHands, EQ::invslot::slotLegs, EQ::invslot::slotFeet - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - - return true; + return BotInventoriesRepository::SaveAllArmorColors(database, owner_id, rgb_value); } -bool BotDatabase::SaveHelmAppearance(const uint32 owner_id, const uint32 bot_id, const bool show_flag) +bool BotDatabase::SaveHelmAppearance(const uint32 bot_id, const bool show_flag) { - if (!owner_id || !bot_id) + if (!bot_id) { return false; + } - query = StringFormat( - "UPDATE `bot_data`" - " SET `show_helm` = '%u'" - " WHERE `owner_id` = '%u'" - " AND `bot_id` = '%u'", - (show_flag ? 1 : 0), - owner_id, - bot_id - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; + auto e = BotDataRepository::FindOne(database, bot_id); - return true; + e.show_helm = show_flag ? 1 : 0; + + return BotDataRepository::UpdateOne(database, e); } bool BotDatabase::SaveAllHelmAppearances(const uint32 owner_id, const bool show_flag) { - if (!owner_id) + if (!owner_id) { return false; + } - query = StringFormat( - "UPDATE `bot_data`" - " SET `show_helm` = '%u'" - " WHERE `owner_id` = '%u'", - (show_flag ? 1 : 0), - owner_id - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - - return true; -} - -bool BotDatabase::ToggleHelmAppearance(const uint32 owner_id, const uint32 bot_id) -{ - if (!owner_id || !bot_id) - return false; - - query = StringFormat( - "UPDATE `bot_data`" - " SET `show_helm` = (`show_helm` XOR '1')" - " WHERE `owner_id` = '%u'" - " AND `bot_id` = '%u'", - owner_id, - bot_id - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - - return true; + return BotDataRepository::SaveAllHelmAppearances(database, owner_id, show_flag); } bool BotDatabase::ToggleAllHelmAppearances(const uint32 owner_id) { - if (!owner_id) + if (!owner_id) { return false; + } - query = StringFormat( - "UPDATE `bot_data`" - " SET `show_helm` = (`show_helm` XOR '1')" - " WHERE `owner_id` = '%u'", - owner_id - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - - return true; + return BotDataRepository::ToggleAllHelmAppearances(database, owner_id); } -bool BotDatabase::SaveFollowDistance(const uint32 owner_id, const uint32 bot_id, const uint32 follow_distance) +bool BotDatabase::SaveFollowDistance(const uint32 bot_id, const uint32 follow_distance) { - if (!owner_id || !bot_id || !follow_distance) + if (!bot_id || !follow_distance) { return false; + } - query = StringFormat( - "UPDATE `bot_data`" - " SET `follow_distance` = '%u'" - " WHERE `owner_id` = '%u'" - " AND `bot_id` = '%u'", - follow_distance, - owner_id, - bot_id - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; + auto e = BotDataRepository::FindOne(database, bot_id); - return true; + e.follow_distance = follow_distance; + + return BotDataRepository::UpdateOne(database, e); } bool BotDatabase::SaveAllFollowDistances(const uint32 owner_id, const uint32 follow_distance) { - if (!owner_id || !follow_distance) - return false; - - query = StringFormat( - "UPDATE `bot_data`" - " SET `follow_distance` = '%u'" - " WHERE `owner_id` = '%u'", - follow_distance, - owner_id - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - - return true; -} - -bool BotDatabase::CreateCloneBot(const uint32 owner_id, const uint32 bot_id, const std::string& clone_name, uint32& clone_id) -{ - if (!owner_id || !bot_id || clone_name.empty()) - return false; - - query = StringFormat( - "INSERT INTO `bot_data`" - " (" - "`owner_id`," - " `spells_id`," - " `name`," - " `last_name`," - " `title`," - " `suffix`," - " `zone_id`," - " `gender`," - " `race`," - " `class`," - " `level`," - " `deity`," - " `creation_day`," - " `last_spawn`," - " `time_spawned`," - " `size`," - " `face`," - " `hair_color`," - " `hair_style`," - " `beard`," - " `beard_color`," - " `eye_color_1`," - " `eye_color_2`," - " `drakkin_heritage`," - " `drakkin_tattoo`," - " `drakkin_details`," - " `ac`," - " `atk`," - " `hp`," - " `mana`," - " `str`," - " `sta`," - " `cha`," - " `dex`," - " `int`," - " `agi`," - " `wis`," - " `fire`," - " `cold`," - " `magic`," - " `poison`," - " `disease`," - " `corruption`," - " `show_helm`," - " `follow_distance`," - " `stop_melee_level`" - ")" - " SELECT" - " bd.`owner_id`," - " bd.`spells_id`," - " '%s'," - " ''," - " bd.`title`," - " bd.`suffix`," - " bd.`zone_id`," - " bd.`gender`," - " bd.`race`," - " bd.`class`," - " bd.`level`," - " bd.`deity`," - " UNIX_TIMESTAMP()," - " UNIX_TIMESTAMP()," - " '0'," - " bd.`size`," - " bd.`face`," - " bd.`hair_color`," - " bd.`hair_style`," - " bd.`beard`," - " bd.`beard_color`," - " bd.`eye_color_1`," - " bd.`eye_color_2`," - " bd.`drakkin_heritage`," - " bd.`drakkin_tattoo`," - " bd.`drakkin_details`," - " bd.`ac`," - " bd.`atk`," - " bd.`hp`," - " bd.`mana`," - " bd.`str`," - " bd.`sta`," - " bd.`cha`," - " bd.`dex`," - " bd.`int`," - " bd.`agi`," - " bd.`wis`," - " bd.`fire`," - " bd.`cold`," - " bd.`magic`," - " bd.`poison`," - " bd.`disease`," - " bd.`corruption`," - " bd.`show_helm`," - " bd.`follow_distance`," - " bd.`stop_melee_level`" - " FROM `bot_data` bd" - " WHERE" - " bd.`owner_id` = '%u'" - " AND" - " bd.`bot_id` = '%u'", - clone_name.c_str(), - owner_id, - bot_id - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - - clone_id = results.LastInsertedID(); - - return true; -} - -bool BotDatabase::CreateCloneBotInventory(const uint32 owner_id, const uint32 bot_id, const uint32 clone_id) -{ - if (!owner_id || !bot_id || !clone_id) - return false; - - query = StringFormat( - "INSERT INTO `bot_inventories`" - " (" - "bot_id," - " `slot_id`," - " `item_id`," - " `inst_charges`," - " `inst_color`," - " `inst_no_drop`," - " `inst_custom_data`," - " `ornament_icon`," - " `ornament_id_file`," - " `ornament_hero_model`," - " `augment_1`," - " `augment_2`," - " `augment_3`," - " `augment_4`," - " `augment_5`," - " `augment_6`" - ")" - " SELECT" - " '%u' bot_id," - " bi.`slot_id`," - " bi.`item_id`," - " bi.`inst_charges`," - " bi.`inst_color`," - " bi.`inst_no_drop`," - " bi.`inst_custom_data`," - " bi.`ornament_icon`," - " bi.`ornament_id_file`," - " bi.`ornament_hero_model`," - " bi.`augment_1`," - " bi.`augment_2`," - " bi.`augment_3`," - " bi.`augment_4`," - " bi.`augment_5`," - " bi.`augment_6`" - " FROM `bot_inventories` bi" - " WHERE" - " bi.`bot_id` = '%u'" - " AND" - " '%u' = (SELECT `owner_id` FROM `bot_data` WHERE `bot_id` = '%u')", - clone_id, - bot_id, - owner_id, - bot_id - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - DeleteItems(clone_id); + if (!owner_id || !follow_distance) { return false; } + return BotDataRepository::SaveAllFollowDistances(database, owner_id, follow_distance); +} + +bool BotDatabase::CreateCloneBot(const uint32 bot_id, const std::string& clone_name, uint32& clone_id) +{ + if (!bot_id || clone_name.empty()) { + return false; + } + + auto e = BotDataRepository::FindOne(database, bot_id); + + e.bot_id = 0; + e.name = clone_name; + + e = BotDataRepository::InsertOne(database, e); + + if (!e.bot_id) { + return false; + } + + clone_id = e.bot_id; + return true; } -bool BotDatabase::SaveStopMeleeLevel(const uint32 owner_id, const uint32 bot_id, const uint8 sml_value) +bool BotDatabase::CreateCloneBotInventory(const uint32 bot_id, const uint32 clone_id) { - if (!owner_id || !bot_id) + if (!bot_id || !clone_id) { return false; + } - query = StringFormat( - "UPDATE `bot_data`" - " SET `stop_melee_level` = '%u'" - " WHERE `owner_id` = '%u'" - " AND `bot_id` = '%u'", - sml_value, - owner_id, - bot_id + auto l = BotInventoriesRepository::GetWhere( + database, + fmt::format( + "`bot_id` = {}", + bot_id + ) ); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - return true; + if (l.empty()) { + return true; + } + + for (auto& e : l) { + e.bot_id = clone_id; + } + + return BotInventoriesRepository::InsertMany(database, l); } -bool BotDatabase::LoadOwnerOptions(Client *owner) +bool BotDatabase::SaveStopMeleeLevel(const uint32 bot_id, const uint8 sml_value) { - if (!owner || !owner->CharacterID()) { + if (!bot_id) { return false; } - query = fmt::format("SELECT `option_type`, `option_value` FROM `bot_owner_options` WHERE `owner_id` = '{}'", owner->CharacterID()); + auto e = BotDataRepository::FindOne(database, bot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) { + e.stop_melee_level = sml_value; + + return BotDataRepository::UpdateOne(database, e); +} + +bool BotDatabase::LoadOwnerOptions(Client* c) +{ + if (!c || !c->CharacterID()) { return false; } - for (auto row : results) { + const auto& l = BotOwnerOptionsRepository::GetWhere( + database, + fmt::format( + "`owner_id` = {}", + c->CharacterID() + ) + ); - owner->SetBotOption(static_cast(Strings::ToUnsignedInt(row[0])), (Strings::ToUnsignedInt(row[1]) != 0)); + if (l.empty()) { + return true; + } + + for (const auto& e : l) { + c->SetBotOption(static_cast(e.option_type), e.option_value); } return true; @@ -2157,32 +1837,34 @@ bool BotDatabase::SaveOwnerOption(const uint32 owner_id, size_t type, const bool return false; } - switch (static_cast(type)) { - case Client::booDeathMarquee: - case Client::booStatsUpdate: - case Client::booSpawnMessageClassSpecific: - case Client::booAltCombat: - case Client::booAutoDefend: - case Client::booBuffCounter: - case Client::booMonkWuMessage: - { - query = fmt::format( - "REPLACE INTO `bot_owner_options`(`owner_id`, `option_type`, `option_value`) VALUES ('{}', '{}', '{}')", - owner_id, - type, - (flag == true ? 1 : 0) + std::vector l = { + Client::booDeathMarquee, + Client::booStatsUpdate, + Client::booSpawnMessageClassSpecific, + Client::booAltCombat, + Client::booAutoDefend, + Client::booBuffCounter, + Client::booMonkWuMessage + }; + + if ( + std::find( + l.begin(), + l.end(), + static_cast(type) + ) != l.end() + ) { + return BotOwnerOptionsRepository::ReplaceOne( + database, + BotOwnerOptionsRepository::BotOwnerOptions{ + .owner_id = owner_id, + .option_type = static_cast(type), + .option_value = static_cast(flag ? 1 : 0) + } ); - - auto results = database.QueryDatabase(query); - if (!results.Success()) { - return false; - } - - return true; - } - default: - return false; } + + return false; } bool BotDatabase::SaveOwnerOption(const uint32 owner_id, const std::pair type, const std::pair flag) @@ -2191,174 +1873,173 @@ bool BotDatabase::SaveOwnerOption(const uint32 owner_id, const std::pair(type.first)) { - case Client::booSpawnMessageSay: - case Client::booSpawnMessageTell: - { - switch (static_cast(type.second)) { - case Client::booSpawnMessageSay: - case Client::booSpawnMessageTell: - { - query = fmt::format( - "REPLACE INTO `bot_owner_options`(`owner_id`, `option_type`, `option_value`) VALUES ('{}', '{}', '{}'), ('{}', '{}', '{}')", - owner_id, - type.first, - (flag.first == true ? 1 : 0), - owner_id, - type.second, - (flag.second == true ? 1 : 0) - ); + std::vector l = { + Client::booSpawnMessageSay, + Client::booSpawnMessageTell + }; - auto results = database.QueryDatabase(query); - if (!results.Success()) { - return false; - } + auto e = BotOwnerOptionsRepository::NewEntity(); - return true; - } - default: - return false; - } - } - default: - return false; + std::vector v; + + if ( + std::find( + l.begin(), + l.end(), + static_cast(type.first) + ) != l.end() && + std::find( + l.begin(), + l.end(), + static_cast(type.second) + ) != l.end() + ) { + e.owner_id = owner_id; + e.option_type = static_cast(type.first); + e.option_value = static_cast(flag.first ? 1 : 0); + + v.emplace_back(e); + + e.option_type = static_cast(type.second); + e.option_value = static_cast(flag.second ? 1 : 0); + + v.emplace_back(e); + + return BotOwnerOptionsRepository::ReplaceMany(database, v); } + + return false; } -/* Bot owner group functions */ -// added owner ID to this function to fix groups with mulitple players grouped with bots. bool BotDatabase::LoadGroupedBotsByGroupID(const uint32 owner_id, const uint32 group_id, std::list& group_list) { if (!group_id || !owner_id) { return false; } - query = fmt::format( - "SELECT `charid` FROM `group_id` WHERE `groupid` = {} AND `name` IN " - "(SELECT `name` FROM `bot_data` WHERE `owner_id` = {})", - group_id, - owner_id + const auto& l = GroupIdRepository::GetWhere( + database, + fmt::format( + "`groupid` = {} AND `name` IN (SELECT `name` FROM `bot_data` WHERE `owner_id` = {})", + group_id, + owner_id + ) ); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - return false; - } - - if (!results.RowCount()) { + if (l.empty()) { return true; } - for (auto row : results) { - group_list.push_back(Strings::ToUnsignedInt(row[0])); + for (const auto& e : l) { + group_list.push_back(e.charid); } return true; } - -/* Bot heal rotation functions */ bool BotDatabase::LoadHealRotationIDByBotID(const uint32 bot_id, uint32& hr_index) { - if (!bot_id) + if (!bot_id) { return false; + } - query = StringFormat("SELECT `heal_rotation_index` FROM `bot_heal_rotations` WHERE `bot_id` = '%u' LIMIT 1", bot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - if (!results.RowCount()) + const auto& l = BotHealRotationsRepository::GetWhere( + database, + fmt::format( + "`bot_id` = {} LIMIT 1", + bot_id + ) + ); + + if (l.empty()) { return true; + } - auto row = results.begin(); - hr_index = Strings::ToInt(row[0]); + auto e = l.front(); + + hr_index = e.heal_rotation_index; return true; } bool BotDatabase::LoadHealRotation(Bot* hr_member, std::list& member_list, std::list& target_list, bool& load_flag, bool& member_fail, bool& target_fail) { - if (!hr_member) + if (!hr_member) { return false; + } uint32 hr_index = 0; - if (!LoadHealRotationIDByBotID(hr_member->GetBotID(), hr_index)) + + if (!LoadHealRotationIDByBotID(hr_member->GetBotID(), hr_index)) { return false; - if (!hr_index) + } + + if (!hr_index) { return true; + } - if (!hr_member->IsHealRotationMember()) + if (!hr_member->IsHealRotationMember()) { return false; + } - query = StringFormat( - "SELECT " - " `interval`," - " `fast_heals`," - " `adaptive_targeting`," - " `casting_override`," - " `safe_hp_base`," - " `safe_hp_cloth`," - " `safe_hp_leather`," - " `safe_hp_chain`," - " `safe_hp_plate`," - " `critical_hp_base`," - " `critical_hp_cloth`," - " `critical_hp_leather`," - " `critical_hp_chain`," - " `critical_hp_plate`" - " FROM `bot_heal_rotations`" - " WHERE `heal_rotation_index` = '%u'" - " LIMIT 1", - hr_index - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) + const auto& e = BotHealRotationsRepository::FindOne(database, hr_index); + + if (!e.heal_rotation_index) { return false; - if (!results.RowCount()) - return true; + } - auto row = results.begin(); - (*hr_member->MemberOfHealRotation())->SetIntervalS((uint32)Strings::ToInt(row[0])); - (*hr_member->MemberOfHealRotation())->SetFastHeals((bool)Strings::ToInt(row[1])); - (*hr_member->MemberOfHealRotation())->SetAdaptiveTargeting((bool)Strings::ToInt(row[2])); - (*hr_member->MemberOfHealRotation())->SetCastingOverride((bool)Strings::ToInt(row[3])); - (*hr_member->MemberOfHealRotation())->SetArmorTypeSafeHPRatio(ARMOR_TYPE_UNKNOWN, Strings::ToFloat(row[4])); - (*hr_member->MemberOfHealRotation())->SetArmorTypeSafeHPRatio(ARMOR_TYPE_CLOTH, Strings::ToFloat(row[5])); - (*hr_member->MemberOfHealRotation())->SetArmorTypeSafeHPRatio(ARMOR_TYPE_LEATHER, Strings::ToFloat(row[6])); - (*hr_member->MemberOfHealRotation())->SetArmorTypeSafeHPRatio(ARMOR_TYPE_CHAIN, Strings::ToFloat(row[7])); - (*hr_member->MemberOfHealRotation())->SetArmorTypeSafeHPRatio(ARMOR_TYPE_PLATE, Strings::ToFloat(row[8])); - (*hr_member->MemberOfHealRotation())->SetArmorTypeCriticalHPRatio(ARMOR_TYPE_UNKNOWN, Strings::ToFloat(row[9])); - (*hr_member->MemberOfHealRotation())->SetArmorTypeCriticalHPRatio(ARMOR_TYPE_CLOTH, Strings::ToFloat(row[10])); - (*hr_member->MemberOfHealRotation())->SetArmorTypeCriticalHPRatio(ARMOR_TYPE_LEATHER, Strings::ToFloat(row[11])); - (*hr_member->MemberOfHealRotation())->SetArmorTypeCriticalHPRatio(ARMOR_TYPE_CHAIN, Strings::ToFloat(row[12])); - (*hr_member->MemberOfHealRotation())->SetArmorTypeCriticalHPRatio(ARMOR_TYPE_PLATE, Strings::ToFloat(row[13])); + auto m = (*hr_member->MemberOfHealRotation()); + + m->SetIntervalS(e.interval_); + m->SetFastHeals(e.fast_heals); + m->SetAdaptiveTargeting(e.adaptive_targeting); + m->SetCastingOverride(e.casting_override); + + m->SetArmorTypeSafeHPRatio(ARMOR_TYPE_UNKNOWN, e.safe_hp_base); + m->SetArmorTypeSafeHPRatio(ARMOR_TYPE_CLOTH, e.safe_hp_cloth); + m->SetArmorTypeSafeHPRatio(ARMOR_TYPE_LEATHER, e.safe_hp_leather); + m->SetArmorTypeSafeHPRatio(ARMOR_TYPE_CHAIN, e.safe_hp_chain); + m->SetArmorTypeSafeHPRatio(ARMOR_TYPE_PLATE, e.safe_hp_plate); + + m->SetArmorTypeCriticalHPRatio(ARMOR_TYPE_UNKNOWN, e.critical_hp_base); + m->SetArmorTypeCriticalHPRatio(ARMOR_TYPE_CLOTH, e.critical_hp_cloth); + m->SetArmorTypeCriticalHPRatio(ARMOR_TYPE_LEATHER, e.critical_hp_leather); + m->SetArmorTypeCriticalHPRatio(ARMOR_TYPE_CHAIN, e.critical_hp_chain); + m->SetArmorTypeCriticalHPRatio(ARMOR_TYPE_PLATE, e.critical_hp_plate); load_flag = true; - if (!LoadHealRotationMembers(hr_index, member_list)) + if (!LoadHealRotationMembers(hr_index, member_list)) { member_fail = true; + } - if (!LoadHealRotationTargets(hr_index, target_list)) + if (!LoadHealRotationTargets(hr_index, target_list)) { target_fail = true; + } return true; } bool BotDatabase::LoadHealRotationMembers(const uint32 hr_index, std::list& member_list) { - if (!hr_index) + if (!hr_index) { return false; + } - query = StringFormat("SELECT `bot_id` FROM `bot_heal_rotation_members` WHERE `heal_rotation_index` = '%u'", hr_index); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - if (!results.RowCount()) + const auto& l = BotHealRotationMembersRepository::GetWhere( + database, + fmt::format( + "`heal_rotation_index` = {}", + hr_index + ) + ); + + if (l.empty()) { return true; + } - for (auto row : results) { - if (row[0]) - member_list.push_back(Strings::ToInt(row[0])); + for (const auto& e : l) { + member_list.push_back(e.bot_id); } return true; @@ -2366,19 +2047,24 @@ bool BotDatabase::LoadHealRotationMembers(const uint32 hr_index, std::list& target_list) { - if (!hr_index) + if (!hr_index) { return false; + } - query = StringFormat("SELECT `target_name` FROM `bot_heal_rotation_targets` WHERE `heal_rotation_index` = '%u'", hr_index); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - if (!results.RowCount()) + const auto& l = BotHealRotationTargetsRepository::GetWhere( + database, + fmt::format( + "`heal_rotation_index` = {}", + hr_index + ) + ); + + if (l.empty()) { return true; + } - for (auto row : results) { - if (row[0]) - target_list.push_back(row[0]); + for (const auto& e : l) { + target_list.push_back(e.target_name); } return true; @@ -2386,100 +2072,88 @@ bool BotDatabase::LoadHealRotationTargets(const uint32 hr_index, std::listGetBotID()) || + !hr_member->IsHealRotationMember() + ) { return false; - - if (!DeleteHealRotation(hr_member->GetBotID())) - return false; - - if (!hr_member->IsHealRotationMember()) - return false; - - query = StringFormat( - "INSERT INTO `bot_heal_rotations` (" - "`bot_id`," - " `interval`," - " `fast_heals`," - " `adaptive_targeting`," - " `casting_override`," - " `safe_hp_base`," - " `safe_hp_cloth`," - " `safe_hp_leather`," - " `safe_hp_chain`," - " `safe_hp_plate`," - " `critical_hp_base`," - " `critical_hp_cloth`," - " `critical_hp_leather`," - " `critical_hp_chain`," - " `critical_hp_plate`" - ")" - " VALUES (" - "'%u'," - " '%u'," - " '%u'," - " '%u'," - " '%u'," - " '%f'," - " '%f'," - " '%f'," - " '%f'," - " '%f'," - " '%f'," - " '%f'," - " '%f'," - " '%f'," - " '%f'" - ")", - hr_member->GetBotID(), - ((*hr_member->MemberOfHealRotation())->IntervalS()), - ((*hr_member->MemberOfHealRotation())->FastHeals()), - ((*hr_member->MemberOfHealRotation())->AdaptiveTargeting()), - ((*hr_member->MemberOfHealRotation())->CastingOverride()), - ((*hr_member->MemberOfHealRotation())->ArmorTypeSafeHPRatio(ARMOR_TYPE_UNKNOWN)), - ((*hr_member->MemberOfHealRotation())->ArmorTypeSafeHPRatio(ARMOR_TYPE_CLOTH)), - ((*hr_member->MemberOfHealRotation())->ArmorTypeSafeHPRatio(ARMOR_TYPE_LEATHER)), - ((*hr_member->MemberOfHealRotation())->ArmorTypeSafeHPRatio(ARMOR_TYPE_CHAIN)), - ((*hr_member->MemberOfHealRotation())->ArmorTypeSafeHPRatio(ARMOR_TYPE_PLATE)), - ((*hr_member->MemberOfHealRotation())->ArmorTypeCriticalHPRatio(ARMOR_TYPE_UNKNOWN)), - ((*hr_member->MemberOfHealRotation())->ArmorTypeCriticalHPRatio(ARMOR_TYPE_CLOTH)), - ((*hr_member->MemberOfHealRotation())->ArmorTypeCriticalHPRatio(ARMOR_TYPE_LEATHER)), - ((*hr_member->MemberOfHealRotation())->ArmorTypeCriticalHPRatio(ARMOR_TYPE_CHAIN)), - ((*hr_member->MemberOfHealRotation())->ArmorTypeCriticalHPRatio(ARMOR_TYPE_PLATE)) - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; - - uint32 hr_index = results.LastInsertedID(); - if (!hr_index) - return false; - - std::list* member_list = (*hr_member->MemberOfHealRotation())->MemberList(); - - for (auto member_iter : *member_list) { - if (!member_iter) - continue; - - query = StringFormat("INSERT INTO `bot_heal_rotation_members` (`heal_rotation_index`, `bot_id`) VALUES ('%u', '%u')", hr_index, member_iter->GetBotID()); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - member_fail = true; - break; - } } - std::list* target_list = (*hr_member->MemberOfHealRotation())->TargetList(); + auto m = (*hr_member->MemberOfHealRotation()); - for (auto target_iter : *target_list) { - if (!target_iter) + auto e = BotHealRotationsRepository::NewEntity(); + + e.bot_id = hr_member->GetBotID(); + e.interval_ = m->IntervalS(); + e.fast_heals = m->FastHeals(); + e.adaptive_targeting = m->AdaptiveTargeting(); + e.casting_override = m->CastingOverride(); + + e.safe_hp_base = m->ArmorTypeSafeHPRatio(ARMOR_TYPE_UNKNOWN); + e.safe_hp_cloth = m->ArmorTypeSafeHPRatio(ARMOR_TYPE_CLOTH); + e.safe_hp_leather = m->ArmorTypeSafeHPRatio(ARMOR_TYPE_LEATHER); + e.safe_hp_chain = m->ArmorTypeSafeHPRatio(ARMOR_TYPE_CHAIN); + e.safe_hp_plate = m->ArmorTypeSafeHPRatio(ARMOR_TYPE_PLATE); + + e.critical_hp_base = m->ArmorTypeCriticalHPRatio(ARMOR_TYPE_UNKNOWN); + e.critical_hp_cloth = m->ArmorTypeCriticalHPRatio(ARMOR_TYPE_CLOTH); + e.critical_hp_leather = m->ArmorTypeCriticalHPRatio(ARMOR_TYPE_LEATHER); + e.critical_hp_chain = m->ArmorTypeCriticalHPRatio(ARMOR_TYPE_CHAIN); + e.critical_hp_plate = m->ArmorTypeCriticalHPRatio(ARMOR_TYPE_PLATE); + + e = BotHealRotationsRepository::InsertOne(database, e); + + if (!e.heal_rotation_index) { + return false; + } + + std::list* ml = m->MemberList(); + + auto re = BotHealRotationMembersRepository::NewEntity(); + + re.heal_rotation_index = e.heal_rotation_index; + + std::vector rv; + + for (auto m : *ml) { + if (!m) { continue; - - query = StringFormat("INSERT INTO `bot_heal_rotation_targets` (`heal_rotation_index`, `target_name`) VALUES ('%u', '%s')", hr_index, target_iter->GetCleanName()); - auto results = database.QueryDatabase(query); - if (!results.Success()) { - target_fail = true; - break; } + + re.bot_id = m->GetBotID(); + + rv.emplace_back(re); + } + + const int inserted_members = BotHealRotationMembersRepository::InsertMany(database, rv); + + if (!inserted_members) { + member_fail = true; + } + + std::list* tl = m->TargetList(); + + auto te = BotHealRotationTargetsRepository::NewEntity(); + + te.heal_rotation_index = e.heal_rotation_index; + + std::vector tv; + + for (auto m : *tl) { + if (!m) { + continue; + } + + te.target_name = m->GetCleanName(); + + tv.emplace_back(te); + } + + const int inserted_targets = BotHealRotationTargetsRepository::InsertMany(database, tv); + + if (!inserted_targets) { + target_fail = true; } return true; @@ -2487,48 +2161,67 @@ bool BotDatabase::SaveHealRotation(Bot* hr_member, bool& member_fail, bool& targ bool BotDatabase::DeleteHealRotation(const uint32 creator_id) { - if (!creator_id) + if (!creator_id) { return false; + } uint32 hr_index = 0; - if (!LoadHealRotationIDByBotID(creator_id, hr_index)) + + if (!LoadHealRotationIDByBotID(creator_id, hr_index)) { return false; - if (!hr_index) + } + + if (!hr_index) { return true; + } - query = StringFormat("DELETE FROM `bot_heal_rotation_targets` WHERE `heal_rotation_index` = '%u'", hr_index); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; + BotHealRotationTargetsRepository::DeleteWhere( + database, + fmt::format( + "`heal_rotation_index` = {}", + hr_index + ) + ); - query = StringFormat("DELETE FROM `bot_heal_rotation_members` WHERE `heal_rotation_index` = '%u'", hr_index); - results = database.QueryDatabase(query); - if (!results.Success()) - return false; + BotHealRotationMembersRepository::DeleteWhere( + database, + fmt::format( + "`heal_rotation_index` = {}", + hr_index + ) + ); - query = StringFormat("DELETE FROM `bot_heal_rotations` WHERE `heal_rotation_index` = '%u'", hr_index); - results = database.QueryDatabase(query); - if (!results.Success()) - return false; + BotHealRotationsRepository::DeleteWhere( + database, + fmt::format( + "`heal_rotation_index` = {}", + hr_index + ) + ); return true; } bool BotDatabase::DeleteAllHealRotations(const uint32 owner_id) { - if (!owner_id) + if (!owner_id) { return false; + } - query = StringFormat("SELECT `bot_id` FROM `bot_heal_rotations` WHERE `bot_id` IN (SELECT `bot_id` FROM `bot_data` WHERE `owner_id` = '%u')", owner_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) - return false; + const auto& l = BotHealRotationsRepository::GetWhere( + database, + fmt::format( + "`bot_id` IN (SELECT `bot_id` FROM `bot_data` WHERE `owner_id` = {})", + owner_id + ) + ); - for (auto row : results) { - if (!row[0]) - continue; + if (l.empty()) { + return true; + } - DeleteHealRotation(Strings::ToInt(row[0])); + for (const auto& e : l) { + DeleteHealRotation(e.bot_id); } return true; @@ -2538,31 +2231,23 @@ bool BotDatabase::DeleteAllHealRotations(const uint32 owner_id) /* Bot miscellaneous functions */ uint8 BotDatabase::GetSpellCastingChance(uint8 spell_type_index, uint8 class_index, uint8 stance_index, uint8 conditional_index) // class_index is 0-based { - if (spell_type_index >= Bot::SPELL_TYPE_COUNT) - return 0; - if (class_index >= Class::PLAYER_CLASS_COUNT) - return 0; - if (stance_index >= EQ::constants::STANCE_TYPE_COUNT) - return 0; - if (conditional_index >= cntHSND) + if ( + spell_type_index >= Bot::SPELL_TYPE_COUNT || + class_index >= Class::PLAYER_CLASS_COUNT || + stance_index >= EQ::constants::STANCE_TYPE_COUNT || + conditional_index >= cntHSND + ) { return 0; + } return Bot::spell_casting_chances[spell_type_index][class_index][stance_index][conditional_index]; } -uint16 BotDatabase::GetRaceClassBitmask(uint16 bot_race) +uint32 BotDatabase::GetRaceClassBitmask(uint32 bot_race) { - std::string query = fmt::format( - "SELECT `classes` FROM `bot_create_combinations` WHERE `race` = {}", - bot_race - ); - auto results = database.QueryDatabase(query); - uint16 classes = 0; - if (results.RowCount() == 1) { - auto row = results.begin(); - classes = Strings::ToInt(row[0]); - } - return classes; + const auto& e = BotCreateCombinationsRepository::FindOne(database, bot_race); + + return e.race ? e.classes : 0; } bool BotDatabase::SaveExpansionBitmask(const uint32 bot_id, const int expansion_bitmask) @@ -2571,20 +2256,15 @@ bool BotDatabase::SaveExpansionBitmask(const uint32 bot_id, const int expansion_ return false; } - query = fmt::format( - "UPDATE `bot_data` " - "SET `expansion_bitmask` = {} " - "WHERE `bot_id` = {}", - expansion_bitmask, - bot_id - ); + auto e = BotDataRepository::FindOne(database, bot_id); - auto results = database.QueryDatabase(query); - if (!results.Success()) { + if (!e.bot_id) { return false; } - return true; + e.expansion_bitmask = expansion_bitmask; + + return BotDataRepository::UpdateOne(database, e); } bool BotDatabase::SaveEnforceSpellSetting(const uint32 bot_id, const bool enforce_spell_setting) @@ -2593,19 +2273,15 @@ bool BotDatabase::SaveEnforceSpellSetting(const uint32 bot_id, const bool enforc return false; } - query = fmt::format( - "UPDATE `bot_data`" - "SET `enforce_spell_settings` = {} " - "WHERE `bot_id` = {}", - (enforce_spell_setting ? 1 : 0), - bot_id - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) { + auto e = BotDataRepository::FindOne(database, bot_id); + + if (!e.bot_id) { return false; } - return true; + e.enforce_spell_settings = enforce_spell_setting ? 1 : 0; + + return BotDataRepository::UpdateOne(database, e); } bool BotDatabase::SaveBotArcherSetting(const uint32 bot_id, const bool bot_archer_setting) @@ -2613,133 +2289,31 @@ bool BotDatabase::SaveBotArcherSetting(const uint32 bot_id, const bool bot_arche if (!bot_id) { return false; } - query = fmt::format( - "UPDATE `bot_data`" - "SET `archery_setting` = {} " - "WHERE `bot_id` = {}", - (bot_archer_setting ? 1 : 0), - bot_id - ); - auto results = database.QueryDatabase(query); - if (!results.Success()) { + + auto e = BotDataRepository::FindOne(database, bot_id); + + if (!e.bot_id) { return false; } - return true; + + e.archery_setting = bot_archer_setting ? 1 : 0; + + return BotDataRepository::UpdateOne(database, e); } -std::string BotDatabase::GetBotNameByID(const uint32 bot_id) +bool BotDatabase::SaveBotCasterRange(const uint32 bot_id, const uint32 bot_caster_range_value) { - if (!bot_id) { - return nullptr; - } - query = fmt::format( - "SELECT `name` FROM `bot_data` WHERE `bot_id` = {}", - bot_id - ); - auto results = database.QueryDatabase(query); - - if (!results.Success()) { - return nullptr; - } - - if (results.RowCount() == 1) { - auto row = results.begin(); - return row[0]; - } - - return nullptr; -} - -bool BotDatabase::SaveBotCasterRange(const uint32 owner_id, const uint32 bot_id, const uint32 bot_caster_range_value) -{ - if (!owner_id || !bot_id) { return false; } - query = fmt::format( - "UPDATE `bot_data`" - " SET `caster_range` = '{}'" - " WHERE `owner_id` = '{}'" - " AND `bot_id` = '{}'", - bot_caster_range_value, - owner_id, - bot_id - ); - auto results = database.QueryDatabase(query); + auto e = BotDataRepository::FindOne(database, bot_id); - if (!results.Success()) { + if (!e.bot_id) { return false; } - return true; + e.caster_range = bot_caster_range_value; + + return BotDataRepository::UpdateOne(database, e); } - -/* fail::Bot functions */ -const char* BotDatabase::fail::LoadBotsList() { return "Failed to bots list"; } -const char* BotDatabase::fail::LoadOwnerID() { return "Failed to load owner ID"; } -const char* BotDatabase::fail::LoadBotID() { return "Failed to load bot ID"; } -const char* BotDatabase::fail::LoadBot() { return "Failed to load bot"; } -const char* BotDatabase::fail::SaveNewBot() { return "Failed to save new bot"; } -const char* BotDatabase::fail::SaveBot() { return "Failed to save bot"; } -const char* BotDatabase::fail::DeleteBot() { return "Failed to delete bot"; } -const char* BotDatabase::fail::LoadBuffs() { return "Failed to load buffs"; } -const char* BotDatabase::fail::SaveBuffs() { return "Failed to save buffs"; } -const char* BotDatabase::fail::DeleteBuffs() { return "Failed to delete buffs"; } -const char* BotDatabase::fail::DeleteStance() { return "Failed to delete stance"; } -const char* BotDatabase::fail::LoadTimers() { return "Failed to load timers"; } -const char* BotDatabase::fail::SaveTimers() { return "Failed to save timers"; } -const char* BotDatabase::fail::DeleteTimers() { return "Failed to delete timers"; } - -/* fail::Bot inventory functions */ -const char* BotDatabase::fail::QueryInventoryCount() { return "Failed to query inventory count"; } -const char* BotDatabase::fail::LoadItems() { return "Failed to load items"; } -const char* BotDatabase::fail::SaveItems() { return "Failed to save items"; } -const char* BotDatabase::fail::DeleteItems() { return "Failed to delete items"; } -const char* BotDatabase::fail::SaveItemBySlot() { return "Failed to save item by slot"; } -const char* BotDatabase::fail::DeleteItemBySlot() { return "Failed to delete item by slot"; } -const char* BotDatabase::fail::LoadEquipmentColor() { return "Failed to load equipment color"; } -const char* BotDatabase::fail::SaveEquipmentColor() { return "Failed to save equipment color"; } - -/* fail::Bot pet functions */ -const char* BotDatabase::fail::LoadPetIndex() { return "Failed to load pet index"; } -const char* BotDatabase::fail::LoadPetSpellID() { return "Failed to load pet spell ID"; } -const char* BotDatabase::fail::LoadPetStats() { return "Failed to load pet stats"; } -const char* BotDatabase::fail::SavePetStats() { return "Failed to save pet stats"; } -const char* BotDatabase::fail::DeletePetStats() { return "Failed to delete pet stats"; } -const char* BotDatabase::fail::LoadPetBuffs() { return "Failed to load pet buffs"; } -const char* BotDatabase::fail::SavePetBuffs() { return "Failed to save pet buffs"; } -const char* BotDatabase::fail::DeletePetBuffs() { return "Failed to delete pet buffs"; } -const char* BotDatabase::fail::LoadPetItems() { return "Failed to load pet items"; } -const char* BotDatabase::fail::SavePetItems() { return "Failed to save pet items"; } -const char* BotDatabase::fail::DeletePetItems() { return "Failed to delete pet items"; } - -/* fail::Bot command functions */ -const char* BotDatabase::fail::LoadInspectMessage() { return "Failed to load inspect message"; } -const char* BotDatabase::fail::SaveInspectMessage() { return "Failed to save inspect message"; } -const char* BotDatabase::fail::DeleteInspectMessage() { return "Failed to delete inspect message"; } -const char* BotDatabase::fail::SaveAllInspectMessages() { return "Failed to save all inspect messages"; } -const char* BotDatabase::fail::DeleteAllInspectMessages() { return "Failed to delete all inspect messages"; } -const char* BotDatabase::fail::SaveAllArmorColorBySlot() { return "Failed to save all armor color by slot"; } -const char* BotDatabase::fail::SaveAllArmorColors() { return "Failed to save all armor colors"; } -const char* BotDatabase::fail::SaveHelmAppearance() { return "Failed to save helm appearance"; } -const char* BotDatabase::fail::SaveAllHelmAppearances() { return "Failed to save all helm appearances"; } -const char* BotDatabase::fail::ToggleHelmAppearance() { return "Failed to save toggle helm appearance"; } -const char* BotDatabase::fail::ToggleAllHelmAppearances() { return "Failed to save toggle all helm appearance"; } -const char* BotDatabase::fail::SaveFollowDistance() { return "Failed to save follow distance"; } -const char* BotDatabase::fail::SaveAllFollowDistances() { return "Failed to save all follow distances"; } -const char* BotDatabase::fail::SaveStopMeleeLevel() { return "Failed to save stop melee level"; } -const char* BotDatabase::fail::SaveBotCasterRange() { return "Failed to save caster range"; } - -/* fail::Bot heal rotation functions */ -const char* BotDatabase::fail::LoadHealRotationIDByBotID() { return "Failed to load heal rotation ID by bot ID"; } -const char* BotDatabase::fail::LoadHealRotation() { return "Failed to load heal rotation"; } -const char* BotDatabase::fail::LoadHealRotationMembers() { return "Failed to load heal rotation members"; } -const char* BotDatabase::fail::LoadHealRotationTargets() { return "Failed to load heal rotation targets"; } -const char* BotDatabase::fail::SaveHealRotation() { return "Failed to save heal rotation"; } -const char* BotDatabase::fail::DeleteHealRotation() { return "Failed to delete heal rotation"; } -const char* BotDatabase::fail::DeleteAllHealRotations() { return "Failed to delete all heal rotations"; } - -/* fail::Bot miscellaneous functions */ -const char* BotDatabase::fail::GetBotNameByID() { return "Failed to get bot name by bot ID"; } -const char* BotDatabase::fail::LoadGroupedBotsByGroupID() { return "Failed to load grouped bots by group ID."; } diff --git a/zone/bot_database.h b/zone/bot_database.h index fa4259325..1d02e9e00 100644 --- a/zone/bot_database.h +++ b/zone/bot_database.h @@ -50,31 +50,28 @@ public: /* Bot functions */ bool QueryNameAvailablity(const std::string& bot_name, bool& available_flag); bool QueryBotCount(const uint32 owner_id, int class_id, uint32& bot_count, uint32& bot_class_count); - bool LoadBotsList(const uint32 owner_id, std::list& bots_list, bool ByAccount = false); + bool LoadBotsList(const uint32 owner_id, std::list& bots_list, bool by_account = false); - bool LoadOwnerID(const std::string& bot_name, uint32& owner_id); - bool LoadOwnerID(const uint32 bot_id, uint32& owner_id); uint32 GetOwnerID(const uint32 bot_id); - bool LoadBotID(const uint32 owner_id, const std::string& bot_name, uint32& bot_id); - bool LoadBotID(const uint32 owner_id, const std::string& bot_name, uint32& bot_id, uint8& bot_class_id); + bool LoadBotID(const std::string& bot_name, uint32& bot_id, uint8& bot_class_id); bool LoadBot(const uint32 bot_id, Bot*& loaded_bot); - bool SaveNewBot(Bot* bot_inst, uint32& bot_id); - bool SaveBot(Bot* bot_inst); + bool SaveNewBot(Bot* b, uint32& bot_id); + bool SaveBot(Bot* b); bool DeleteBot(const uint32 bot_id); - bool LoadBuffs(Bot* bot_inst); - bool SaveBuffs(Bot* bot_inst); + bool LoadBuffs(Bot* b); + bool SaveBuffs(Bot* b); bool DeleteBuffs(const uint32 bot_id); bool LoadStance(const uint32 bot_id, int& bot_stance); - bool LoadStance(Bot* bot_inst, bool& stance_flag); + bool LoadStance(Bot* b, bool& stance_flag); bool SaveStance(const uint32 bot_id, const int bot_stance); - bool SaveStance(Bot* bot_inst); + bool SaveStance(Bot* b); bool DeleteStance(const uint32 bot_id); - bool LoadTimers(Bot* bot_inst); - bool SaveTimers(Bot* bot_inst); + bool LoadTimers(Bot* b); + bool SaveTimers(Bot* b); bool DeleteTimers(const uint32 bot_id); @@ -82,17 +79,14 @@ public: bool QueryInventoryCount(const uint32 bot_id, uint32& item_count); bool LoadItems(const uint32 bot_id, EQ::InventoryProfile &inventory_inst); - bool SaveItems(Bot* bot_inst); bool DeleteItems(const uint32 bot_id); bool LoadItemSlots(const uint32 bot_id, std::map& m); - bool LoadItemBySlot(Bot* bot_inst); bool LoadItemBySlot(const uint32 bot_id, const uint32 slot_id, uint32& item_id); - bool SaveItemBySlot(Bot* bot_inst, const uint32 slot_id, const EQ::ItemInstance* item_inst); + bool SaveItemBySlot(Bot* b, const uint32 slot_id, const EQ::ItemInstance* inst); bool DeleteItemBySlot(const uint32 bot_id, const uint32 slot_id); - bool LoadEquipmentColor(const uint32 bot_id, const uint8 material_slot_id, uint32& rgb); - bool SaveEquipmentColor(const uint32 bot_id, const int16 slot_id, const uint32 rgb); + bool SaveEquipmentColor(const uint32 bot_id, const int16 slot_id, const uint32 color); bool SaveExpansionBitmask(const uint32 bot_id, const int expansion_bitmask); bool SaveEnforceSpellSetting(const uint32 bot_id, const bool enforce_spell_setting); @@ -126,19 +120,18 @@ public: bool SaveAllArmorColorBySlot(const uint32 owner_id, const int16 slot_id, const uint32 rgb_value); bool SaveAllArmorColors(const uint32 owner_id, const uint32 rgb_value); - bool SaveHelmAppearance(const uint32 owner_id, const uint32 bot_id, const bool show_flag = true); + bool SaveHelmAppearance(const uint32 bot_id, const bool show_flag = true); bool SaveAllHelmAppearances(const uint32 owner_id, const bool show_flag = true); - bool ToggleHelmAppearance(const uint32 owner_id, const uint32 bot_id); bool ToggleAllHelmAppearances(const uint32 owner_id); - bool SaveFollowDistance(const uint32 owner_id, const uint32 bot_id, const uint32 follow_distance); + bool SaveFollowDistance(const uint32 bot_id, const uint32 follow_distance); bool SaveAllFollowDistances(const uint32 owner_id, const uint32 follow_distance); - bool CreateCloneBot(const uint32 owner_id, const uint32 bot_id, const std::string& clone_name, uint32& clone_id); - bool CreateCloneBotInventory(const uint32 owner_id, const uint32 bot_id, const uint32 clone_id); + bool CreateCloneBot(const uint32 bot_id, const std::string& clone_name, uint32& clone_id); + bool CreateCloneBotInventory(const uint32 bot_id, const uint32 clone_id); - bool SaveStopMeleeLevel(const uint32 owner_id, const uint32 bot_id, const uint8 sml_value); + bool SaveStopMeleeLevel(const uint32 bot_id, const uint8 sml_value); bool SaveBotArcherSetting(const uint32 bot_id, const bool bot_archer_setting); @@ -146,7 +139,7 @@ public: bool SaveOwnerOption(const uint32 owner_id, size_t type, const bool flag); bool SaveOwnerOption(const uint32 owner_id, const std::pair type, const std::pair flag); - bool SaveBotCasterRange(const uint32 owner_id, const uint32 bot_id, const uint32 bot_caster_range_value); + bool SaveBotCasterRange(const uint32 bot_id, const uint32 bot_caster_range_value); /* Bot group functions */ bool LoadGroupedBotsByGroupID(const uint32 owner_id, const uint32 group_id, std::list& group_list); @@ -164,16 +157,12 @@ public: /* Bot miscellaneous functions */ uint8 GetSpellCastingChance(uint8 spell_type_index, uint8 class_index, uint8 stance_index, uint8 conditional_index); - std::string GetBotNameByID(const uint32 bot_id); - uint16 GetRaceClassBitmask(uint16 bot_race); + uint32 GetRaceClassBitmask(uint32 bot_race); class fail { public: /* fail::Bot functions */ - static const char* LoadBotsList(); - static const char* LoadOwnerID(); - static const char* LoadBotID(); static const char* LoadBot(); static const char* SaveNewBot(); static const char* SaveBot(); @@ -189,11 +178,9 @@ public: /* fail::Bot inventory functions */ static const char* QueryInventoryCount(); static const char* LoadItems(); - static const char* SaveItems(); static const char* DeleteItems(); static const char* SaveItemBySlot(); static const char* DeleteItemBySlot(); - static const char* LoadEquipmentColor(); static const char* SaveEquipmentColor(); /* fail::Bot pet functions */ @@ -212,34 +199,23 @@ public: /* fail::Bot command functions */ static const char* LoadInspectMessage(); static const char* SaveInspectMessage(); - static const char* DeleteInspectMessage(); static const char* SaveAllInspectMessages(); - static const char* DeleteAllInspectMessages(); static const char* SaveAllArmorColorBySlot(); static const char* SaveAllArmorColors(); - static const char* SaveHelmAppearance(); static const char* SaveAllHelmAppearances(); - static const char* ToggleHelmAppearance(); static const char* ToggleAllHelmAppearances(); static const char* SaveFollowDistance(); static const char* SaveAllFollowDistances(); static const char* SaveStopMeleeLevel(); static const char* SaveBotCasterRange(); - /* fail::Bot group functions */ - static const char* LoadGroupedBotsByGroupID(); - /* fail::Bot heal rotation functions */ - static const char* LoadHealRotationIDByBotID(); static const char* LoadHealRotation(); static const char* LoadHealRotationMembers(); static const char* LoadHealRotationTargets(); static const char* SaveHealRotation(); static const char* DeleteHealRotation(); static const char* DeleteAllHealRotations(); - - /* fail::Bot miscellaneous functions */ - static const char* GetBotNameByID(); }; private: diff --git a/zone/bot_raid.cpp b/zone/bot_raid.cpp index fe596d1d1..0bcf5cd95 100644 --- a/zone/bot_raid.cpp +++ b/zone/bot_raid.cpp @@ -25,7 +25,7 @@ #include "quest_parser_collection.h" #include "../common/data_verification.h" -std::vector Raid::GetRaidGroupMembers(uint32 gid) +std::vector Raid::GetRaidGroupMembers(uint32 gid) { std::vector raid_group_members; raid_group_members.clear(); @@ -126,9 +126,9 @@ void Raid::HandleOfflineBots(uint32 owner) { } for (const auto& b: bots_list) { - if (IsRaidMember(b.Name)) { + if (IsRaidMember(b.bot_name)) { for (const auto& m: members) { - if (m.is_bot && strcmp(m.member_name, b.Name) == 0) { + if (m.is_bot && strcmp(m.member_name, b.bot_name) == 0) { uint32 gid = GetGroup(m.member_name); SendRaidGroupRemove(m.member_name, gid); RemoveMember(m.member_name); @@ -313,7 +313,7 @@ void Client::SpawnRaidBotsOnConnect(Raid* raid) { if (strlen(m.member_name) != 0) { for (const auto& b: bots_list) { - if (strcmp(m.member_name, b.Name) == 0) { + if (strcmp(m.member_name, b.bot_name) == 0) { std::string buffer = "^spawn "; buffer.append(m.member_name); bot_command_real_dispatch(this, buffer.c_str()); diff --git a/zone/bot_structs.h b/zone/bot_structs.h index ca225f8b4..50e319e9e 100644 --- a/zone/bot_structs.h +++ b/zone/bot_structs.h @@ -24,14 +24,14 @@ #include struct BotsAvailableList { - uint32 ID; - char Name[64]; - uint16 Class; - uint8 Level; - uint16 Race; - uint8 Gender; - char Owner[64]; - uint32 Owner_ID; + uint32 bot_id; + char bot_name[64]; + uint16 class_; + uint8 level; + uint16 race; + uint8 gender; + char owner_name[64]; + uint32 owner_id; }; struct BotSpell {