using Managing.Common;

namespace Managing.Application.Shared;

public static class GrainHelpers
{
    /// <summary>
    /// Gets the interval in minutes for the reminder based on the timeframe
    /// </summary>
    public static double GetIntervalMinutes(Enums.Timeframe timeframe)
    {
        return timeframe switch
        {
            Enums.Timeframe.OneMinute => 1.0,
            Enums.Timeframe.FiveMinutes => 5.0,
            Enums.Timeframe.FifteenMinutes => 7.5, // Half of the timeframe for more frequent checks
            Enums.Timeframe.OneHour => 30.0, // Half of the timeframe for more frequent checks
            Enums.Timeframe.FourHour => 120.0, // Half of the timeframe for more frequent checks
            Enums.Timeframe.OneDay => 720.0, // Half of the timeframe for more frequent checks
            _ => 5.0 // Default to 5 minutes
        };
    }

    // Helper method to get a randomized due time and period
    public static (TimeSpan dueTime, TimeSpan period) GetDynamicRandomizedTimerOptions(TimeSpan basePeriod,
        int numberOfBots)
    {
        var random = new Random();

        // Determine the jitter percentage based on bot count
        // Example: 2% jitter for 100 bots, 10% for 1000 bots, etc.
        // This formula can be fine-tuned based on your system's performance metrics.
        double jitterPercentage = Math.Min(0.20, (double)numberOfBots / 10000); // Caps at 20% for 10,000 bots

        // Calculate a random due time within the period
        var dueTimeSeconds = random.Next(1, (int)basePeriod.TotalSeconds);
        var dueTime = TimeSpan.FromSeconds(dueTimeSeconds);

        // Add a random jitter to the period
        var jitterFactor = (random.NextDouble() * jitterPercentage) - (jitterPercentage / 2);
        var periodSeconds = (int)(basePeriod.TotalSeconds * (1 + jitterFactor));
        var period = TimeSpan.FromSeconds(periodSeconds);

        return (dueTime, period);
    }
}