using Newtonsoft.Json;
using Newtonsoft.Json.Converters;
using OF_DL.Enumerations;
using Serilog;

namespace OF_DL.Models;

public class Config : IFileNameFormatConfig
{
    [ToggleableConfig] public bool DownloadAvatarHeaderPhoto { get; set; } = true;

    [ToggleableConfig] public bool DownloadPaidPosts { get; set; } = true;

    [ToggleableConfig] public bool DownloadPosts { get; set; } = true;

    [ToggleableConfig] public bool DownloadArchived { get; set; } = true;

    [ToggleableConfig] public bool DownloadStreams { get; set; } = true;

    [ToggleableConfig] public bool DownloadStories { get; set; } = true;

    [ToggleableConfig] public bool DownloadHighlights { get; set; } = true;

    [ToggleableConfig] public bool DownloadMessages { get; set; } = true;

    [ToggleableConfig] public bool DownloadPaidMessages { get; set; } = true;

    [ToggleableConfig] public bool DownloadImages { get; set; } = true;

    [ToggleableConfig] public bool DownloadVideos { get; set; } = true;

    [ToggleableConfig] public bool DownloadAudios { get; set; } = true;

    [ToggleableConfig] public bool IncludeExpiredSubscriptions { get; set; } = false;

    [ToggleableConfig] public bool IncludeRestrictedSubscriptions { get; set; } = false;

    [ToggleableConfig] public bool SkipAds { get; set; } = false;

    public string? DownloadPath { get; set; } = "";

    [ToggleableConfig] public bool RenameExistingFilesWhenCustomFormatIsSelected { get; set; } = false;

    public int? Timeout { get; set; } = -1;

    [ToggleableConfig] public bool FolderPerPaidPost { get; set; } = false;

    [ToggleableConfig] public bool FolderPerPost { get; set; } = false;

    [ToggleableConfig] public bool FolderPerPaidMessage { get; set; } = false;

    [ToggleableConfig] public bool FolderPerMessage { get; set; } = false;

    [ToggleableConfig] public bool LimitDownloadRate { get; set; } = false;

    public int DownloadLimitInMbPerSec { get; set; } = 4;

    // Indicates if you want to download only on specific dates.
    [ToggleableConfig] public bool DownloadOnlySpecificDates { get; set; } = false;

    // This enum will define if we want data from before or after the CustomDate.
    [JsonConverter(typeof(StringEnumConverter))]
    public DownloadDateSelection DownloadDateSelection { get; set; } = DownloadDateSelection.before;
    // This is the specific date used in combination with the above enum.

    [JsonConverter(typeof(ShortDateConverter))]
    public DateTime? CustomDate { get; set; } = null;

    [ToggleableConfig] public bool ShowScrapeSize { get; set; } = false;

    [ToggleableConfig] public bool DownloadPostsIncrementally { get; set; } = false;

    public bool NonInteractiveMode { get; set; } = false;
    public string NonInteractiveModeListName { get; set; } = "";

    [ToggleableConfig] public bool NonInteractiveModePurchasedTab { get; set; } = false;

    public string? FFmpegPath { get; set; } = "";

    [ToggleableConfig] public bool BypassContentForCreatorsWhoNoLongerExist { get; set; } = false;

    public Dictionary<string, CreatorConfig> CreatorConfigs { get; set; } = new();

    [ToggleableConfig] public bool DownloadDuplicatedMedia { get; set; } = false;

    public string IgnoredUsersListName { get; set; } = "";

    [JsonConverter(typeof(StringEnumConverter))]
    public LoggingLevel LoggingLevel { get; set; } = LoggingLevel.Error;

    [ToggleableConfig] public bool IgnoreOwnMessages { get; set; } = false;

    [ToggleableConfig] public bool DisableBrowserAuth { get; set; } = false;

    [JsonConverter(typeof(StringEnumConverter))]
    public VideoResolution DownloadVideoResolution { get; set; } = VideoResolution.source;

    // When enabled, post/message text is stored as-is without XML stripping.
    [ToggleableConfig] public bool DisableTextSanitization { get; set; } = false;

    public string? PaidPostFileNameFormat { get; set; } = "";
    public string? PostFileNameFormat { get; set; } = "";
    public string? PaidMessageFileNameFormat { get; set; } = "";
    public string? MessageFileNameFormat { get; set; } = "";

    public IFileNameFormatConfig GetCreatorFileNameFormatConfig(string username)
    {
        FileNameFormatConfig combinedFilenameFormatConfig = new()
        {
            PaidPostFileNameFormat = PaidPostFileNameFormat,
            PostFileNameFormat = PostFileNameFormat,
            PaidMessageFileNameFormat = PaidMessageFileNameFormat,
            MessageFileNameFormat = MessageFileNameFormat
        };

        if (CreatorConfigs.TryGetValue(username, out CreatorConfig? creatorConfig))
        {
            if (creatorConfig?.PaidPostFileNameFormat != null)
            {
                combinedFilenameFormatConfig.PaidPostFileNameFormat = creatorConfig.PaidPostFileNameFormat;
            }

            if (creatorConfig?.PostFileNameFormat != null)
            {
                combinedFilenameFormatConfig.PostFileNameFormat = creatorConfig.PostFileNameFormat;
            }

            if (creatorConfig?.PaidMessageFileNameFormat != null)
            {
                combinedFilenameFormatConfig.PaidMessageFileNameFormat = creatorConfig.PaidMessageFileNameFormat;
            }

            if (creatorConfig?.MessageFileNameFormat != null)
            {
                combinedFilenameFormatConfig.MessageFileNameFormat = creatorConfig.MessageFileNameFormat;
            }
        }

        Log.Debug("PaidMessageFilenameFormat: {CombinedConfigPaidMessageFileNameFormat}",
            combinedFilenameFormatConfig.PaidMessageFileNameFormat);
        Log.Debug("PostFileNameFormat: {CombinedConfigPostFileNameFormat}",
            combinedFilenameFormatConfig.PostFileNameFormat);
        Log.Debug("MessageFileNameFormat: {CombinedConfigMessageFileNameFormat}",
            combinedFilenameFormatConfig.MessageFileNameFormat);
        Log.Debug("PaidPostFileNameFormat: {CombinedConfigPaidPostFileNameFormat}",
            combinedFilenameFormatConfig.PaidPostFileNameFormat);

        return combinedFilenameFormatConfig;
    }
}
