using SharpChat.Auth;
using SharpChat.Users;
using System.Text.Json.Serialization;

namespace SharpChat.Flashii;

public class FlashiiAuthResult : AuthResult {
    public string UserId => UserIdRaw.ToString();
    public string UserName => UserNameRaw ?? string.Empty;
    public ColourInheritable UserColour => ColourInheritable.FromMisuzu(UserColourRaw);

    public UserPermissions UserPermissions {
        get {
            UserPermissions perms = 0;

            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_MESSAGE_SEND))
                perms |= UserPermissions.SendMessage;
            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_MESSAGE_DELETE_OWN))
                perms |= UserPermissions.DeleteOwnMessage;
            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_MESSAGE_DELETE_ANY))
                perms |= UserPermissions.DeleteAnyMessage;
            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_MESSAGE_EDIT_OWN))
                perms |= UserPermissions.EditOwnMessage;
            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_MESSAGE_EDIT_ANY))
                perms |= UserPermissions.EditAnyMessage;
            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_MESSAGE_BROADCAST))
                perms |= UserPermissions.SendBroadcast;

            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_USER_KICK))
                perms |= UserPermissions.KickUser;
            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_USER_BAN))
                perms |= UserPermissions.BanUser
                    | UserPermissions.ViewBanList
                    | UserPermissions.PardonUser
                    | UserPermissions.PardonIPAddress;
            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_USER_VIEW_ADDR))
                perms |= UserPermissions.ViewIPAddress;

            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_CHANNEL_CREATE))
                perms |= UserPermissions.CreateChannel;
            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_CHANNEL_SET_PERSIST))
                perms |= UserPermissions.SetChannelPermanent;
            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_CHANNEL_SET_PASSWORD))
                perms |= UserPermissions.SetChannelPassword;
            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_CHANNEL_SET_MIN_RANK))
                perms |= UserPermissions.SetChannelMinimumRank;
            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_CHANNEL_DELETE))
                perms |= UserPermissions.DeleteChannel;
            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_CHANNEL_JOIN_ANY))
                perms |= UserPermissions.JoinAnyChannel;

            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_NICK_SET_OWN))
                perms |= UserPermissions.SetOwnNickname;
            if(UserPermissionsRaw.HasFlag(FlashiiUserPermissions.C_NICK_SET_ANY))
                perms |= UserPermissions.SetOthersNickname;

            return perms;
        }
    }

    [JsonPropertyName("success")]
    public bool Success { get; init; }

    [JsonPropertyName("reason")]
    public string? Reason { get; init; }

    [JsonPropertyName("user_id")]
    public long UserIdRaw { get; init; }

    [JsonPropertyName("username")]
    public string? UserNameRaw { get; init; }

    [JsonPropertyName("colour_raw")]
    public int UserColourRaw { get; init; }

    [JsonPropertyName("hierarchy")]
    public int UserRank { get; init; }

    [JsonPropertyName("perms")]
    public FlashiiUserPermissions UserPermissionsRaw { get; init; }
}