Files
administration/Program.cs
2025-09-16 22:20:21 +02:00

170 lines
7.3 KiB
C#
Raw Permalink Blame History

This file contains invisible Unicode characters

This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

using administration.Models;
using administration.Models.Finances;
using administration.Models.HelloFresh;
using administration.Services;
using IngredientsAI.Services;
using Microsoft.AspNetCore.Authentication.Cookies;
using Microsoft.AspNetCore.HttpOverrides;
using Microsoft.AspNetCore.Identity;
using Microsoft.EntityFrameworkCore;
using System.Text.Json;
using User = administration.Models.User;
namespace administration
{
public class Program
{
public static void Main(string[] args)
{
DotNetEnv.Env.Load();
var builder = WebApplication.CreateBuilder(args);
// ==============================================
// 1⃣ Base de données
// ==============================================
var dbConnection = Environment.GetEnvironmentVariable("ADMIN_DB_CONNECTION");
if (string.IsNullOrEmpty(dbConnection))
throw new Exception("❌ ADMIN_DB_CONNECTION est introuvable.");
bool inContainer = Environment.GetEnvironmentVariable("DOTNET_RUNNING_IN_CONTAINER") == "true";
string hostOverride = builder.Configuration["DB_HOST"] ?? Environment.GetEnvironmentVariable("DB_HOST");
string Fix(string? cs, string? dbNameFallback)
{
if (string.IsNullOrWhiteSpace(cs) && !string.IsNullOrWhiteSpace(dbNameFallback))
{
var def = builder.Configuration.GetConnectionString("DefaultConnection") ?? "";
if (!string.IsNullOrWhiteSpace(def))
cs = System.Text.RegularExpressions.Regex.Replace(def, @"Database=([^;]+)", $"Database={dbNameFallback}");
}
if (!string.IsNullOrWhiteSpace(cs) && !inContainer && !string.IsNullOrWhiteSpace(hostOverride))
{
cs = cs.Replace("Server=sqlserver,1433", $"Server={hostOverride},1433", StringComparison.OrdinalIgnoreCase);
}
return cs ?? "";
}
var csLayout = Fix(builder.Configuration.GetConnectionString("DefaultConnection"), "LayoutData");
var csHello = Fix(builder.Configuration.GetConnectionString("HelloFresh"), "HelloFresh");
var csFinance = Fix(builder.Configuration.GetConnectionString("Finances"), "Finances");
builder.Services.AddDbContext<LayoutDataContext>(o => o.UseSqlServer(csLayout));
builder.Services.AddDbContext<HelloFreshContext>(o => o.UseSqlServer(csHello));
builder.Services.AddDbContext<FinancesContext>(o => o.UseSqlServer(csFinance));
AppSettings.Initialize(builder.Configuration);
builder.Services.AddSingleton<OllamaService>();
// ==============================================
// 2⃣ Session
// ==============================================
builder.Services.AddSession(options =>
{
options.IdleTimeout = TimeSpan.FromHours(8);
options.Cookie.HttpOnly = true;
options.Cookie.IsEssential = true;
});
// ==============================================
// 3⃣ Authentification par cookie
// ==============================================
builder.Services.AddAuthentication(CookieAuthenticationDefaults.AuthenticationScheme)
.AddCookie(options =>
{
options.LoginPath = "/Connections/Login";
options.AccessDeniedPath = "/Connections/Login";
options.SlidingExpiration = true;
options.ExpireTimeSpan = TimeSpan.FromDays(14);
});
builder.Services.AddAuthorization();
builder.Services.AddControllers().AddJsonOptions(o =>
{
o.JsonSerializerOptions.PropertyNamingPolicy = JsonNamingPolicy.CamelCase;
});
// ==============================================
// 4⃣ MVC + services
// ==============================================
builder.Services.AddControllersWithViews();
builder.Services.AddHttpContextAccessor();
builder.Services.AddScoped<IPasswordHasher<User>, PasswordHasher<User>>();
// ==============================================
// 5⃣ CORS
// ==============================================
builder.Services.AddCors(options =>
{
options.AddPolicy("AllowFrontend", policy =>
{
policy.WithOrigins("http://localhost:5018", "https://administration.byakurepo.online")
.AllowAnyHeader()
.AllowAnyMethod();
});
});
builder.Services.AddHttpClient(); // déjà présent chez toi
builder.Services.AddHttpClient("ollama", (sp, client) =>
{
var cfg = sp.GetRequiredService<IConfiguration>();
var baseUrl = cfg["Ollama:Url"] ?? "http://ollama:11434";
client.BaseAddress = new Uri(baseUrl);
client.Timeout = TimeSpan.FromSeconds(25);
});
var ollamaBuilder = builder.Services.AddHttpClient("ollama", (sp, client) =>
{
var cfg = sp.GetRequiredService<IConfiguration>();
var baseUrl = cfg["Ollama:Url"] ?? "http://ollama:11434";
client.BaseAddress = new Uri(baseUrl);
client.Timeout = TimeSpan.FromSeconds(25);
});
#if DEBUG
ollamaBuilder.ConfigurePrimaryHttpMessageHandler(() => new HttpClientHandler
{
ServerCertificateCustomValidationCallback = HttpClientHandler.DangerousAcceptAnyServerCertificateValidator
});
#endif
// ...
// ...
builder.Logging.AddFilter("administration.Services.BasicAuthenticationHandler", LogLevel.Warning);
var app = builder.Build();
// ==============================================
// 6⃣ Pipeline
app.MapGet("/_dbping", async (HelloFreshContext hf, LayoutDataContext ld) =>
{
try { await hf.Database.ExecuteSqlRawAsync("SELECT 1"); } catch (Exception ex) { return Results.Problem($"HelloFresh: {ex.GetBaseException().Message}"); }
try { await ld.Database.ExecuteSqlRawAsync("SELECT 1"); } catch (Exception ex) { return Results.Problem($"LayoutData: {ex.GetBaseException().Message}"); }
return Results.Ok("OK");
});
if (!app.Environment.IsDevelopment())
{
app.UseExceptionHandler("/Home/Error");
app.UseHsts();
}
app.UseHttpsRedirection();
app.UseStaticFiles();
app.UseForwardedHeaders(new ForwardedHeadersOptions { ForwardedHeaders = ForwardedHeaders.XForwardedFor | ForwardedHeaders.XForwardedProto });
app.UseRouting();
app.UseCors("AllowFrontend");
app.UseSession(); // ✅ toujours avant auth
app.UseAuthentication(); // ✅ s'applique à tout le site
app.UseAuthorization();
app.MapControllerRoute(
name: "default",
pattern: "{controller=Home}/{action=Index}/{id?}");
app.Run();
}
}
}