Mise en place de la structure définitive du CRUD et modification de la page principale avec les datas

This commit is contained in:
2025-08-03 16:58:04 +02:00
parent 354c25ac06
commit fd080b2e64
1767 changed files with 147564 additions and 216 deletions

View File

@@ -0,0 +1,10 @@
using Microsoft.AspNetCore.Mvc;
namespace administration.Controllers
{
public class ApiBaseController : Controller
{
protected int? UserId => HttpContext.Session.GetInt32("UserId");
protected string? UserName => HttpContext.Session.GetString("UserName");
}
}

View File

@@ -0,0 +1,13 @@
using Microsoft.AspNetCore.Mvc;
using Microsoft.Data.SqlClient;
public class DBConnectionController : Controller
{
protected SqlConnection GetConnection()
{
var connectionString = AppSettings.GetConnectionString("DefaultConnection");
var connection = new SqlConnection(connectionString);
connection.Open();
return connection;
}
}

View File

@@ -0,0 +1,117 @@

using administration.Models;
using administration.Services;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
namespace administration.Controllers
{
/// <summary>
/// Contrôleur API pour la gestion des dépenses de l'utilisateur.
/// Fournit des points de terminaison pour récupérer les dépenses du mois en cours
/// pour l'utilisateur actuellement connecté.
/// </summary>
[ApiController]
[Route("api/[controller]")]
public class ExpenseController : Controller
{
private readonly FinancesContext _context;
private readonly IUserSessionService _userSession;
/// <summary>
/// Initialise une nouvelle instance du contrôleur <see cref="ExpenseController"/>.
/// </summary>
/// <param name="context">Contexte de base de données des finances.</param>
/// <param name="userSession">Service de session utilisateur pour obtenir l'utilisateur courant.</param>
public ExpenseController(FinancesContext context, IUserSessionService userSession)
{
_context = context;
_userSession = userSession;
}
/// <summary>
/// Récupère la dernière dépense du mois en cours pour l'utilisateur connecté.
/// </summary>
/// <returns>
/// Un objet <see cref="IActionResult"/> contenant la dépense trouvée ou un code d'erreur approprié.
/// </returns>
[HttpGet("last_expenses")]
public IActionResult GetRightExpenses()
{
try
{
if (_userSession.UserId == null)
return Unauthorized("Utilisateur non connecté.");
var expense = _context.Expenses
.Where(e => e.UserId == _userSession.UserId &&
e.Date.Month == DateTime.Now.Month)
.OrderByDescending(e => e.Date)
.FirstOrDefault();
if (expense == null)
return NotFound("Aucune dépense trouvée pour ce mois.");
var additionalSources = (
from additional in _context.AdditionalSources
join logo in _context.Logos on additional.LogoId equals logo.Id
where additional.UserId == _userSession.UserId &&
additional.Date.Month == DateTime.Now.Month &&
(additional.TransactionType == "expense" || additional.TransactionType == "sub")
select new
{
additional.Id,
additional.TransactionType,
additional.Amount,
additional.Description,
additional.Date,
Logo = new
{
logo.Id,
logo.Name,
logo.Image
}
}
).ToList();
var totalExpenses = expense.Rent
+ expense.Electricity
+ expense.Trash
+ expense.Wifi
+ expense.Groceries
+ expense.Insurance
+ expense.Saving;
var totalAdditionalExpense = additionalSources
.Where(a => a.TransactionType == "expense")
.Sum(a => a.Amount);
var totalAdditionalSub = additionalSources
.Where(a => a.TransactionType == "sub")
.Sum(a => a.Amount);
var result = new
{
expense.Id,
expense.Rent,
expense.Electricity,
expense.Trash,
expense.Wifi,
expense.Groceries,
expense.Insurance,
expense.Date,
expense.Saving,
AdditionalSourcesExpense = additionalSources.Where(a => a.TransactionType == "expense").ToList(),
AdditionalSourcesSub = additionalSources.Where(a => a.TransactionType == "sub").ToList(),
Total = totalExpenses + totalAdditionalExpense + totalAdditionalSub
};
return Ok(result);
}
catch (Exception ex)
{
return StatusCode(500, $"Erreur serveur : {ex.Message}, Méthode GetAdditionalRevenues");
}
}
}
}

View File

@@ -6,20 +6,35 @@ namespace administration.Controllers;
public class HomeController : Controller
{
private readonly ILogger<HomeController> _logger;
private readonly FinancesContext _context;
public HomeController(ILogger<HomeController> logger)
public HomeController(FinancesContext context)
{
_logger = logger;
_context = context;
}
public IActionResult Index()
{
// R<>cup<75>re un utilisateur fictif pour l<>exemple
var user = _context.Users.Where(X => X.Id == 2).First(); // <20> remplacer par un filtre r<>el (par ex. Email ou Id)
if (user != null)
{
// Stocker dans la session
HttpContext.Session.SetInt32("UserId", user.Id);
HttpContext.Session.SetString("UserName", user.Name);
}
return View();
}
public IActionResult Privacy()
public IActionResult Profile()
{
int? userId = HttpContext.Session.GetInt32("UserId");
string userName = HttpContext.Session.GetString("UserName");
ViewBag.UserId = userId;
ViewBag.UserName = userName;
return View();
}

View File

@@ -0,0 +1,62 @@
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.Mvc.ViewEngines;
using Microsoft.AspNetCore.Mvc.Rendering;
using Microsoft.AspNetCore.Mvc.ViewFeatures;
using Microsoft.AspNetCore.Mvc.ModelBinding;
using System.IO;
namespace administration.Controllers
{
public class PagesController : Controller
{
private readonly ICompositeViewEngine _viewEngine;
private readonly ITempDataProvider _tempDataProvider;
public PagesController(ICompositeViewEngine viewEngine, ITempDataProvider tempDataProvider)
{
_viewEngine = viewEngine;
_tempDataProvider = tempDataProvider;
}
[HttpGet("/pages/{folder}/{page}")]
public async Task<IActionResult> Render(string folder, string page)
{
var allowedFolders = new[] { "Charts", "Components", "Connections", "Home", "Tables", "Utilities" };
var realFolder = allowedFolders.FirstOrDefault(f => string.Equals(f, folder, StringComparison.OrdinalIgnoreCase));
if (realFolder == null)
return Content("Ce dossier n'est pas autorisé.", "text/plain; charset=utf-8");
// Trouver la vraie casse du fichier sur disque
var folderPath = Path.Combine(Directory.GetCurrentDirectory(), "Views", realFolder);
var cshtmlFile = Directory.GetFiles(folderPath, "*.cshtml")
.FirstOrDefault(f => string.Equals(Path.GetFileNameWithoutExtension(f), page, StringComparison.OrdinalIgnoreCase));
if (cshtmlFile == null)
return NotFound($"La vue ~/Views/{realFolder}/{page}.cshtml n'existe pas physiquement.");
var razorViewPath = $"~/Views/{realFolder}/{Path.GetFileName(cshtmlFile)}";
var result = _viewEngine.GetView(null, razorViewPath, true);
if (!result.Success)
return NotFound($"Vue Razor non trouvée : {razorViewPath}");
var viewData = new ViewDataDictionary(new EmptyModelMetadataProvider(), new ModelStateDictionary());
var tempData = new TempDataDictionary(HttpContext, _tempDataProvider);
using var sw = new StringWriter();
var context = new ViewContext(
ControllerContext,
result.View,
viewData,
tempData,
sw,
new HtmlHelperOptions()
);
await result.View.RenderAsync(context);
return Content(sw.ToString(), "text/html");
}
}
}

View File

@@ -0,0 +1,126 @@
using Microsoft.AspNetCore.Mvc;
using administration.Models;
using administration.Services;
namespace administration.Controllers
{
[ApiController]
[Route("api/[controller]")]
public class RevenueController : ControllerBase
{
private readonly FinancesContext _context;
private readonly IUserSessionService _userSession;
public RevenueController(FinancesContext context, IUserSessionService userSession)
{
_context = context;
_userSession = userSession;
}
/// <summary>
/// Récupère les X derniers revenues depuis la base de données.
/// </summary>
/// <param name="rows">Nombre de lignes à retourner</param>
/// <returns>Liste des revenues</returns>
[HttpGet("x_revenues")]
public IActionResult GetXRevenues([FromQuery] int rows = 1)
{
try
{
if (_userSession.UserId == null)
return Unauthorized("Utilisateur non connecté.");
var revenues = _context.Revenues
.Where(r => r.UserId == _userSession.UserId)
.OrderByDescending(r => r.Id)
.Take(rows)
.ToList();
return Ok(revenues);
}
catch (Exception ex)
{
return StatusCode(500, $"Erreur serveur : {ex.Message}, Méthode GetXRevenues");
}
}
/// <summary>
/// Récupère le dernier revenue depuis la base de données.
/// </summary>
/// <returns>Le dernier revenue</returns>
[HttpGet("last_revenue")]
public IActionResult GetLastRevenues()
{
try
{
if (_userSession.UserId == null)
return Unauthorized("Utilisateur non connecté.");
var revenue = _context.Revenues
.Where(r => r.UserId == _userSession.UserId)
.OrderByDescending(r => r.Id)
.FirstOrDefault();
return Ok(revenue);
}
catch (Exception ex)
{
return StatusCode(500, $"Erreur serveur : {ex.Message}, Méthode GetLastRevenues");
}
}
/// <summary>
/// Récupère tous les revenues depuis la base de données.
/// </summary>
/// <returns>Liste de revenues</returns>
[HttpGet("all_revenues")]
public IActionResult GetAllRevenues()
{
try
{
if (_userSession.UserId == null)
return Unauthorized("Utilisateur non connecté.");
var revenues = _context.Revenues
.Where(r => r.UserId == _userSession.UserId)
.OrderByDescending(r => r.Id)
.ToList();
return Ok(revenues);
}
catch (Exception ex)
{
return StatusCode(500, $"Erreur serveur : {ex.Message}, Méthode GetAllRevenues");
}
}
/// <summary>
/// Récupère toutes les ressources supplémentaires dont le type de transaction contient "revenu".
/// </summary>
/// <returns>Liste des ressources supplémentaires</returns>
[HttpGet("additional_revenues")]
public IActionResult GetAdditionalRevenues()
{
try
{
if (_userSession.UserId == null)
return Unauthorized("Utilisateur non connecté.");
var revenus = _context.AdditionalSources
.Where(r => r.UserId == _userSession.UserId &&
r.TransactionType.ToLower().Contains("revenu") &&
r.Date.Month == DateTime.Now.Month)
.OrderByDescending(r => r.Id)
.ToList();
return Ok(revenus);
}
catch (Exception ex)
{
return StatusCode(500, $"Erreur serveur : {ex.Message}, Méthode GetAdditionalRevenues");
}
}
}
}