关于 sentry-span-streaming
供 JavaScript Sentry 项目将基于 transaction 的追踪迁移到 span streaming 使用,指导检测现有配置、修改设置并验证结果。仅覆盖文档列出的 JavaScript SDK 环境。
主要功能
- 01检测平台、SDK 版本和追踪设置
- 02为浏览器和服务端 SDK 启用流式传输
- 03调整 span 回调与过滤器
- 04迁移性能分析配置
- 05验证构建和运行行为
适用场景
- 01将 Sentry 项目切换为流式 span 投递
- 02更新流式模式下的 beforeSendSpan
- 03替换 beforeSendTransaction 逻辑
- 04排查回退到静态模式的警告
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ getsentry/ sentry-for-ai --skill sentry-span-streaming安装后在 Claude Code 中输入/sentry-span-streaming确认已加载。
详细介绍
Sentry Span Streaming 迁移
从默认的基于事务的追踪生命周期(static)迁移到 Span Streaming(stream):Span 完成后分多个批次发送,而不是在事务结束时一次性批量发送。
在以下情况下调用此技能
- 用户要求“启用 Span Streaming”或“迁移到 Span Streaming”
- 用户想从基于事务的 Span 传输切换到流式传输
- 用户提到
traceLifecycle、spanStreamingIntegration或withStreamedSpan - 用户希望降低 Span 传输延迟或逐个处理 Span
支持的平台
| 平台 | 状态 |
|---|---|
| JavaScript(Browser、Node.js、Bun、Deno、Cloudflare) | 支持 |
| Python | 尚不可用 |
| Ruby | 尚不可用 |
| Go | 尚不可用 |
| 其他 SDK | 尚不可用 |
如果用户的项目未使用受支持的 SDK,请告知他们 Span Streaming 目前仅适用于 JavaScript SDK,然后在此处停止。
阶段 1:检测
识别用户的平台、SDK 版本和当前追踪配置。
1.1 检测平台和 SDK
# Check for JavaScript Sentry packages
cat package.json 2>/dev/null | grep -E '"@sentry/'
# Check for Python Sentry
cat requirements.txt setup.py pyproject.toml 2>/dev/null | grep -i sentry
# Check for Ruby Sentry
cat Gemfile 2>/dev/null | grep sentry
# Check for Go Sentry
cat go.mod 2>/dev/null | grep sentry
如果检测到不受支持的 Sentry SDK,请告知用户其平台暂不支持 Span Streaming。
1.2 检测 JavaScript 环境
# Detect if browser, server, or both
grep -rn "from '@sentry/browser'\|from '@sentry/react'\|from '@sentry/vue'\|from '@sentry/angular'\|from '@sentry/svelte'\|from '@sentry/nextjs'\|from '@sentry/nuxt'\|from '@sentry/sveltekit'\|from '@sentry/remix'\|from '@sentry/solidstart'\|from '@sentry/astro'\|from '@sentry/react-router'" --include="*.ts" --include="*.js" --include="*.tsx" --include="*.jsx" --include="*.mjs" -l 2>/dev/null | head -20
grep -rn "from '@sentry/node'\|from '@sentry/bun'\|from '@sentry/deno'\|from '@sentry/cloudflare'" --include="*.ts" --include="*.js" --include="*.tsx" --include="*.jsx" --include="*.mjs" -l 2>/dev/null | head -20
1.3 查找现有 Sentry 配置
# Find Sentry.init calls
grep -rn "Sentry\.init\|init({" --include="*.ts" --include="*.js" --include="*.tsx" --include="*.jsx" --include="*.mjs" -l 2>/dev/null | head -20
# Find beforeSendSpan usage
grep -rn "beforeSendSpan" --include="*.ts" --include="*.js" --include="*.tsx" --include="*.jsx" --include="*.mjs" -l 2>/dev/null
# Find beforeSendTransaction usage
grep -rn "beforeSendTransaction" --include="*.ts" --include="*.js" --include="*.tsx" --include="*.jsx" --include="*.mjs" -l 2>/dev/null
# Find ignoreSpans usage
grep -rn "ignoreSpans" --include="*.ts" --include="*.js" --include="*.tsx" --include="*.jsx" --include="*.mjs" -l 2>/dev/null
1.4 环境分类
根据检测结果,将每个 Sentry.init 调用归类为:
| 环境 | 软件包 | 迁移路径 |
|---|---|---|
| Browser | @sentry/browser、@sentry/react、@sentry/vue、@sentry/angular、@sentry/svelte | 添加 spanStreamingIntegration() |
| Server | @sentry/node、@sentry/bun、@sentry/deno、@sentry/cloudflare | 添加 traceLifecycle: 'stream' |
| 框架(两者) | @sentry/nextjs、@sentry/nuxt、@sentry/sveltekit、@sentry/remix、@sentry/astro、@sentry/solidstart、@sentry/react-router | 分别迁移客户端和服务端配置 |
阶段 2:迁移(JavaScript)
前提条件: Sentry JavaScript SDK >=10.53.1,并已启用追踪(配置了 tracesSampleRate 或 tracesSampler)。
对每个 Sentry.init 调用应用更改。依次处理阶段 1 中识别出的每个文件。
2.1 启用 Span Streaming
服务端 SDK
在 Sentry.init() 中添加 traceLifecycle: 'stream':
// Before
Sentry.init({
dsn: '...',
tracesSampleRate: 1.0,
});
// After
Sentry.init({
dsn: '...',
tracesSampleRate: 1.0,
traceLifecycle: 'stream',
});
浏览器端 SDK
将 Sentry.spanStreamingIntegration() 添加到 integrations 数组中。此集成会自动启用 traceLifecycle: 'stream',无需手动设置。
// Before
Sentry.init({
dsn: '...',
integrations: [
Sentry.browserTracingIntegration(),
],
tracesSampleRate: 1.0,
});
// After
Sentry.init({
dsn: '...',
integrations: [
Sentry.spanStreamingIntegration(),
Sentry.browserTracingIntegration(),
],
tracesSampleRate: 1.0,
});
spanStreamingIntegration() 相对于其他集成的顺序无关紧要。
框架 SDK(客户端 + 服务端)
对客户端配置文件应用浏览器端迁移,对服务端配置文件应用服务端迁移。常见模式如下:
| 框架 | 客户端配置 | 服务端配置 |
|---|---|---|
| Next.js | sentry.client.config.ts | sentry.server.config.ts、sentry.edge.config.ts |
| Nuxt | 模块中的客户端 Sentry.init | 模块中的服务端 Sentry.init |
| SvelteKit | src/hooks.client.ts | src/hooks.server.ts |
| Remix | entry.client.tsx | entry.server.tsx |
| Astro | 客户端初始化 | 服务端初始化 |
2.2 迁移 beforeSendSpan
如果用户配置了 beforeSendSpan 回调,必须使用 Sentry.withStreamedSpan() 包装该回调,才能在流式模式下正常工作。如果不使用此包装器,SDK 会回退到静态模式。
回调的结构也有所变化:
description现在是namedata现在是attributes- span 对象从
SpanJSON变为StreamedSpanJSON
// Before (static mode)
Sentry.init({
beforeSendSpan: (span) => {
if (span.description?.includes('/health')) {
span.description = '[filtered]';
}
// 'data' contains span attributes
delete span.data?.['http.request.body'];
return span;
},
});
// After (streaming mode)
Sentry.init({
beforeSendSpan: Sentry.withStreamedSpan((span) => {
if (span.name?.includes('/health')) {
span.name = '[filtered]';
}
// 'attributes' replaces 'data'
if (span.attributes) {
delete span.attributes['http.request.body'];
}
return span;
}),
});
回调中的主要区别:
静态(SpanJSON) | 流式(StreamedSpanJSON) |
|---|---|
span.description | span.name |
span.data(处理后的属性) | span.attributes(原始属性) |
span.timestamp(结束时间) | span.end_timestamp |
span.status(可选字符串) | span.status('ok' 或 'error') |
span.op | span.attributes['sentry.op'] |
从 beforeSendSpan 返回 null 不会丢弃 span:该返回值会被忽略,并记录一条警告。
2.3 移除或替换 beforeSendTransaction
beforeSendTransaction 在流式模式下不起作用。span 会单独发送,而不是批量组成事务。
// Before
Sentry.init({
beforeSendTransaction: (event) => {
// This entire callback is ignored in streaming mode
if (event.transaction === '/health') {
return null;
}
return event;
},
});
根据 beforeSendTransaction 的用途选择迁移方式:
| 用途 | 流式模式下的替代方案 |
|---|---|
| 按名称/路由丢弃 span | 使用 ignoreSpans 选项 |
| 发送前修改 span 数据 | 使用 withStreamedSpan 包装的 beforeSendSpan |
| 按事务名称筛选 | 使用带字符串/RegExp 模式的 ignoreSpans |
| 向事务添加标签/上下文 | 使用 withStreamedSpan 包装的 beforeSendSpan |
迁移其逻辑后,从 Sentry.init() 中移除 beforeSendTransaction 选项。
2.4 配置 ignoreSpans(可选)
ignoreSpans 在静态模式和流式模式下均可使用,但筛选器会在 span 生命周期的不同时间点进行评估:
- **流式模式:**在 span 开始时评估。只考虑 span 开始时可用的数据——span 名称和创建时设置的属性。
- **静态模式:**在根 span 结束时评估。只考虑该时间点可用的数据——span 名称和属性。
在两种模式下,匹配都会阻止记录或发送该 span。由于流式模式下最早可能在 span 开始时进行匹配,因此只有 span 名称和 span 开始时设置的属性能够保证可用——不要依赖 span 生命周期后期添加的属性。
Sentry.init({
traceLifecycle: 'stream',
ignoreSpans: [
// String match against span name
'/health',
'/ready',
// RegExp match against span name
/^OPTIONS /,
// Object filter — all conditions must match
{
op: 'middleware.handle',
name: /^corsMiddleware/,
},
// Filter by attributes (string = substring match, RegExp for patterns)
{
op: 'http.server',
attributes: {
'http.route': /^\/internal\//,
},
},
],
});
筛选器对象的属性:
| 属性 | 类型 | 匹配对象 |
|---|---|---|
name | string | RegExp | span 名称(description) |
op | string | RegExp | span 操作 |
attributes | Record<string, string | RegExp | number | boolean | Array> | span 属性 |
筛选器对象指定了多个属性时,必须全部匹配,该 span 才会被忽略。
2.5 设置浏览器性能分析(可选)
在浏览器中使用 span 流式传输时,请使用v2 性能分析选项,而不是旧版 profilesSampleRate。旧版选项已弃用,且无法与 span 流式传输生命周期集成。
添加 browserProfilingIntegration() 并配置以下两个 v2 选项:
// Before (legacy profiling — do NOT use with span streaming)
Sentry.init({
integrations: [
Sentry.browserTracingIntegration(),
],
tracesSampleRate: 1.0,
profilesSampleRate: 0.5, // deprecated
});
// After (v2 profiling with span streaming)
Sentry.init({
integrations: [
Sentry.spanStreamingIntegration(),
Sentry.browserTracingIntegration(),
Sentry.browserProfilingIntegration(),
],
tracesSampleRate: 1.0,
profileSessionSampleRate: 1.0,
profileLifecycle: 'trace',
});
v2 性能分析选项:
| 选项 | 类型 | 说明 |
|---|---|---|
profileSessionSampleRate | number(0–1) | 启用性能分析的用户会话百分比。默认值:0(禁用)。 |
profileLifecycle | 'trace' | 'manual' | 'trace':当存在经过采样的根 span 时,分析器会自动运行。'manual':通过 Sentry.uiProfiler.startProfiler() / stopProfiler() 显式启动/停止分析器。默认值:'manual'。 |
profileLifecycle: 'trace' 要求启用追踪(配置 tracesSampleRate 或 tracesSampler)。分析器会在根 span 开始时启动,并在不再有经过采样的根 span 时停止。性能分析数据块每 60 秒独立发送一次,或在最后一个根 span 结束时发送。
不要混用旧版选项和 v2 选项。如果设置了 profilesSampleRate,profileSessionSampleRate 将不起作用,SDK 也会记录一条警告。
阶段 3:验证
应用更改后,验证迁移是否正常运行。
3.1 构建检查
# TypeScript check
npx tsc --noEmit 2>&1 | head -30
# Build
npm run build 2>&1 | tail -20
3.2 运行时验证
指导用户在浏览器开发者工具或服务器日志中进行验证:
- 检查网络面板:Span 信封应以单独请求的形式出现,内容类型为
application/vnd.sentry.items.span.v2+json,而不是事务信封 - 检查 Sentry 控制面板:Span 完成后不久应出现在 Traces 视图中,无需等待整个事务结束
- 检查回退警告:如果 SDK 记录了有关回退到静态模式的警告,则可能是
beforeSendSpan回调缺少withStreamedSpan包装器
3.3 常见问题
| 症状 | 原因 | 修复方法 |
|---|---|---|
| SDK 回退到静态模式 | beforeSendSpan 未使用 withStreamedSpan 包装 | 包装回调:Sentry.withStreamedSpan(callback) |
未调用 beforeSendTransaction | 流式模式下的预期行为 | 将逻辑迁移到 beforeSendSpan 或 ignoreSpans |
| Span 仍以事务形式到达 | 未设置 traceLifecycle 或缺少集成 | 服务端:添加 traceLifecycle: 'stream';浏览器:添加 spanStreamingIntegration() |
span.description 出现类型错误 | StreamedSpanJSON 使用的是 name,而不是 description | 在回调中将 span.description 改为 span.name |
span.data 出现类型错误 | StreamedSpanJSON 使用的是 attributes,而不是 data | 在回调中将 span.data 改为 span.attributes |
profileSessionSampleRate 不起作用 | 同时设置了旧版 profilesSampleRate | 移除 profilesSampleRate,仅使用 profileSessionSampleRate + profileLifecycle |
快速参考(JavaScript)
最简服务端配置
import * as Sentry from '@sentry/node';
Sentry.init({
dsn: '__DSN__',
tracesSampleRate: 1.0,
traceLifecycle: 'stream',
});
最简浏览器配置
import * as Sentry from '@sentry/browser';
Sentry.init({
dsn: '__DSN__',
integrations: [
Sentry.spanStreamingIntegration(),
Sentry.browserTracingIntegration(),
],
tracesSampleRate: 1.0,
});
配置性能分析的浏览器设置
import * as Sentry from '@sentry/browser';
Sentry.init({
dsn: '__DSN__',
integrations: [
Sentry.spanStreamingIntegration(),
Sentry.browserTracingIntegration(),
Sentry.browserProfilingIntegration(),
],
tracesSampleRate: 1.0,
profileSessionSampleRate: 1.0,
profileLifecycle: 'trace',
});
完整迁移检查清单
- SDK 版本为
>=10.53.1 - 服务端配置:已添加
traceLifecycle: 'stream' - 浏览器配置:已添加
spanStreamingIntegration() -
beforeSendSpan回调已使用Sentry.withStreamedSpan()包装 -
beforeSendSpan回调已更新:description->name,data->attributes -
beforeSendTransaction逻辑已迁移到beforeSendSpan或ignoreSpans - 已从配置中移除
beforeSendTransaction - (如果使用性能分析)已将
profilesSampleRate替换为profileSessionSampleRate+profileLifecycle - (如果使用性能分析)已将
browserProfilingIntegration()添加到集成列表 - 构建通过,且无类型错误
- Span 在 Sentry 控制面板中可见