using BenchmarkDotNet.Columns;
using BenchmarkDotNet.Configs;
using BenchmarkDotNet.Exporters;
using BenchmarkDotNet.Reports;
using BenchmarkDotNet.Running;
using Microsoft.Extensions.Logging;
using Serilog.Context;

namespace ZB.MOM.WW.CBDD.Tests.Benchmark;

class Program
{
    static void Main(string[] args)
    {
        var logger = Logging.CreateLogger<Program>();
        var mode = args.Length > 0 ? args[0].Trim().ToLowerInvariant() : string.Empty;

        if (mode == "manual")
        {
            using var _ = LogContext.PushProperty("Mode", "Manual");
            ManualBenchmark.Run(logger);
            return;
        }

        if (mode == "size")
        {
            using var _ = LogContext.PushProperty("Mode", "SizeBenchmark");
            DatabaseSizeBenchmark.Run(logger);
            return;
        }

        if (mode == "compression")
        {
            using var _ = LogContext.PushProperty("Mode", "CompressionBenchmarks");
            BenchmarkRunner.Run<CompressionBenchmarks>(CreateConfig());
            return;
        }

        if (mode == "compaction")
        {
            using var _ = LogContext.PushProperty("Mode", "CompactionBenchmarks");
            BenchmarkRunner.Run<CompactionBenchmarks>(CreateConfig());
            return;
        }

        if (mode == "mixed")
        {
            using var _ = LogContext.PushProperty("Mode", "MixedWorkloadBenchmarks");
            BenchmarkRunner.Run<MixedWorkloadBenchmarks>(CreateConfig());
            return;
        }

        if (mode == "all")
        {
            using var _ = LogContext.PushProperty("Mode", "AllBenchmarks");
            var config = CreateConfig();
            BenchmarkRunner.Run<InsertBenchmarks>(config);
            BenchmarkRunner.Run<ReadBenchmarks>(config);
            BenchmarkRunner.Run<SerializationBenchmarks>(config);
            BenchmarkRunner.Run<CompressionBenchmarks>(config);
            BenchmarkRunner.Run<CompactionBenchmarks>(config);
            BenchmarkRunner.Run<MixedWorkloadBenchmarks>(config);
            return;
        }

        using var __ = LogContext.PushProperty("Mode", "BenchmarkDotNet");
        var defaultConfig = CreateConfig();

        BenchmarkRunner.Run<InsertBenchmarks>(defaultConfig);
        BenchmarkRunner.Run<ReadBenchmarks>(defaultConfig);
        BenchmarkRunner.Run<SerializationBenchmarks>(defaultConfig);
    }

    private static IConfig CreateConfig()
    {
        return DefaultConfig.Instance
            .AddExporter(HtmlExporter.Default)
            .WithSummaryStyle(SummaryStyle.Default
                .WithRatioStyle(RatioStyle.Trend)
                .WithTimeUnit(Perfolizer.Horology.TimeUnit.Microsecond));
    }
}
