feat: 初始化NewLife Studio项目,完成基础框架与数据管理模块
何炳宏 authored at 2026-05-26 12:09:09
4.15 KiB
NewLife.Studio
using NewLife.Studio.Core;
using Xunit;

namespace NewLife.Studio.Core.Tests;

public class StudioServicesTests
{
    /// <summary>Minimal IServiceProvider stub for testing without DI package dependency.</summary>
    private class TestServiceProvider : IServiceProvider
    {
        private readonly Dictionary<Type, object> _services = new();

        public void Register<T>(T instance) where T : class
        {
            _services[typeof(T)] = instance;
        }

        public object? GetService(Type serviceType)
        {
            _services.TryGetValue(serviceType, out var service);
            return service;
        }
    }

    [Fact]
    public void Initialize_With_Null_Throws_ArgumentNullException()
    {
        var ex = Assert.Throws<ArgumentNullException>(() => StudioServices.Initialize(null!));
        Assert.Equal("serviceProvider", ex.ParamName);
    }

    [Fact]
    public void GetRequiredService_Throws_When_Not_Initialized()
    {
        // We cannot easily reset the static field, so we test that
        // calling GetRequiredService on the uninitialized static throws.
        // Since other tests may have initialized it, this test verifies
        // the behavior when _serviceProvider is null.
        // Use reflection to reset for a clean test.
        ResetStudioServices();

        var ex = Assert.Throws<InvalidOperationException>(() => StudioServices.GetRequiredService<string>());
        Assert.Contains("not initialized", ex.Message);
    }

    [Fact]
    public void Initialize_Then_GetRequiredService_Returns_Registered_Service()
    {
        ResetStudioServices();

        var provider = new TestServiceProvider();
        var myService = "Hello, World!";
        provider.Register(myService);

        StudioServices.Initialize(provider);

        var result = StudioServices.GetRequiredService<string>();
        Assert.Equal("Hello, World!", result);
    }

    [Fact]
    public void Initialize_Then_GetService_Returns_Registered_Service()
    {
        ResetStudioServices();

        var provider = new TestServiceProvider();
        var myService = "Hello, Service!";
        provider.Register(myService);

        StudioServices.Initialize(provider);

        var result = StudioServices.GetService<string>();
        Assert.NotNull(result);
        Assert.Equal("Hello, Service!", result);
    }

    [Fact]
    public void GetService_Returns_Null_When_Service_Not_Registered()
    {
        ResetStudioServices();

        var provider = new TestServiceProvider();
        StudioServices.Initialize(provider);

        var result = StudioServices.GetService<string>();
        Assert.Null(result);
    }

    [Fact]
    public void GetRequiredService_Throws_When_Service_Not_Registered()
    {
        ResetStudioServices();

        var provider = new TestServiceProvider();
        StudioServices.Initialize(provider);

        var ex = Assert.Throws<InvalidOperationException>(() => StudioServices.GetRequiredService<System.Text.StringBuilder>());
        Assert.Contains("StringBuilder", ex.Message);
        Assert.Contains("not registered", ex.Message);
    }

    [Fact]
    public void GetService_Returns_Null_When_Not_Initialized()
    {
        ResetStudioServices();

        var result = StudioServices.GetService<string>();
        Assert.Null(result);
    }

    [Fact]
    public void Initialize_Can_Be_Called_Multiple_Times()
    {
        ResetStudioServices();

        var provider1 = new TestServiceProvider();
        provider1.Register("service1");
        StudioServices.Initialize(provider1);
        Assert.Equal("service1", StudioServices.GetRequiredService<string>());

        var provider2 = new TestServiceProvider();
        provider2.Register("service2");
        StudioServices.Initialize(provider2);
        Assert.Equal("service2", StudioServices.GetRequiredService<string>());
    }

    /// <summary>Reset the static service provider to null for clean test state.</summary>
    private static void ResetStudioServices()
    {
        var field = typeof(StudioServices).GetField("_serviceProvider",
            System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Static);
        field?.SetValue(null, null);
    }
}