using System; using System.Collections.Generic; using Npgsql; using WingsAPI.Data.Drops; using WingsAPI.Data.Shops; using WingsEmu.DTOs.Maps; using WingsEmu.DTOs.Recipes; using WingsEmu.DTOs.ServerDatas; using WingsEmu.DTOs.Shops; using WingsEmu.Packets.Enums; namespace WingsEmu.Plugins.BasicImplementations.ServerConfigs.Persistence; public static class ParserDataPostgresReader { public static bool DbFirstEnabled => string.Equals(Environment.GetEnvironmentVariable("DB_FIRST"), "true", StringComparison.OrdinalIgnoreCase); public static bool StrictDbOnlyEnabled => string.Equals(Environment.GetEnvironmentVariable("STRICT_DB_ONLY"), "true", StringComparison.OrdinalIgnoreCase); private static string BuildConnectionString() { string host = Environment.GetEnvironmentVariable("DATABASE_IP") ?? Environment.GetEnvironmentVariable("POSTGRES_DATABASE_IP") ?? "127.0.0.1"; string port = Environment.GetEnvironmentVariable("DATABASE_PORT") ?? Environment.GetEnvironmentVariable("POSTGRES_DATABASE_PORT") ?? "5432"; string db = Environment.GetEnvironmentVariable("DATABASE_NAME") ?? Environment.GetEnvironmentVariable("POSTGRES_DATABASE_NAME") ?? "game"; string user = Environment.GetEnvironmentVariable("DATABASE_USER") ?? Environment.GetEnvironmentVariable("POSTGRES_DATABASE_USER") ?? "postgres"; string pass = Environment.GetEnvironmentVariable("DATABASE_PASSWORD") ?? Environment.GetEnvironmentVariable("POSTGRES_DATABASE_PASSWORD") ?? "postgres"; return $"Host={host};Port={port};Database={db};Username={user};Password={pass}"; } public static List LoadDrops() { var result = new List(); using var conn = new NpgsqlConnection(BuildConnectionString()); conn.Open(); using var cmd = new NpgsqlCommand("SELECT drop_id, amount, drop_chance, item_vnum, map_id, monster_vnum, race_type, race_sub_type FROM drops;", conn); using var reader = cmd.ExecuteReader(); while (reader.Read()) { result.Add(new DropDTO { Id = reader.GetInt32(0), Amount = reader.GetInt32(1), DropChance = reader.GetInt32(2), ItemVNum = reader.GetInt32(3), MapId = reader.IsDBNull(4) ? null : reader.GetInt32(4), MonsterVNum = reader.IsDBNull(5) ? null : reader.GetInt32(5), RaceType = reader.IsDBNull(6) ? null : reader.GetInt32(6), RaceSubType = reader.IsDBNull(7) ? null : reader.GetInt32(7) }); } return result; } public static List LoadMapMonsters() { var result = new List(); using var conn = new NpgsqlConnection(BuildConnectionString()); conn.Open(); using var cmd = new NpgsqlCommand("SELECT map_monster_id, map_id, vnum, map_x, map_y, direction, can_move FROM map_monsters;", conn); using var reader = cmd.ExecuteReader(); while (reader.Read()) { result.Add(new MapMonsterDTO { Id = reader.GetInt32(0), MapId = reader.GetInt32(1), MonsterVNum = reader.GetInt32(2), MapX = reader.GetInt16(3), MapY = reader.GetInt16(4), Direction = reader.IsDBNull(5) ? (byte)0 : reader.GetByte(5), IsMoving = !reader.IsDBNull(6) && reader.GetBoolean(6) }); } return result; } public static List LoadMapNpcs() { var result = new List(); using var conn = new NpgsqlConnection(BuildConnectionString()); conn.Open(); using var cmd = new NpgsqlCommand("SELECT map_npc_id, map_id, vnum, pos_x, pos_y, effect_vnum, effect_delay, dialog_id, direction_facing FROM map_npcs;", conn); using var reader = cmd.ExecuteReader(); while (reader.Read()) { result.Add(new MapNpcDTO { Id = reader.GetInt32(0), MapId = reader.GetInt32(1), NpcVNum = reader.GetInt32(2), MapX = reader.GetInt16(3), MapY = reader.GetInt16(4), Effect = reader.IsDBNull(5) ? (short)0 : reader.GetInt16(5), EffectDelay = reader.IsDBNull(6) ? (short)0 : reader.GetInt16(6), Dialog = reader.IsDBNull(7) ? (short)0 : reader.GetInt16(7), Direction = reader.IsDBNull(8) ? (byte)0 : reader.GetByte(8) }); } return result; } public static List LoadShops() { var shops = new Dictionary(); using var conn = new NpgsqlConnection(BuildConnectionString()); conn.Open(); using (var cmd = new NpgsqlCommand("SELECT map_npc_id, menu_type, shop_type, name FROM shops;", conn)) using (var reader = cmd.ExecuteReader()) { while (reader.Read()) { int mapNpcId = reader.GetInt32(0); shops[mapNpcId] = new ShopDTO { MapNpcId = mapNpcId, MenuType = (byte)reader.GetInt32(1), ShopType = (byte)reader.GetInt32(2), Name = reader.IsDBNull(3) ? null : reader.GetString(3), Items = new List(), Skills = new List() }; } } using (var cmd = new NpgsqlCommand("SELECT map_npc_id, slot, color, item_vnum, rare, type, upgrade, price FROM shop_items;", conn)) using (var reader = cmd.ExecuteReader()) { while (reader.Read()) { int mapNpcId = reader.GetInt32(0); if (!shops.TryGetValue(mapNpcId, out ShopDTO shop)) { continue; } shop.Items ??= new List(); shop.Items.Add(new ShopItemDTO { Slot = reader.GetInt16(1), Color = reader.GetByte(2), ItemVNum = reader.GetInt32(3), Rare = reader.GetInt16(4), Type = reader.GetByte(5), Upgrade = reader.GetByte(6), Price = reader.IsDBNull(7) ? null : reader.GetInt32(7) }); } } using (var cmd = new NpgsqlCommand("SELECT map_npc_id, skill_vnum, slot, type FROM shop_skills;", conn)) using (var reader = cmd.ExecuteReader()) { while (reader.Read()) { int mapNpcId = reader.GetInt32(0); if (!shops.TryGetValue(mapNpcId, out ShopDTO shop)) { continue; } shop.Skills ??= new List(); shop.Skills.Add(new ShopSkillDTO { SkillVNum = reader.GetInt16(1), Slot = reader.GetInt16(2), Type = reader.GetByte(3) }); } } return new List(shops.Values); } public static List LoadRecipes() { var recipes = new Dictionary(); using var conn = new NpgsqlConnection(BuildConnectionString()); conn.Open(); using (var cmd = new NpgsqlCommand("SELECT recipe_id, amount, producer_map_npc_id, produced_item_vnum, producer_item_vnum, producer_npc_vnum FROM recipes;", conn)) using (var reader = cmd.ExecuteReader()) { while (reader.Read()) { int recipeId = reader.GetInt32(0); recipes[recipeId] = new RecipeDTO { Id = recipeId, Amount = reader.GetInt32(1), ProducerMapNpcId = reader.IsDBNull(2) ? null : reader.GetInt32(2), ProducedItemVnum = reader.GetInt32(3), ProducerItemVnum = reader.IsDBNull(4) ? null : reader.GetInt32(4), ProducerNpcVnum = reader.IsDBNull(5) ? null : reader.GetInt32(5), Items = new List() }; } } using (var cmd = new NpgsqlCommand("SELECT recipe_id, slot, item_vnum, amount FROM recipe_items;", conn)) using (var reader = cmd.ExecuteReader()) { while (reader.Read()) { int recipeId = reader.GetInt32(0); if (!recipes.TryGetValue(recipeId, out RecipeDTO recipe)) { continue; } recipe.Items ??= new List(); recipe.Items.Add(new RecipeItemDTO { Slot = reader.GetInt16(1), ItemVNum = reader.GetInt16(2), Amount = reader.GetInt16(3) }); } } return new List(recipes.Values); } public static List LoadTeleporters() { var result = new List(); using var conn = new NpgsqlConnection(BuildConnectionString()); conn.Open(); using var cmd = new NpgsqlCommand("SELECT teleporter_id, idx, type, map_id, map_npc_id, map_x, map_y FROM map_teleporters;", conn); using var reader = cmd.ExecuteReader(); while (reader.Read()) { result.Add(new TeleporterDTO { Id = reader.GetInt32(0), Index = reader.GetInt16(1), Type = (TeleporterType)reader.GetInt32(2), MapId = reader.GetInt32(3), MapNpcId = reader.GetInt32(4), MapX = reader.GetInt16(5), MapY = reader.GetInt16(6) }); } return result; } public static List LoadItemBoxes() { var boxes = new Dictionary(); using var conn = new NpgsqlConnection(BuildConnectionString()); conn.Open(); using (var cmd = new NpgsqlCommand("SELECT item_vnum, box_type, min_rewards, max_rewards, shows_raid_panel FROM item_boxes;", conn)) using (var reader = cmd.ExecuteReader()) { while (reader.Read()) { int itemVnum = reader.GetInt32(0); boxes[itemVnum] = new ItemBoxDto { Id = itemVnum, ItemBoxType = (ItemBoxType)reader.GetInt32(1), MinimumRewards = reader.IsDBNull(2) ? null : reader.GetInt32(2), MaximumRewards = reader.IsDBNull(3) ? null : reader.GetInt32(3), ShowsRaidBoxPanelOnOpen = !reader.IsDBNull(4) && reader.GetBoolean(4), Items = new List() }; } } using (var cmd = new NpgsqlCommand("SELECT item_vnum, probability, min_original_rare, max_original_rare, generated_amount, generated_vnum, generated_random_rarity, generated_upgrade FROM item_box_items;", conn)) using (var reader = cmd.ExecuteReader()) { while (reader.Read()) { int itemVnum = reader.GetInt32(0); if (!boxes.TryGetValue(itemVnum, out ItemBoxDto box)) { continue; } box.Items ??= new List(); box.Items.Add(new ItemBoxItemDto { Probability = reader.GetInt16(1), MinimumOriginalItemRare = reader.GetInt16(2), MaximumOriginalItemRare = reader.GetInt16(3), ItemGeneratedAmount = reader.GetInt16(4), ItemGeneratedVNum = reader.GetInt32(5), ItemGeneratedRandomRarity = !reader.IsDBNull(6) && reader.GetBoolean(6), ItemGeneratedUpgrade = reader.GetByte(7) }); } } return new List(boxes.Values); } public static List LoadServerMaps() { var maps = new Dictionary(); using var conn = new NpgsqlConnection(BuildConnectionString()); conn.Open(); using (var cmd = new NpgsqlCommand("SELECT map_id, map_vnum, map_name_id, map_music_id FROM server_maps;", conn)) using (var reader = cmd.ExecuteReader()) { while (reader.Read()) { int mapId = reader.GetInt32(0); maps[mapId] = new ServerMapDto { Id = mapId, MapVnum = reader.GetInt32(1), NameId = reader.GetInt32(2), MusicId = reader.GetInt32(3), Flags = new List() }; } } using (var cmd = new NpgsqlCommand("SELECT map_id, flag FROM server_map_flags;", conn)) using (var reader = cmd.ExecuteReader()) { while (reader.Read()) { int mapId = reader.GetInt32(0); if (!maps.TryGetValue(mapId, out ServerMapDto map)) { continue; } string flag = reader.GetString(1); if (Enum.TryParse(flag, out MapFlags parsed)) { map.Flags ??= new List(); map.Flags.Add(parsed); } } } return new List(maps.Values); } public static List LoadMapPortals() { var result = new List(); using var conn = new NpgsqlConnection(BuildConnectionString()); conn.Open(); using var cmd = new NpgsqlCommand("SELECT destination_map_id, destination_map_x, destination_map_y, source_map_id, source_map_x, source_map_y, type FROM map_portals;", conn); using var reader = cmd.ExecuteReader(); while (reader.Read()) { result.Add(new PortalDTO { DestinationMapId = reader.GetInt32(0), DestinationX = reader.GetInt16(1), DestinationY = reader.GetInt16(2), SourceMapId = reader.GetInt32(3), SourceX = reader.GetInt16(4), SourceY = reader.GetInt16(5), Type = reader.GetInt16(6), IsDisabled = false }); } return result; } }