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

OpenTelemetry集成Prisma无法提取查询参数,如何无自定义装饰器获取?

解决Prisma链路追踪中SQL占位符替换为实际参数的问题

核心原因

Prisma默认的Instrumentation出于性能和敏感数据防护的考虑,不会自动将SQL占位符替换为实际参数,因此Span的db.statement字段仅保留带占位符的SQL模板。

无需自定义装饰器的实现方案

1. 拦截Prisma查询日志注入Span

利用Prisma自带的查询日志事件,将带实际参数的SQL关联到当前活跃Span:

import { PrismaClient } from '@prisma/client';
import { trace } from '@opentelemetry/api';

const prisma = new PrismaClient({
  log: [
    {
      emit: 'event',
      level: 'query',
    },
  ],
});

prisma.$on('query', (e) => {
  const currentSpan = trace.getActiveSpan();
  if (!currentSpan) return;

  // 替换占位符为实际参数,生成完整SQL
  let fullStatement = e.query;
  e.params.forEach((param, index) => {
    // 处理字符串类型参数的单引号转义
    const formattedParam = typeof param === 'string' 
      ? `'${param.replace(/'/g, "''")}'` 
      : param.toString();
    fullStatement = fullStatement.replace(`$${index + 1}`, formattedParam);
  });

  // 更新Span的db.statement字段
  currentSpan.setAttribute('db.statement', fullStatement);
});

2. 自定义PrismaInstrumentation增强逻辑

继承PrismaInstrumentation类,重写onQuery方法直接在链路追踪层面处理参数替换:

import { PrismaInstrumentation } from '@opentelemetry/instrumentation-prisma';

class CustomPrismaInstrumentation extends PrismaInstrumentation {
  protected override onQuery(span, event) {
    super.onQuery(span, event);
    if (!span || !event.params) return;

    let fullStatement = event.query;
    event.params.forEach((param, index) => {
      const formattedParam = typeof param === 'string' 
        ? `'${param.replace(/'/g, "''")}'` 
        : param.toString();
      fullStatement = fullStatement.replace(`$${index + 1}`, formattedParam);
    });

    span.setAttribute('db.statement', fullStatement);
  }
}

// 使用自定义Instrumentation替代默认实现
const instrumentation = new CustomPrismaInstrumentation();

注意事项

  • 敏感数据风险:替换参数后Span会包含实际业务数据,若导出至第三方监控系统,需针对性做脱敏处理(如过滤密码、手机号等字段)。
  • 性能开销:批量查询或大参数场景下,占位符替换会产生一定性能消耗,建议根据业务场景评估启用必要性。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.01 12:28:25