using Microsoft.AspNetCore.Authentication;
using Microsoft.AspNetCore.Authentication.JwtBearer;
using Microsoft.Identity.Abstractions;
using Microsoft.Identity.Web;
using Microsoft.Identity.Web.Resource;

namespace Api
{
    using Microsoft.EntityFrameworkCore;
    using Api.Models;
    using Microsoft.AspNetCore.Rewrite;

    public static class Program
    {
        public static void Main(string[] args)
        {
            var builder = WebApplication.CreateBuilder(args);

            // Add services to the container.
            builder.Services.AddAuthentication(options =>
            {
                options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
                options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
            })
            .AddJwtBearer(options =>
            {
                options.Authority = builder.Configuration["Authentication:PocketId:Authority"];
                options.TokenValidationParameters = new Microsoft.IdentityModel.Tokens.TokenValidationParameters()
                {
                    ValidAudiences = builder.Configuration["Authentication:PocketId:ClientId"]?.Split(';').Select(i => i.Trim()).ToArray(),
                    ValidIssuers = builder.Configuration["Authentication:PocketId:Authority"]?.Split(';').Select(i => i.Trim()).ToArray()
                };
            });

            builder.Services.AddCors(options =>
            {
                options.AddPolicy("Default", policy =>
                {
                    var allowedHostsConfiguration = builder.Configuration["CorsOrigins"]?
                        .ToString()
                        .Split(',');

                    policy
                        .WithOrigins(allowedHostsConfiguration ?? new[] { "*" })
                        .AllowAnyHeader()
                        .AllowAnyMethod();
                });
            });

            builder.Services.AddControllers();

            // Add DbContext with SQL Server
            // Allow connection string to be set via environment variable (e.g., in Docker)
            builder.Services.AddDbContext<AppDbContext>(options =>
                options.UseSqlServer(builder.Configuration.GetConnectionString("DefaultConnection")));

            // Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle
            builder.Services.AddEndpointsApiExplorer();
            builder.Services.AddSwaggerGen();

            var app = builder.Build();

            app.UseSwagger();
            app.UseSwaggerUI();


            if (!app.Environment.IsDevelopment())
            {
                app.UseHttpsRedirection();
            }

            // Angular rewrite for SPA hosting
            var routes = new[] { "api", "swagger" };
            var rewriteString = String.Join("|", routes);
            var rewriteOptions = new RewriteOptions()
                .AddRewrite(@$"^(?!.*?\b({rewriteString}))^(?!.*?\.\b(jpg|jpeg|png|svg|ttf|woff|woff2|html|js|json|css|ico))", "index.html", false);
            app.UseRewriter(rewriteOptions);

            // Serve static files from the Angular app
            if (app.Environment.IsDevelopment())
            {
                var currentDirectory = Directory.GetCurrentDirectory();
                var staticFilePath = Path.Combine(currentDirectory, "../Web/dist/Web/browser");
                app.UseDefaultFiles(new DefaultFilesOptions
                {
                    FileProvider = new Microsoft.Extensions.FileProviders.PhysicalFileProvider(staticFilePath),
                    DefaultFileNames = new List<string> { "index.html" }
                });
                app.UseStaticFiles(new StaticFileOptions
                {
                    FileProvider = new Microsoft.Extensions.FileProviders.PhysicalFileProvider(staticFilePath),
                    RequestPath = ""
                });
            }
            else
            {
                app.UseDefaultFiles(); // Uses wwwroot by default
                app.UseStaticFiles();
            }

            app.UseCors("Default");
            app.UseAuthentication();
            app.UseAuthorization();

            app.MapControllers();

            app.Run();
        }
    }
}
