build-flow.api/tests/BuildFlow.File.Tests/DownloadFileQueryHandlerTests.cs
xiangning 8f85a2d3c8 refactor(file): 移除bucket参数并使用默认桶解析器
- 移除AbortMultipartCommand中的BucketName参数
- 移除CompleteMultipartCommand中的BucketName参数
- 移除DeleteFileCommand中的BucketName参数
- 移除DownloadFileQuery中的BucketName参数
- 移除GetFileContentQuery中的BucketName参数
- 移除GetFilePreviewQuery中的BucketName参数
- 移除GetOfficePreviewQuery中的BucketName参数
- 移除InitMultipartCommand中的BucketName参数
- 在各处理器中注入IBucketResolver并获取默认桶
- 更新所有相关端点和请求模型移除bucket参数
- 修改测试代码适配参数变更
- 添加IM离线消息到平台通知中心的跨模块集成实现
2026-07-03 13:32:08 +08:00

80 lines
2.9 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

using System.Text;
using File.Application.Common;
using File.Application.Features.Files.Handlers;
using File.Application.Features.Files.Queries;
using File.Infrastructure.Storage;
using FluentAssertions;
using Moq;
using Xunit;
namespace BuildFlow.File.Tests;
/// <summary>
/// 下载文件查询处理器单元测试。覆盖正常下载、空内容两个场景。
/// Mock IS3StorageService 隔离 S3 外部依赖。
/// </summary>
public class DownloadFileQueryHandlerTests
{
/// <summary>测试用 bucket 解析器,固定返回 "test-bucket"。</summary>
private static IBucketResolver BucketResolver()
{
var mock = new Mock<IBucketResolver>();
mock.Setup(r => r.GetDefaultBucketAsync(It.IsAny<CancellationToken>())).ReturnsAsync("test-bucket");
return mock.Object;
}
/// <summary>创建 Mock S3 + Handler。</summary>
private static (Mock<IS3StorageService> s3Mock, DownloadFileQueryHandler handler) Setup(string content = "hello world")
{
var s3Mock = new Mock<IS3StorageService>();
var stream = new MemoryStream(Encoding.UTF8.GetBytes(content));
s3Mock
.Setup(x => x.DownloadFileAsync("test-bucket", "test-key", It.IsAny<CancellationToken>()))
.ReturnsAsync((stream, "text/plain"));
var handler = new DownloadFileQueryHandler(s3Mock.Object, BucketResolver());
return (s3Mock, handler);
}
[Fact]
public async Task DownloadFile_WithValidPath_ReturnsContent()
{
// Arrange
var (s3Mock, handler) = Setup("hello world");
// Act
var result = await handler.Handle(
new DownloadFileQuery("test-key"),
CancellationToken.None);
// Assert — 返回的是 S3 原始流,透传给调用方;ContentType 取 S3 返回的真实类型
result.Should().NotBeNull();
result.Stream.Should().NotBeNull();
result.ContentType.Should().Be("text/plain");
result.FileName.Should().Be("test-key");
s3Mock.Verify(x => x.DownloadFileAsync("test-bucket", "test-key", It.IsAny<CancellationToken>()), Times.Once);
}
[Fact]
public async Task DownloadFile_S3ReturnsEmpty_ReturnsReadableEmptyStream()
{
// Arrange — DownloadFileQueryHandler 透传 S3 流,空内容对应空 MemoryStream
var s3Mock = new Mock<IS3StorageService>();
var emptyStream = new MemoryStream();
s3Mock
.Setup(x => x.DownloadFileAsync(It.IsAny<string>(), It.IsAny<string>(), It.IsAny<CancellationToken>()))
.ReturnsAsync((emptyStream, "application/octet-stream"));
var handler = new DownloadFileQueryHandler(s3Mock.Object, BucketResolver());
// Act
var result = await handler.Handle(
new DownloadFileQuery("test-key"),
CancellationToken.None);
// Assert — Handler 透传空流,长度为 0
result.Stream.Should().NotBeNull();
result.Stream.Length.Should().Be(0);
}
}