using Microsoft.AspNetCore.Builder;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using OpenTelemetry.Metrics;
using OpenTelemetry.Resources;
using OpenTelemetry.Trace;

namespace Baya.Infrastructure.Monitoring.Configurations;

/// <summary>
/// The single OpenTelemetry stack (refinement-phase-9, §9.1). Metrics and traces share one resource
/// (<c>service.name = Baya.Web.Api</c>). Metrics are scraped by Prometheus (the <c>/metrics</c> endpoint,
/// wired in <see cref="PrometheusMetricsConfigurations"/>); traces cover ASP.NET Core requests and EF Core
/// commands so a cross-service money flow (webhook → confirm → ledger) can be followed end to end. The
/// request's trace id is the <c>ApiResult.RequestId</c> the client sees, so a support ticket maps 1:1 to a
/// trace.
/// <para>The prior duplicate prometheus-net stack was removed — OpenTelemetry is now the only metrics source.</para>
/// <para>OTLP export (traces + metrics) is <b>opt-in</b>: it is wired only when <c>OpenTelemetry:Otlp:Endpoint</c>
/// is configured, so an MVP deployment with Prometheus alone runs unchanged and no exporter spams connection
/// errors against an absent collector.</para>
/// </summary>
public static class OpenTelemetryConfigurations
{
    public const string ServiceName = "Baya.Web.Api";

    public static WebApplicationBuilder SetupOpenTelemetry(this WebApplicationBuilder builder)
    {
        var otlpEndpoint = builder.Configuration["OpenTelemetry:Otlp:Endpoint"];
        var hasOtlp = !string.IsNullOrWhiteSpace(otlpEndpoint);

        builder.Services.AddOpenTelemetry()
            .ConfigureResource(resource => resource.AddService(ServiceName))
            .WithMetrics(metricsBuilder =>
            {
                metricsBuilder.AddRuntimeInstrumentation()
                    .AddAspNetCoreInstrumentation()
                    .AddMeter("Microsoft.AspNetCore.Hosting"
                        , "Microsoft.AspNetCore.Server.Kestrel"
                        , "System.Net.Http"
                        , "Baya.Web.Api"
                        , "ControllerMetrics"
                        // The mediator request-duration histogram (MetricsBehaviour) — captured here so the one
                        // metrics stack actually exports it (the removed prometheus-net stack never did).
                        , "mediator_meter")
                    .AddPrometheusExporter();

                if (hasOtlp)
                    metricsBuilder.AddOtlpExporter(options => options.Endpoint = new Uri(otlpEndpoint!));
            })
            .WithTracing(tracingBuilder =>
            {
                tracingBuilder.AddAspNetCoreInstrumentation()
                    .AddEntityFrameworkCoreInstrumentation();

                if (hasOtlp)
                    tracingBuilder.AddOtlpExporter(options => options.Endpoint = new Uri(otlpEndpoint!));
            });

        builder.Services.AddMetrics();

        return builder;
    }
}
