using CounterStrikeSharp.API.Core;
using CounterStrikeSharp.API.Core.Capabilities;
using CounterStrikeSharp.API.Modules.Entities;
using Dapper;
using Microsoft.Extensions.Logging;
using MySqlConnector;
using VipCoreApi;

namespace VIP_SkinChecker;

public class Config
{
    public int ServerId { get; set; }

    public Connection Connection { get; init; } = new()
    {
        Host = "HOST",
        Database = "DATABASENAME",
        User = "USER",
        Password = "PASSWORD",
        Port = 3306
    };

    public Dictionary<string, List<int>> Groups { get; set; } = new()
    {
        ["LITE"] =
        [
            1240, 789, 1016, 84, 159, 230, 732, 38, 694, 1167, 607, 1227, 532, 381, 48,
            964, 179, 272, 248, 839, 520, 555,
            501, 668, 1044, 168, 749, 1081, 162, 813, 125, 358, 907,
            709, 1064, 350, 435, 325, 543, 268, 687,
            396, 447, 978, 249, 220, 625, 153, 1156, 261,
            1050, 841, 757, 603, 469, 470, 273, 37, 347, 328, 232, 397,
            595, 1145, 1232,
            885, 795, 300, 341, 1035, 226, 656,
            494, 546, 647, 807, 972, 1013, 83, 1071, 379,
            519, 287, 613, 955, 686, 61, 39, 1151,
            251, 1058, 975, 424, 838, 84, 718, 584,
            670, 554, 868, 956, 989,
            1129, 806, 712, 628, 438,
            1045, 1229, 1025, 965, 284, 310, 812, 742, 651, 402, 188, 337, 44,
            846, 915, 974, 800, 1061,
            593, 20, 1233, 1154, 228, 1250, 669, 759,
            436, 704, 851, 688, 916, 990, 1003, 652,
            1163, 500, 893, 752, 719, 213, 536,
            508, 884, 349, 13, 306, 1125,
            953, 83, 596, 405, 390, 1160,
            1135, 1021, 654, 821, 689, 521, 314, 557,
            248, 987, 634, 746, 716, 699, 263, 356, 214, 1247,
            1148, 648, 902, 496,
            698, 483, 1043, 514,
            922, 1031, 60, 637, 1136, 290, 318, 817, 183,
            71, 485, 667, 894, 951, 246, 1055,
            1002, 906, 1093, 510, 530, 464, 274, 44, 1168,
            1165, 187, 1097, 384, 926, 471, 480, 164,
            189, 440, 1223, 1130, 60, 631, 254, 383,
            305, 583, 727, 758, 779, 823, 886,
            1092, 999, 529, 477, 371, 288, 260, 194,
            612, 196, 954,
            1094, 39, 867, 482, 61, 679, 262,
            846, 915, 974, 800, 1061,
            703, 787, 608, 431, 961, 1072, 1089, 39, 535
        ],
        ["GOLD"] =
        [
            1240, 789, 1016, 84, 159, 230, 732, 38, 694, 1167, 607, 1227, 532, 381, 48,
            964, 179, 272, 248, 839, 520, 555,
            501, 668, 1044, 168, 749, 1081, 162, 813, 125, 358, 907,
            709, 1064, 350, 435, 325, 543, 268, 687,
            396, 447, 978, 249, 220, 625, 153, 1156, 261,
            1050, 841, 757, 603, 469, 470, 273, 37, 347, 328, 232, 397,
            595, 1145, 1232,
            885, 795, 300, 341, 1035, 226, 656,
            494, 546, 647, 807, 972, 1013, 83, 1071, 379,
            519, 287, 613, 955, 686, 61, 39, 1151,
            251, 1058, 975, 424, 838, 84, 718, 584,
            670, 554, 868, 956, 989,
            1129, 806, 712, 628, 438,
            1045, 1229, 1025, 965, 284, 310, 812, 742, 651, 402, 188, 337, 44,
            846, 915, 974, 800, 1061,
            593, 20, 1233, 1154, 228, 1250, 669, 759,
            436, 704, 851, 688, 916, 990, 1003, 652,
            1163, 500, 893, 752, 719, 213, 536,
            508, 884, 349, 13, 306, 1125,
            953, 83, 596, 405, 390, 1160,
            1135, 1021, 654, 821, 689, 521, 314, 557,
            248, 987, 634, 746, 716, 699, 263, 356, 214, 1247,
            1148, 648, 902, 496,
            698, 483, 1043, 514,
            922, 1031, 60, 637, 1136, 290, 318, 817, 183,
            71, 485, 667, 894, 951, 246, 1055,
            1002, 906, 1093, 510, 530, 464, 274, 44, 1168,
            1165, 187, 1097, 384, 926, 471, 480, 164,
            189, 440, 1223, 1130, 60, 631, 254, 383,
            305, 583, 727, 758, 779, 823, 886,
            1092, 999, 529, 477, 371, 288, 260, 194,
            612, 196, 954,
            1094, 39, 867, 482, 61, 679, 262,
            846, 915, 974, 800, 1061,
            703, 787, 608, 431, 961, 1072, 1089, 39, 535,

            // GOLD
            1100, 437, 963, 353, 988, 1119, 1120, 1121, 1122, 1123, 586, 957,
            889, 616, 791,
            1153, 551, 404, 388, 295, 271, 258, 1248, 678,
            643, 476, 269, 270,
            747, 658, 1126,
            61, 231, 805, 764, 351, 527, 962, 711, 185, 1090,
            683, 843, 523, 522,
            14, 1018, 44, 282, 941, 490, 456, 394, 1143, 340, 506, 1087, 1141, 1004, 1171, 949, 1221, 724, 921, 801,
            180, 707, 675, 639, 524, 474, 380, 316, 302, 600,
            661, 428, 1038, 398,
            487, 750, 1084, 897,
            212, 691, 1222, 1029, 227, 640, 525, 259, 181, 174, 662, 395, 1144, 279, 344, 1026, 917, 51, 887, 446,
            819, 803, 756, 475, 736,
            899, 503, 1052, 1101, 222, 624,
            511, 493,
            947, 1009, 1067, 1098, 898, 433,
            923, 810,
            283, 182, 1000, 516, 67, 636, 911, 359, 156,
            556, 879, 802, 1236,
            1133, 481, 696,
            676, 542,
            720, 638, 1155, 256,
            970, 850, 1046, 393,
            62, 537, 286,
            763,
            1173, 1065, 339, 1027, 991, 221, 313, 1040, 504, 1142, 653,
            184, 591, 211, 1224, 389,
            427, 979, 352, 1082, 660, 837,
            985, 400, 664, 588, 449, 971, 1041, 1063, 1228, 533, 844, 695, 632, 512, 336, 255, 215, 155, 1255, 309,
            321, 1017, 1166, 257, 644, 326, 681, 714, 792, 445, 301, 1073, 1001, 984, 946, 360, 548, 497, 587,
            9, 845, 913, 690, 541, 601, 455, 280,
            626, 723, 429, 1053, 1127, 154, 1241, 604, 919,
            597, 391, 312, 165,
            734, 910, 1037, 609, 1134,
            923, 810,
            737, 948,
            1172

            // перчатки
        ]
    };

    public List<int> Gloves { get; set; } =
    [
        5030
    ];
}

public class Connection
{
    public required string Host { get; init; }
    public required string Database { get; init; }
    public required string User { get; init; }
    public required string Password { get; init; }
    public int Port { get; init; }
}

public class VipSkinChecker : BasePlugin
{
    public override string ModuleAuthor => "thesamefabius";
    public override string ModuleName => "[VIP] Skin Checker";
    public override string ModuleVersion => "v1.0.0";

    private IVipCoreApi? _api;
    private readonly PluginCapability<IVipCoreApi> _pluginCapability = new("vipcore:core");

    private Config _config = null!;
    private string _dbConnectionString = string.Empty;

    public override void OnAllPluginsLoaded(bool hotReload)
    {
        _api = _pluginCapability.Get();
        if (_api == null) return;

        _config = _api.LoadConfig<Config>("vip_skinchecker");
        _dbConnectionString = BuildConnectionString();

        RegisterEventHandler<EventPlayerConnectFull>(EventPlayerConnectFull);
    }

    private HookResult EventPlayerConnectFull(EventPlayerConnectFull @event, GameEventInfo info)
    {
        var player = @event.Userid;
        if (player is null) return HookResult.Continue;

        Task.Run(() => CheckPlayerSkin(player));
        return HookResult.Continue;
    }

private async Task CheckPlayerSkin(CCSPlayerController player)
{
    try
    {
        await using var connection = new MySqlConnection(_dbConnectionString);
        await connection.OpenAsync();

        var playerId = await connection.QueryFirstOrDefaultAsync<int>(
            "select id from sc_player where steamid = @SteamId",
            new { SteamId = player.SteamID });

        if (playerId == 0)
        {
            Logger.LogError($"Player ID not found for SteamID: {player.SteamID}");
            return;
        }

        var gloves = _config.Gloves;
        var glovesFromDb = await connection.QueryAsync<int>(
            "select glove from sc_items where player_id = @PlayerId and server_id = @ServerId",
            new
            {
                PlayerId = playerId, _config.ServerId
            });

        var groups = _config.Groups;
        var skinFromDb = await connection.QueryAsync<string>(
            "select skin from sc_skins where player_id = @PlayerId and server_id = @ServerId",
            new { PlayerId = playerId, _config.ServerId });

        foreach (var glove in glovesFromDb)
        {
            if (!_api!.IsClientVip(player) || (_api.IsClientVip(player) && _api.GetClientVipGroup(player) is not "GOLD"))
            {
                var affectedRows = await connection.ExecuteAsync(
                    $"update sc_items set glove = @Glove where player_id = @PlayerId and server_id = @ServerId and glove = @OldGlove",
                    new
                    {
                        Glove = 0,
                        PlayerId = playerId,
                        _config.ServerId,
                        OldGlove = glove
                    });

                Logger.LogInformation(
                    $"Updated glove for player with ID {playerId}. Affected rows: {affectedRows}");
            }
        }

        foreach (var skinDb in skinFromDb)
        {
            var skin = int.Parse(skinDb.Split(';')[0]);
            if (!_api!.IsClientVip(player))
            {
                if (groups.Values.Any(groupsValue => groupsValue.Contains(skin)))
                {
                    var rows = await connection.ExecuteAsync(
                        "update sc_skins set stickers = @Stickers, skin = @NewSkin where player_id = @PlayerId and skin = @Skin and server_id = @ServerId",
                        new
                        {
                            Stickers = "0;0;0;0",
                            NewSkin = "0;0;0",
                            PlayerId = playerId,
                            Skin = skinDb,
                            _config.ServerId
                        });

                    Logger.LogInformation($"Updated skin for player with ID {playerId}. Affected rows: {rows}");
                }

                continue;
            }

            var group = _api!.GetClientVipGroup(player);

            if (!groups.TryGetValue(group, out var skinId)) continue;
            if (group is not "GOLD")
            {
                var code = await connection.ExecuteAsync(
                    "update sc_skins set stickers = @Stickers where player_id = @PlayerId and server_id = @ServerId",
                    new
                    {
                        Stickers = "0;0;0;0",
                        PlayerId = playerId,
                        _config.ServerId
                    });

                Logger.LogInformation(
                    $"Updated stickers for non-GOLD VIP player. Player ID: {playerId}, Affected rows: {code}");
            }

            if (skinId.Contains(skin)) continue;

            var updateCode = await connection.ExecuteAsync(
                "update sc_skins set skin = @NewSkin where player_id = @PlayerId and skin = @Skin and server_id = @ServerId",
                new
                {
                    NewSkin = "0;0;0",
                    PlayerId = playerId,
                    Skin = skinDb,
                    _config.ServerId
                });

            Logger.LogInformation($"Updated VIP player skin. Player ID: {playerId}, Affected rows: {updateCode}");
        }
    }
    catch (Exception e)
    {
        Logger.LogError(e.ToString());
    }
}

    private string BuildConnectionString()
    {
        var connection = _config.Connection;
        var builder = new MySqlConnectionStringBuilder
        {
            Database = connection.Database,
            UserID = connection.User,
            Password = connection.Password,
            Server = connection.Host,
            Port = (uint)connection.Port
        };

        Console.WriteLine("OK!");
        return builder.ConnectionString;
    }
}

улучши этот код, сделай его лучше.