using InnovEnergy.App.Backend.S3;
using InnovEnergy.Lib.Utils;

namespace S3Explorer;

public static class Program
{

    public static async Task<Int32> Main(String[] args)
    {
        // Todo refactor S3Access into Lib
        
        // Sssssecret
        if (args.Contains("-s"))
        {
            await SnakeGameSs.PlaySnake();
        }
        
        // Help message
        if (args.Length < 4 || args.Contains("-h"))
        {
            Console.WriteLine("Usage: S3Explorer [BucketId] [from:Unix-time] [to:Unix-time] [#Data-points]");
            Console.WriteLine("-h Shows this message.");
            Console.WriteLine("-s 🐍");
            return 0;
        }
        
        // Parsing Arguments
        var bucketName = args[0] + "-3e5b3069-214a-43ee-8d85-57d72000c19d";
        var startTime = Int64.Parse(args[1]);
        var endTime = Int64.Parse(args[2]);
        var numberOfDataPoints = Int64.Parse(args[3]);
        
        var timeBetweenDataPoints = TimeBetweenDataPoints(startTime, endTime, numberOfDataPoints);

        // Building a List of the timestamps we want to grab the files for.
        var timestampList = new List<String> { };
        for (var i = startTime; i <= endTime; i += timeBetweenDataPoints)
        {
            //Rounding to even numbers only (we only save every second second)
            timestampList.Add((i/2 *2).ToString());
        }

        await PrintFiles(bucketName,timestampList);
        
        // Success
        return 0;
    }

    private static async Task PrintFiles(String bucketName, List<String> timestampList)
    {
        var newestDataFilename = timestampList.Last();
        var csvFileText = await GetFileText(bucketName, newestDataFilename);
        
        // Building Header-Row from the newest data
        csvFileText
            .Select(l => l.Split(";"))
            .Select(l => l[0])
            .Prepend("Timestamp")
            .JoinWith(";")
            .WriteLine();
        
        foreach (var timestamp in timestampList)
        {
            csvFileText = await GetFileText(bucketName, timestamp);
            
            // Writing Data below data-keys in a timestamped row
            csvFileText.Select(l => l.Split(";"))
                   .Select(l => l[1])
                   .Prepend(timestamp)
                   .JoinWith(";")
                   .WriteLine();
        }

    }
    
    private static Int64 TimeBetweenDataPoints(Int64 startTime, Int64 endTime, Int64 numberOfDataPoints)
    {
        // Calculating temporal distance of data files from the number of requested points.
        var timeSpan = endTime - startTime;
        var timeBetweenDataPoints = timeSpan / numberOfDataPoints;

        // We only upload data every second second so sampling more is impossible.
        // If this ever changes we might have to change this as well.
        timeBetweenDataPoints = Math.Max(timeBetweenDataPoints, 2);
        return timeBetweenDataPoints;
    }
    
    // This Method extracts the Text from a given csv file on the s3 bucket
    private static async Task<String[]> GetFileText(String bucketName, String filename)
    {
        return await S3Access.Admin.GetFileText(bucketName, filename + ".csv");
    }
}