GFramework/GFramework.Core.Tests/Packaging/TransitiveGlobalUsingsPackagingTests.cs
GeWuYou 20f1c987eb refactor(tests): 优化全局引用测试的命名空间发现机制
- 添加基于真实类型的命名空间常量定义,避免硬编码字符串
- 引入 Architecture、Extensions 和 CoroutineExtensions 命名空间自动发现
- 将 FindRepositoryRoot 方法重构为 ResolveRepositoryRoot 并使用 CallerFilePath
- 更新断言逻辑以使用动态命名空间变量而非字面量字符串
- 移除对解决方案文件扫描的依赖,改用相对路径计算仓库根目录
- 添加方法参数验证和异常处理增强代码健壮性
2026-03-24 22:29:45 +08:00

80 lines
3.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.IO;
using System.Runtime.CompilerServices;
using GFramework.Core.Architectures;
using GFramework.Core.Coroutine.Extensions;
namespace GFramework.Core.Tests.Packaging;
/// <summary>
/// 验证运行时模块在构建期间会自动生成 transitive global usings 资产。
/// 该测试覆盖命名空间自动发现、框架侧过滤和消费者侧排除钩子的最终构建产物。
/// </summary>
[TestFixture]
public class TransitiveGlobalUsingsPackagingTests
{
/// <summary>
/// 使用真实类型派生架构命名空间,避免测试断言和命名空间重构脱节。
/// </summary>
private static readonly string ArchitectureNamespace = typeof(Architecture).Namespace
?? throw new InvalidOperationException(
"Architecture namespace should not be null.");
/// <summary>
/// 使用真实类型派生扩展命名空间,避免对字面量命名空间字符串的重复维护。
/// </summary>
private static readonly string ExtensionsNamespace = typeof(ContextAwareEnvironmentExtensions).Namespace
?? throw new InvalidOperationException(
"Extensions namespace should not be null.");
/// <summary>
/// 使用真实类型派生协程扩展命名空间,确保断言和源码自动发现保持一致。
/// </summary>
private static readonly string CoroutineExtensionsNamespace = typeof(CoroutineExtensions).Namespace
?? throw new InvalidOperationException(
"Coroutine extensions namespace should not be null.");
/// <summary>
/// 验证 GFramework.Core 在构建后会生成 transitive global usings props
/// 且 props 内容来自源码自动发现,并保留消费者侧排除机制。
/// </summary>
[Test]
public void CoreBuild_Should_Generate_AutoDiscovered_TransitiveGlobalUsingsProps()
{
var repositoryRoot = ResolveRepositoryRoot();
var propsPath = Path.Combine(
repositoryRoot,
"GFramework.Core",
"obj",
"gframework",
"GeWuYou.GFramework.Core.props");
Assert.That(File.Exists(propsPath), Is.True, $"Expected generated props to exist: {propsPath}");
var propsContent = File.ReadAllText(propsPath);
Assert.That(propsContent, Does.Contain(ExtensionsNamespace));
Assert.That(propsContent, Does.Contain(ArchitectureNamespace));
Assert.That(propsContent, Does.Contain(CoroutineExtensionsNamespace));
Assert.That(propsContent, Does.Contain("Remove=\"@(GFrameworkExcludedUsing)\""));
Assert.That(propsContent, Does.Not.Contain("System.Runtime.CompilerServices"));
}
/// <summary>
/// 基于当前测试源文件的已知位置解析仓库根目录。
/// 这里不扫描解决方案文件,避免测试对仓库布局演进产生额外脆弱性。
/// </summary>
/// <param name="sourceFilePath">由编译器注入的当前测试源文件绝对路径。</param>
/// <returns>仓库根目录绝对路径。</returns>
private static string ResolveRepositoryRoot([CallerFilePath] string sourceFilePath = "")
{
if (string.IsNullOrWhiteSpace(sourceFilePath))
{
throw new InvalidOperationException("Caller file path is required to resolve the repository root.");
}
var sourceDirectory = Path.GetDirectoryName(sourceFilePath)
?? throw new DirectoryNotFoundException(
$"Could not determine the directory for source file path: {sourceFilePath}");
return Path.GetFullPath(Path.Combine(sourceDirectory, "..", ".."));
}
}