Dapper如何处理SQL Server的FOR JSON PATH Dapper高效生成JSON

来源:这里教程网 时间:2026-02-21 17:36:41 作者:

Dapper本身不直接解析或处理SQL Server的

FOR JSON PATH
结果,但它能高效地将这类查询返回的JSON字符串作为普通字段读取——关键在于让SQL Server生成JSON,Dapper只负责“原样拿回来”,不额外序列化,避免双重JSON化或性能浪费。

明确职责分工:SQL Server做JSON生成,Dapper做轻量映射

SQL Server 2016+ 支持

FOR JSON PATH
,可直接在查询中把结果集转成JSON字符串。Dapper只需用
string
SqlDbType.NVarChar
类型接收该列,无需引用
Newtonsoft.Json
System.Text.Json
去再序列化。

✅ 正确做法:查询返回
SELECT Name, (SELECT Id, Title FROM Posts WHERE UserId = U.Id FOR JSON PATH) AS PostsJson FROM Users U
,映射到
class User { public string Name { get; set; } public string PostsJson { get; set; } }
❌ 错误做法:用Dapper查出对象列表后再用
JsonSerializer.Serialize()
转JSON——这绕过了SQL Server的优化,还多一次内存分配和序列化开销

注意NULL和空集合的JSON表现

FOR JSON PATH
默认对空子查询返回
NULL
(不是
[]
),若需空数组,得显式处理:

ISNULL((SELECT ... FOR JSON PATH), '[]')
确保返回字符串
"[]"
或用
COALESCE((SELECT ... FOR JSON PATH), '[]')
Dapper读到的就是标准JSON字符串,后续可用
JsonDocument.Parse()
JsonSerializer.Deserialize<t>()</t>
按需解析

大结果集场景:流式读取 + 避免全量加载

FOR JSON PATH
生成的JSON很大(如导出报表),别用
Query<t>()</t>
一次性加载全部。改用
QueryMultiple()
ExecuteReader()
配合
SqlDataReader.GetFieldValue<string>(index)</string>
,逐行读取JSON字符串,再流式写入响应或文件。

减少内存峰值,尤其适合Web API返回大型JSON文档 Dapper的
QueryFirstAsync<string>()</string>
也适用——只取首行JSON字段,不构建对象列表

与Dapper.Extensions或Dapper.Contrib无关

FOR JSON PATH
是纯SQL能力,不依赖任何Dapper扩展库。不需要引入
DapperExtensions
Dapper.Contrib
,也不需要配置
JsonConverter
。保持Dapper轻量本质:它就是
IDbConnection
的扩展,只管执行SQL、读取结果。

基本上就这些。核心就一条:让SQL Server吐JSON,Dapper当管道,不加工、不拦截、不重造轮子。

相关推荐