网站商城建设合同范本中国建设银行电话95533
2026/2/17 10:27:47 网站建设 项目流程
网站商城建设合同范本,中国建设银行电话95533,网站建设排行,win7优化大师下载背景 在 ASP.NET Core 应用开发中#xff0c;使用 PostgreSQL的jsonb类型存储多语言数据是一种常见的方案。这种方式相比传统的多列存储或独立翻译表#xff0c;在模式定义上更加灵活。 例如#xff0c;对于一个包含多语言简介的“艺术家”实体#xff0c;我们通常如下定…背景在 ASP.NET Core 应用开发中使用 PostgreSQL的jsonb类型存储多语言数据是一种常见的方案。这种方式相比传统的多列存储或独立翻译表在模式定义上更加灵活。例如对于一个包含多语言简介的“艺术家”实体我们通常如下定义/* by 01130.hk - online tools website : 01130.hk/zh/formatjava.html */ public class ArtistEntity { public int Id { get; set; } // 使用 jsonb 存储多语言字典Key语言代码(en, zh-CN), Value内容 [Column(TypeName jsonb)] public Dictionarystring, string Biography { get; set; } []; }性能考量虽然存储方便但在读取时会面临流量和性能问题。在大多数业务场景中前端仅需要展示当前用户语言如英语的内容。如果直接查询实体EF Core会将包含所有语言的JSONB对象完整加载到内存中。对于包含几十种语言的长文本字段这不仅浪费数据库 I/O也增加了网络传输开销。尝试使用EF Core的字典索引器语法/* by 01130.hk - online tools website : 01130.hk/zh/formatjava.html */ // 期望生成的 SQL 是直接取值 var bio context.Artists.Select(x x.Biography[en]).FirstOrDefault();根据 Npgsql EF Core Provider 文档虽然 Provider 提供了如EF.Functions.JsonContains、EF.Functions.JsonExists等丰富的 JSONB 操作函数但在处理 Dictionary 索引器的投影翻译时仍存在局限性。在某些复杂的 Select 投影中它可能无法生成最优的-操作符或者导致查询在客户端求值。目前Npgsql的EF.Functions中并没有直接对应jsonb_extract_path_text的方法而这个原生函数恰恰是解决此类需求最直接的方式。它能在数据库服务端完成解析仅返回指定路径的文本值。什么是 jsonb_extract_path_textjsonb_extract_path_text是PostgreSQL的原生函数等同于操作符#专门用于从 JSON 数据中根据路径提取文本。相比于直接返回 JSON 对象它能直接返回纯文本text 类型非常适合提取多语言字典中的单一语言值。假设数据库里的Biography字段存储如下 JSON{ en: Hello World, zh-CN: 你好世界, fr: Bonjour le monde }如果我们只想获取中文简介-- 使用函数提取 zh-CN 键的值 SELECT jsonb_extract_path_text(Biography, zh-CN) FROM Artists; -- 结果仅返回字符串 你好世界这种处理方式完全在数据库端完成传输到应用层的只有这4个字符而不是包含英文和法文的完整JSON 对象。解决方案映射自定义函数为了在EF Core中使用jsonb_extract_path_text我们可以通过自定义函数映射来实现。什么是 EF Core自定义函数EF Core 的自定义函数映射User-defined function mapping允许开发者 C#方法直接映射到数据库中的 SQL 函数。在 LINQ 查询中使用这些被映射的 C# 方法时EF Core不会在客户端执行它们而是将它们“翻译”成对应的 SQL 片段发送给数据库执行。这就像是给了你一把钥匙让你能够从 C# 代码中直接调用数据库特有的、强大的原生能力如 PostgreSQL 的 JSON 处理、GIS 地理信息计算等而无需编写原生的 SQL 字符串。1. 定义函数存根在 C# 中定义一个静态方法作为存根Stub用于告诉 EF Core 即使翻译 SQL。public static class DbFunctionsExtensions { // 此方法仅用于 EF Core 查询映射客户端调用时抛出异常 public static string JsonExtractPathText(this Dictionarystring, string json, string key) { throw new NotSupportedException(此方法仅用于 EF Core 查询映射不可在客户端执行。); } }2. 配置模型映射在OnModelCreating中通过 Fluent API 进行映射关系配置,HasDbFunction将其映射到数据库函数jsonb_extract_path_text。protected override void OnModelCreating(ModelBuilder modelBuilder) { modelBuilder.HasDbFunction(typeof(DbFunctionsExtensions) .GetMethod(nameof(DbFunctionsExtensions.JsonExtractPathText), [typeof(Dictionarystring, string), typeof(string)])!) .HasName(jsonb_extract_path_text) .IsBuiltIn(); }或者也可以使用[DbFunction]特性直接配置映射关系这样代码更加紧凑。using Microsoft.EntityFrameworkCore; public static class DbFunctionsExtensions { // 映射到 PostgreSQL 的内置函数 jsonb_extract_path_text [DbFunction(jsonb_extract_path_text, IsBuiltIn true)] public static string JsonExtractPathText(this Dictionarystring, string json, string key) { throw new NotSupportedException(此方法仅用于 EF Core 查询映射不可在客户端执行。); } }3. 使用示例配置完成后可以在 LINQ 查询中直接调用该扩展方法var query db.Artists .Select(entity new { Id entity.Id, // 数据库仅返回当前语言的文本 Bio entity.Biography.JsonExtractPathText(CultureInfo.CurrentUICulture.Name) });生成的 SQL 将调用原生jsonb_extract_path_text函数避免了全量传输 JSON 数据。索引优化策略针对 JSONB 字段的查询优化需要根据具体需求选择合适的索引类型。GIN 索引适用于“包含”类查询如 Biography 是否包含 en 键。builder.EntityArtistEntity() .HasIndex(x x.Biography) .HasMethod(gin);函数索引 (B-Tree)如果业务中存在大量基于特定语言如英文名称的精确查找或排序需求GIN 索引效率较低。此时应针对热点语言创建函数索引-- 针对英语内容建立 B-Tree 索引 CREATE INDEX idx_artist_bio_en ON Artists (( Biography - en ));适用场景与局限性虽然通过jsonb_extract_path_text可以减少网络传输但这并不是所有场景下的万能解。高并发读取即便减少了传输量解析 JSONB 在数据库层面依然有 CPU 开销。如果面临极高并发的读取请求如首页热门列表频繁让数据库解析 JSON 并不是最优解。在这种情况下应当引入应用层缓存如 Redis或使用专门的搜索引擎如 Elasticsearch。数据结构复杂度此方法最适合扁平的 Key-Value 结构。如果 JSON 结构非常复杂且嵌套深维护路径映射会变得困难。数据库负载将数据处理逻辑下推到数据库虽然方便但会增加数据库 CPU 负载。在数据库资源已是瓶颈的系统中需谨慎使用。通过这种方式我们在保持开发便利性的同时通过利用数据库原生能力解决了一个具体的性能问题。开发者应根据实际的数据量级和访问模式决定是采用此直连方案还是引入更复杂的缓存架构。参考链接https://learn.microsoft.com/en-us/ef/core/querying/user-defined-function-mappinghttps://github.com/npgsql/efcore.pg/issues/2703作者 马行空的博客出处 https://www.cnblogs.com/netry/p/19452236/efcore_jsonb_extract_path_text_in_postgredb本文版权归作者和博客园共有欢迎转载但未经作者同意必须保留此段声明且在文章页面明显位置给出原文链接。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询