using MediatR; using mws.backend.dotnet.application.Common; using mws.backend.dotnet.application.Permissions; namespace mws.backend.dotnet.application.Documents; public record DeleteDocumentCommand(Guid UserId, Guid DocumentId) : IRequest; public class DeleteDocumentHandler(IUnitOfWork uow, IDocumentContentStore contentStore) : IRequestHandler { public async Task Handle(DeleteDocumentCommand command, CancellationToken ct) { var doc = await DocumentAccess.GetDocumentForUserAsync(uow, command.UserId, command.DocumentId, ct); await DocumentAccess.EnsureDocumentPermissionAsync(uow, command.UserId, doc.ProjectId, PermissionAction.Delete, ct); var allIds = new List<(Guid ProjectId, Guid DocumentId)>(); await CollectDescendants(uow, command.DocumentId, doc.ProjectId, allIds, ct); allIds.Add((doc.ProjectId, doc.Id)); await DocumentAccess.DeleteDescendantsAsync(uow, command.DocumentId, ct); uow.Documents.Remove(doc); await uow.SaveChangesAsync(ct); foreach (var (projectId, documentId) in allIds) { await contentStore.DeleteAsync(projectId, documentId, ct); } } private static async Task CollectDescendants( IUnitOfWork uow, Guid parentId, Guid projectId, List<(Guid ProjectId, Guid DocumentId)> ids, CancellationToken ct) { var children = await uow.Documents.GetChildrenAsync(parentId, ct); foreach (var child in children) { ids.Add((projectId, child.Id)); await CollectDescendants(uow, child.Id, projectId, ids, ct); } } }