using NSubstitute; using PnvPanel.Application.Admin.Media; using PnvPanel.Application.Common.Interfaces; using PnvPanel.Application.Media; using PnvPanel.Application.Tests.TestSupport; using Xunit; namespace PnvPanel.Application.Tests.Media; public class UploadMediaImageCommandHandlerTests { private readonly IFileStorage _fileStorage = Substitute.For(); private static MediaImageUpload Upload( string contentType = "image/png", long sizeBytes = 1024, string fileName = "screenshot.png" ) => new(new MemoryStream([1, 2, 3]), fileName, contentType, sizeBytes); [Fact] public async Task Handle_WithValidImage_SavesFileAndRow() { using var dbContext = InMemoryDbContextFactory.Create(); var adminId = Guid.NewGuid(); _fileStorage .SaveAsync(Arg.Any(), Arg.Any()) .Returns("stored-name"); var handler = new UploadMediaImageCommandHandler( dbContext, _fileStorage, FakeCurrentUser.Authenticated(adminId, "admin") ); var result = await handler.Handle( new UploadMediaImageCommand(Upload()), CancellationToken.None ); await dbContext.SaveChangesAsync(CancellationToken.None); Assert.True(result.IsSuccess); Assert.Equal("screenshot.png", result.Value.FileName); var image = Assert.Single(dbContext.MediaImages); Assert.Equal("stored-name", image.StoredFileName); Assert.Equal(adminId, image.UploadedBy); } [Fact] public async Task Handle_WithUnsupportedContentType_ReturnsValidationErrorWithoutSaving() { using var dbContext = InMemoryDbContextFactory.Create(); var handler = new UploadMediaImageCommandHandler( dbContext, _fileStorage, FakeCurrentUser.Authenticated(Guid.NewGuid()) ); var result = await handler.Handle( new UploadMediaImageCommand(Upload(contentType: "image/svg+xml", fileName: "x.svg")), CancellationToken.None ); Assert.False(result.IsSuccess); Assert.Equal(MediaErrors.UnsupportedImageType, result.Error); Assert.Empty(dbContext.MediaImages); await _fileStorage .DidNotReceive() .SaveAsync(Arg.Any(), Arg.Any()); } /// Лимит продублирован из MediaImageValidation — она internal (см. Application). private const long MaxSizeBytes = 5 * 1024 * 1024; [Fact] public async Task Handle_WithTooLargeImage_ReturnsValidationError() { using var dbContext = InMemoryDbContextFactory.Create(); var handler = new UploadMediaImageCommandHandler( dbContext, _fileStorage, FakeCurrentUser.Authenticated(Guid.NewGuid()) ); var result = await handler.Handle( new UploadMediaImageCommand(Upload(sizeBytes: MaxSizeBytes + 1)), CancellationToken.None ); Assert.False(result.IsSuccess); Assert.Equal(MediaErrors.ImageTooLarge, result.Error); Assert.Empty(dbContext.MediaImages); } }