我有一个包含动态网格定义的 SQL 表(我正在使用 Angular 的 AGGrid 库)。 示例:
TB_AGGrid_定义
身份证 | 网格键 |
---|---|
1 | 测试网格 |
TB_AGGrid_Columns
身份证 | 网格ID | 田野 |
---|---|---|
1 | 1 | 第一栏 |
2 | 1 | 第二栏 |
我使用 ASP.NET Core 和 EF Core 为我的 Angular Web 应用程序创建后端 WebAPI 服务。 我有一个可以检索网格信息的控制器。
JSON 示例
{
"grid":{
"id":1,
"gridKey":"TestGrid",
"columns":[
{
"id":1,
"gridId":1,
"field":"FirstColumn"
},
{
"id":2,
"gridId":1,
"field":"SecondColumn"
}
]
}
}
我只想使用与 JsonSerializer 相同的算法来转换
Field
中 camelCase
属性的值。
我需要这样做才能正确绑定对象和区分大小写的网格列定义。
如果我将 AGGrid FirstColumn
作为字段发送到,它将无法与具有名为 firstColumn
的属性的对象一起使用(这将是默认序列化后的默认行为)。
我有这样的字段:
"IDTabella" --\> "idTabella"
"IDDTUltimoCommission" --\> "idDtUltimoCommission"
"NDGCliente" --\> "ndgCliente"
自动序列化工作完美,但我无法用我自己的函数复制相同的结果。
预期 JSON
{
"grid":{
"id":1,
"gridKey":"TestGrid",
"columns":[
{
"id":1,
"gridId":1,
"field":"firstColumn"
},
{
"id":2,
"gridId":1,
"field":"secondColumn"
}
]
}
}
正如您特别要求
camelCasing
在 .NET 中使用的 JsonSerializer
算法一样。以下是从 Github 上 .NET 运行时的官方开源存储库获取的实现(请参阅Github - dotnet/runtime)。
在当前
分支上实现,最后一次提交的哈希值是main
,该哈希值已经在 .NET 8 发布之后了。3138a80
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.
namespace System.Text.Json
{
internal sealed class JsonCamelCaseNamingPolicy : JsonNamingPolicy
{
public override string ConvertName(string name)
{
if (string.IsNullOrEmpty(name) || !char.IsUpper(name[0]))
{
return name;
}
#if NETCOREAPP
return string.Create(name.Length, name, (chars, name) =>
{
name.CopyTo(chars);
FixCasing(chars);
});
#else
char[] chars = name.ToCharArray();
FixCasing(chars);
return new string(chars);
#endif
}
private static void FixCasing(Span<char> chars)
{
for (int i = 0; i < chars.Length; i++)
{
if (i == 1 && !char.IsUpper(chars[i]))
{
break;
}
bool hasNext = (i + 1 < chars.Length);
// Stop when next char is already lowercase.
if (i > 0 && hasNext && !char.IsUpper(chars[i + 1]))
{
// If the next char is a space, lowercase current char before exiting.
if (chars[i + 1] == ' ')
{
chars[i] = char.ToLowerInvariant(chars[i]);
}
break;
}
chars[i] = char.ToLowerInvariant(chars[i]);
}
}
}
}
正如人们想象的那样,考虑到性能,它的实施得相当好。 e.主要通过在必要时使用
Span<T>
来避免堆分配,并使用通常仅在真正关心性能时才使用的某些方法(例如此处的 string.Create()
)。