You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

266 lines
9.8 KiB
C#

This file contains ambiguous Unicode characters!

This file contains ambiguous Unicode characters that may be confused with others in your current locale. If your use case is intentional and legitimate, you can safely ignore this warning. Use the Escape button to highlight these characters.

using OptionStudy.UnitApp.Next;
namespace OptionStudy.Next
{
/// <summary>
/// 配置绑定 测试
/// 引用 Microsoft.Extensions.Configuration.Binder 包
/// </summary>
public class ConfigBinderTest : IDisposable
{
private readonly ITestOutputHelper testOutput;
public ConfigBinderTest(ITestOutputHelper testOutputHelper)
{
this.testOutput = testOutputHelper;
}
/// <summary>
/// 绑定配置项的值
/// </summary>
[Fact]
public void Binder_ConfigItem_Test()
{
IDictionary<string, string?> memoryData = new Dictionary<string, string?>()
{
["AppName"] = "MemoryAppName",
["AppVersion"] = "0.0.0.1",
["EMail:ReceiveAddress"] = "memory@163.com",
["EMail:Recipient"] = "memory",
["foo"] = null,
["bar"] = "",
["baz"] = "123",
};
var root = new ConfigurationBuilder().AddInMemoryCollection(memoryData).Build();
//针对 object : 直接返回原始值字符串或null
Assert.Null(root.GetValue<object>("foo"));
Assert.Equal(string.Empty, root.GetValue<object>("bar"));
Assert.Equal("123", root.GetValue<object>("baz"));
//针对普通类型: 针对类型的 TypeConverter 来 完成类型转换
Assert.Equal(0,root.GetValue<int>("foo"));
Assert.Equal(123, root.GetValue<int>("baz"));
//针对 Nullable<T> 类型:原始值为""或null时返回null,否则转换成基础类型。匹配不了了,则借值为 Default(T)
Assert.Null(root.GetValue<int?>("foo"));
Assert.Null(root.GetValue<int?>("bar"));
testOutput.WriteLine("绑定配置项的值");
}
/// <summary>
/// 绑定配置项的值,使用自定义转换器
/// </summary>
[Fact]
public void Binder_ConfigItem_CustomConverter_Test()
{
IDictionary<string, string?> memoryData = new Dictionary<string, string?>()
{
["Point"] = "(123,456)",
};
var root = new ConfigurationBuilder().AddInMemoryCollection(memoryData).Build();
var point = root.GetValue<Point>("Point");
Assert.Equal(123, point.x);
Assert.Equal(456,point.y);
testOutput.WriteLine("绑定配置项的值,使用自定义转换器");
}
/// <summary>
/// 绑定复合对象
/// 自定义的类或结构等对象
/// </summary>
[Fact]
public void Binder_ComplexObject_Test()
{
IDictionary<string, string?> memoryData = new Dictionary<string, string?>()
{
["AppName"] = "MemoryAppName",
["AppVersion"] = "0.0.0.1",
["EMail:ReceiveAddress"] = "memory@163.com",
["EMail:Recipient"] = "memory",
};
var root = new ConfigurationBuilder().AddInMemoryCollection(memoryData).Build();
var appOption = root.Get<AppOption>();
Assert.Equal("MemoryAppName", appOption.AppName);
Assert.Equal("0.0.0.1", appOption.AppVersion.ToString());
Assert.Equal("memory@163.com", appOption.EMail?.ReceiveAddress);
Assert.Equal("memory", appOption.EMail?.Recipient);
var email = root.GetSection("EMail").Get<ReceiveMailOption>();
Assert.Equal("memory@163.com", email.ReceiveAddress);
Assert.Equal("memory", email.Recipient);
testOutput.WriteLine("绑定复合对象");
}
/// <summary>
/// 绑定集合(包括数组)
/// </summary>
[Fact]
public void Binder_Set_Test()
{
IDictionary<string, string?> memoryData = new Dictionary<string, string?>()
{
["0:AppName"] = "MemoryAppName",
["0:AppVersion"] = "0.0.0.1",
["0:EMail:ReceiveAddress"] = "memory@163.com",
["0:EMail:Recipient"] = "memory",
["1:AppName"] = "MemoryAppName",
["1:AppVersion"] = "0.0.0.1",
["1:EMail:ReceiveAddress"] = "memory@163.com",
["1:EMail:Recipient"] = "memory",
["2;AppName"] = "MemoryAppName",
["2;AppVersion"] = "0.0.0.1",
["2;EMail:ReceiveAddress"] = "memory@163.com",
["2;EMail:Recipient"] = "memory",
};
var root = new ConfigurationBuilder().AddInMemoryCollection(memoryData).Build();
var appOptions = root.Get<IList<AppOption>>();
Assert.Equal("MemoryAppName", appOptions[0].AppName);
Assert.Equal("0.0.0.1", appOptions[0].AppVersion.ToString());
Assert.Equal("memory@163.com", appOptions[0].EMail?.ReceiveAddress);
Assert.Equal("memory", appOptions[0].EMail?.Recipient);
Assert.Equal("MemoryAppName", appOptions[1].AppName);
Assert.Equal("0.0.0.1", appOptions[1].AppVersion.ToString());
Assert.Equal("memory@163.com", appOptions[1].EMail?.ReceiveAddress);
Assert.Equal("memory", appOptions[1].EMail?.Recipient);
Assert.Equal("MemoryAppName", appOptions[1].AppName);
Assert.Equal("0.0.0.1", appOptions[1].AppVersion.ToString());
Assert.Equal("memory@163.com", appOptions[1].EMail?.ReceiveAddress);
Assert.Equal("memory", appOptions[1].EMail?.Recipient);
testOutput.WriteLine("绑定集合(包括数组)");
}
/// <summary>
/// 绑定集合与数组的差别
/// 某项绑定失败,不影响其它项绑定,但是数组表现为空项而集合表现为忽略失败项
/// </summary>
[Fact]
public void Binder_CollectionAndArray_Differences_Test()
{
IDictionary<string, string?> memoryData = new Dictionary<string, string?>()
{
["0:AppName"] = "0MemoryAppName",
["0:AppVersion"] = "0.0.0.1",
["1:AppName"] = "1MemoryAppName",
["1:AppVersion"] = "A.B.C.D", //此项改为非版本数值,故意出错
["2:AppName"] = "2MemoryAppName",
["2:AppVersion"] = "2.1.2.3",
};
var root = new ConfigurationBuilder().AddInMemoryCollection(memoryData).Build();
var list = root.Get<IList<AppOption>>();
var array = root.Get<AppOption[]>();
Assert.Equal(2, list.Count);
Assert.Equal(3, array.Length);
Assert.Null(array[1]);
testOutput.WriteLine("绑定集合与数组的差别");
}
/// <summary>
/// 绑定字典
/// </summary>
[Fact]
public void Binder_Dictionary_Test()
{
IDictionary<string, string?> memoryData = new Dictionary<string, string?>()
{
["One:AppName"] = "0MemoryAppName",
["One:AppVersion"] = "0.0.0.1",
["One:EMail:ReceiveAddress"] = "memory@163.com",
["One:EMail:Recipient"] = "memory",
["Two:AppName"] = "1MemoryAppName",
["Two:AppVersion"] = "1.2.3.4",
["Two:EMail:ReceiveAddress"] = "1@163.com",
["Two:EMail:Recipient"] = "memory1",
["Three:AppName"] = "2MemoryAppName",
["Three:AppVersion"] = "2.0.0.0",
["Three:EMail:ReceiveAddress"] = "2@163.com",
["Three:EMail:Recipient"] = "memory2",
};
var root = new ConfigurationBuilder().AddInMemoryCollection(memoryData).Build();
var dic = root.Get<IDictionary<string,AppOption>>();
Assert.Equal(3, dic.Count);
Assert.Equal("0MemoryAppName", dic["One"].AppName);
Assert.Equal("1MemoryAppName", dic["Two"].AppName);
Assert.Equal("2MemoryAppName", dic["Three"].AppName);
testOutput.WriteLine("绑定字典");
}
/// <summary>
/// 绑定字典有错
/// 存在转换错误时,抛出异常
/// </summary>
[Fact]
public void Binder_Dictionary_HasError_Test()
{
IDictionary<string, string?> memoryData = new Dictionary<string, string?>()
{
["One:AppName"] = "0MemoryAppName",
["One:AppVersion"] = "0.0.0.1",
["One:EMail:ReceiveAddress"] = "memory@163.com",
["One:EMail:Recipient"] = "memory",
["Two:AppName"] = "1MemoryAppName",
["Two:AppVersion"] = "A.B.C.D", //此项改为非版本数值,故意出错
["Two:EMail:ReceiveAddress"] = "1@163.com",
["Two:EMail:Recipient"] = "memory1",
["Three:AppName"] = "2MemoryAppName",
["Three:AppVersion"] = "2.0.0.0",
["Three:EMail:ReceiveAddress"] = "2@163.com",
["Three:EMail:Recipient"] = "memory2",
};
var root = new ConfigurationBuilder().AddInMemoryCollection(memoryData).Build();
//["Two:AppVersion"] = "A.B.C.D"值不能转换成版本类,会抛出异常
Action getConfigDic = () =>
{
root.Get<IDictionary<string, AppOption>>();
};
Assert.Throws<InvalidOperationException>(getConfigDic);
testOutput.WriteLine("绑定字典:存在转换错误时,抛出异常!");
}
public void Dispose()
{
}
}
}