profileShare

rasmusjy / splitapp-backend-modular-monolith

Read-only snapshot

No repository description.

main default branch 418 files Expires Sep 13, 2026, 9:06 AM
BudgetCategoryService.cs 3,406 bytes
1 using MediatR;
2 using SplitApp.Shared.Contracts.Expenses.Queries;
3 using SplitApp.WebApp.Application.DTO;
4 using SplitApp.WebApp.Application.Mappers;
5 using SplitApp.WebApp.Application.Contracts;
6
7 namespace SplitApp.WebApp.Application.Services;
8
9 public class BudgetCategoryService : IBudgetCategoryService
10 {
11 private readonly IAppUnitOfWork _uow;
12 private readonly IMediator _mediator;
13
14 public BudgetCategoryService(IAppUnitOfWork uow, IMediator mediator)
15 {
16 _uow = uow;
17 _mediator = mediator;
18 }
19
20 public async Task<List<BudgetCategoryBllDto>> GetByTripIdAsync(Guid tripId, Guid userId)
21 {
22 if (!await _uow.TripParticipants.IsParticipantAsync(tripId, userId))
23 return new List<BudgetCategoryBllDto>();
24 var categories = await _uow.BudgetCategories.GetByTripIdAsync(tripId);
25 var spent = await _mediator.Send(new GetBudgetCategorySpentQuery(tripId));
26 return BudgetCategoryBllDtoFactory.CreateList(categories, spent);
27 }
28
29 public async Task<List<BudgetCategoryBllDto>> GetByTripIdRawAsync(Guid tripId)
30 {
31 var categories = await _uow.BudgetCategories.GetByTripIdAsync(tripId);
32 var spent = await _mediator.Send(new GetBudgetCategorySpentQuery(tripId));
33 return BudgetCategoryBllDtoFactory.CreateList(categories, spent);
34 }
35
36 public async Task<BudgetCategoryBllDto?> GetByIdAsync(Guid id)
37 {
38 var category = await _uow.BudgetCategories.GetByIdAsync(id);
39 return category == null ? null : BudgetCategoryBllDtoFactory.Create(category);
40 }
41
42 public async Task<(BudgetCategoryBllDto? category, string? errorCode)> CreateAsync(BudgetCategoryBllDto category, Guid userId)
43 {
44 if (!await _uow.TripParticipants.IsOrganizerAsync(category.TripId, userId))
45 return (null, "forbidden");
46
47 var entity = BudgetCategoryBllDtoFactory.ToEntity(category);
48 if (entity.Id == Guid.Empty) entity.Id = Guid.NewGuid();
49 _uow.BudgetCategories.Add(entity);
50 await _uow.SaveChangesAsync();
51
52 var reloaded = await _uow.BudgetCategories.GetByIdAsync(entity.Id);
53 return (reloaded == null ? null : BudgetCategoryBllDtoFactory.Create(reloaded), null);
54 }
55
56 public async Task<(bool success, string? errorCode)> UpdateAsync(Guid id, BudgetCategoryBllDto incoming, Guid userId)
57 {
58 var existing = await _uow.BudgetCategories.GetByIdAsync(id);
59 if (existing == null) return (false, "notfound");
60
61 if (!await _uow.TripParticipants.IsOrganizerAsync(existing.TripId, userId))
62 return (false, "forbidden");
63
64 existing.Name = incoming.Name;
65 existing.IconName = incoming.IconName;
66 existing.PlannedAmount = incoming.PlannedAmount;
67 existing.DisplayOrder = incoming.DisplayOrder;
68
69 _uow.BudgetCategories.Update(existing);
70 await _uow.SaveChangesAsync();
71 return (true, null);
72 }
73
74 public async Task<(bool success, string? errorCode)> DeleteAsync(Guid id, Guid userId)
75 {
76 var existing = await _uow.BudgetCategories.GetByIdAsync(id);
77 if (existing == null) return (false, "notfound");
78
79 if (!await _uow.TripParticipants.IsOrganizerAsync(existing.TripId, userId))
80 return (false, "forbidden");
81
82 await _uow.BudgetCategories.RemoveAsync(id);
83 await _uow.SaveChangesAsync();
84 return (true, null);
85 }
86 }
87