You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Knex查询Sqlite3返回JSON为字符串的问题咨询

解决SQLite+Knex查询返回JSON字符串而非对象的问题

方法1:利用SQLite内置json()函数直接返回JSON对象

SQLite 3.38.0及以上版本支持json()函数,可将JSON字符串转换为SQLite原生JSON类型,Knex会自动将其映射为JavaScript对象。修改你的查询语句,将主查询中的child.data替换为db.raw('json(child.data) as data'):

db
.select('parent.id', 'parent.name', db.raw('json(child.data) as data'))
.from('parent')
.leftJoin(
    db
    .select("parentid", db.raw("json_group_array( json_object ( 'id', id, 'temp', temp )) as data"))
    .from("child")
    .groupBy('parentid')
    .as('child')
    , function(){
        this.on('parent.id','=', 'child.parentid')
    }
)
.orderBy('parent.id')

执行后返回的data字段直接就是JavaScript数组对象,无需额外解析。

方法2:给单个查询添加postProcessResponse钩子

如果你的SQLite版本较低不支持json()函数,可以在当前查询链中添加postProcessResponse,让Knex在处理结果时自动解析data字段:

db
.select('parent.id', 'parent.name', 'child.data')
.from('parent')
.leftJoin(
    db
    .select("parentid", db.raw("json_group_array( json_object ( 'id', id, 'temp', temp )) as data"))
    .from("child")
    .groupBy('parentid')
    .as('child')
    , function(){
        this.on('parent.id','=', 'child.parentid')
    }
)
.orderBy('parent.id')
.postProcessResponse(results => {
  return results.map(item => {
    if (item.data) {
      try {
        item.data = JSON.parse(item.data);
      } catch (err) {
        // 解析失败时保留原字符串,避免报错
      }
    }
    return item;
  });
})

这个操作属于查询本身的配置,无需在API层单独写循环逻辑。

方法3:全局配置Knex的结果处理钩子

如果多个查询都需要处理JSON字符串转对象,可以在创建Knex实例时全局配置postProcessResponse,实现所有查询自动解析指定字段:

const knex = require('knex')({
  client: 'sqlite3',
  connection: {
    filename: './your-db.sqlite'
  },
  postProcessResponse: (results, queryContext) => {
    if (Array.isArray(results)) {
      return results.map(item => {
        // 针对data字段做自动解析
        if (item.data && typeof item.data === 'string') {
          try {
            item.data = JSON.parse(item.data);
          } catch (err) {}
        }
        return item;
      });
    }
    // 处理单条结果的情况
    if (results.data && typeof results.data === 'string') {
      try {
        results.data = JSON.parse(results.data);
      } catch (err) {}
    }
    return results;
  }
});

这样所有查询返回的data字段都会被自动尝试解析为对象,无需重复编写解析逻辑。

内容的提问来源于stack exchange,提问作者j4rey

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.19 17:32:46