@arms/rum-browser-nuxt

Nuxt plugin for @arms/rum-browser SDK (Nuxt 3/4 file-route view tracking + dual-channel error capture, zero nuxt/vue/vue-router imports)
511
Install
npm install @arms/rum-browser-nuxt
Latest Version:0.1.1
Vue:3
License:ISC
Last Updated:Sep 1, 2026
Links: npm
Maintainer: fengsir

@arms/rum-browser-nuxt

Nuxt 插件 for @arms/rum-browser RUM SDK —— 支持 Nuxt 3 / Nuxt 4(Vue 3.5+、vue-router v4 / v5)。

能力范围:

  • 文件路由风格的视图追踪:经 router.afterEach 驱动 Shell.startView(手动 view 模式),view.name 反向归一化为 Nuxt 文件路由风格(/user/:id() → /user/[id]),与 pages/ 目录心智一致、聚合稳定
  • Nuxt 双通道异常捕获:链式包装 vueApp.config.errorHandler(保留原 handler)+ nuxtApp.hook('app:error')(Nuxt 启动 / SSR 传播错误),同一错误对象 WeakSet 去重只报一次,自动上报 source: 'vue' 的异常事件(snapshots 内携带 framework: 'nuxt')
  • 手动错误上报:addNuxtError(error, context?) 供 onErrorCaptured / 自定义 errorHandler 场景转发

不含:组件性能监控、hydration 错误分级、Nuxt Module 形态、Nitro 服务端集成(均为非目标,见 docs-dev/browser-nuxt-spec.md)。

安装

本插件不独立工作 —— 需与主包 @arms/rum-browser(必需 peer dependency)同时安装,并完成主包初始化:

npm install @arms/rum-browser @arms/rum-browser-nuxt

发布前置条件

发布顺序(严格按序,前一步发版在 registry 生效后,再发布下一步):

  1. @arms/rum-core@>=0.1.11:含 Shell.startView 与 IConfiguration.trackViewsManually 能力的发版(已在 npm registry 发布)
  2. @arms/rum-browser@>=0.1.16:含 PvCollector 手动模式防护(trackViewsManually 早退,避免双发 PV)的发版(已在 npm registry 发布)
  3. @arms/rum-browser-nuxt(本包)

本包为独立实现(不依赖 @arms/rum-browser-vue / @arms/rum-browser-react,dependencies 为空),无兄弟包解锁约束;peerDependencies 下限与 registry 实际产物对齐,外部安装可正常解析。后续版本迭代仍需遵循上述发布顺序(依赖包发版在 registry 生效后,再发布本包)。仓库内开发期经 workspace 直链源码使用(无需等待发版),安装依赖请遵循仓库惯例使用 yarn 或 scripts/bootstrap.sh。

快速开始

在 Nuxt 项目中创建客户端插件文件(.client.ts 后缀保证仅在客户端执行):

// plugins/arms-rum.client.ts
import ArmsRum from '@arms/rum-browser';
import { initNuxtPlugin } from '@arms/rum-browser-nuxt';

export default defineNuxtPlugin({
  name: 'arms-rum',
  // enforce: 'pre' 保证本插件先于其他插件执行,
  // 错误双通道可捕获后续插件的启动错误
  enforce: 'pre',
  setup() {
    ArmsRum.init({
      endpoint: 'https://your-endpoint',
      // pid: 'your-pid',
    });
    initNuxtPlugin(ArmsRum, {
      router: useRouter(), // 必填:驱动视图采集
      nuxtApp: useNuxtApp(), // 推荐:启用错误双通道
    });
  },
});

时序说明:initNuxtPlugin 不依赖 armsRum.init() 完成 —— 可在 init 前后任意时序同步调用,先后顺序可互换(反向时序经内部 pending 队列兜底,首屏 view 与排队错误不丢失)。defineNuxtPlugin / useRouter / useNuxtApp 均为 Nuxt 自动导入 —— 本包源码零 nuxt / vue / vue-router 导入(SSR-safe),router / nuxtApp 由用户在 setup() 中取好后传入。

视图命名规则

view.name 按 to.matched 尾向头取第一个非空 path(最深匹配段即页面本身的模板),再反向归一化为 Nuxt 文件路由风格:

vue-router 路由模板(matched.path) view.name(Nuxt 文件路由风格) 对应 pages/ 目录
/users /users pages/users.vue
/user/:id() /user/[id] pages/user/[id].vue
/blog/:slug? /blog/[[slug]] pages/blog/[[slug]].vue
/:slug(.*)* /[...slug] pages/[...slug].vue
/:pathMatch(.*)* /[...pathMatch] pages/[...pathMatch].vue
/users-:group()-:id() /users-[group]-[id] pages/users-[group]-[id].vue
嵌套路由(父 '' + 子 /user/:id()) /user/[id](尾向头取最深段) pages/user/[id].vue

静态路由原样保留;转义字符还原为字面量(\: → :)。

路由语义

警告:router 必填 —— 传入后 view/PV 完全由 afterEach 驱动,主包自动 PV 被禁用

插件在 nuxtCollector.setup 中注入 trackViewsManually: true:主包 PvCollector 跳过首屏 PV 与 history 拦截(避免双发),view 的创建、命名、计时完全依赖 router.afterEach 驱动(内部调用 shell.startView)。

导航语义(对齐 Nuxt 场景约定):

导航场景 是否开新视图 说明
首次导航 / 首屏 ✅ initial_load;init 前触发经 pending 队列补发
路径变化 ✅ route_change(ctx 已有 view 时;否则 initial_load)
query 变化(path 与 hash 不变) ❌ 跳过 /list?page=1 → /list?page=2 不算新视图
hash 变化(path 不变) ❌ 去重 /doc#section-a → /doc#section-b afterEach 放行但视图名不变,经 Shell.startView 同名去重后无新 view 事件(与 browser-vue 行为一致)
导航失败(afterEach 第三参 failure) ❌ 跳过 guard 拦截 / 取消等不算新视图
同名重复导航 ❌ 去重 Shell.startView 内建同名去重

异常捕获说明

nuxtApp 传入时启用双通道自动接管:

  • 通道 1:链式包装 nuxtApp.vueApp.config.errorHandler —— 先经 addNuxtError 上报,再调用你已有的 handler(保留 Nuxt 自带 handleVueError 驱动错误页的行为;无原 handler 时保持 Vue 默认的 console.error 可见性,不吞错)
  • 通道 2:nuxtApp.hook('app:error') 捕获 Nuxt 启动 / SSR 传播错误(纯 Vue 场景不存在的 Nuxt 独有通道;插件 enforce: 'pre' 时可捕获后续插件启动错误)
  • 去重:同一错误对象(引用相等)经双通道只报一次(WeakSet);非 object 错误值无引用语义,不去重

上报字段:

{
  event_type: 'exception',
  type: 'error',
  source: 'vue',                 // 复用家族 vue 错误存储/查询链路
  name: 'TypeError',             // error.name(非 Error 值自动 normalize)
  message: "Cannot read properties of undefined",
  stack: '...',
  // 扩展信息收敛为单一 JSON 字符串字段(值为 undefined 的内部键不会出现)
  snapshots: JSON.stringify({
    handling: 'handled',
    framework: 'nuxt',           // 本包标识,恒定携带
    component_stack: 'at <OrderList>\nat <UserPage>',  // 当前组件在前,沿父链向上
    component_name: 'OrderList',
    lifecycle_hook: 'hook:mounted',  // Vue errorHandler 的 info 参数
  }),
  times: 1,
}

也可在 onErrorCaptured / 自定义 errorHandler 中手动上报(双通道已接管时无需重复调用):

import { addNuxtError } from '@arms/rum-browser-nuxt';

// 组件内
onErrorCaptured(function (err, instance, info) {
  addNuxtError(err, { lifecycle_hook: info });
  return false;
});

API

主入口 @arms/rum-browser-nuxt(单入口,无子入口)

导出 说明
initNuxtPlugin(shell: Shell, options: NuxtPluginOptions) 初始化插件(collector 注册 + 路由视图采集 + 条件启用错误双通道)
addNuxtError(error: unknown, context?: NuxtErrorContext) 手动上报 Nuxt 异常(component_stack / component_name / lifecycle_hook 可选)
type NuxtPluginOptions / NuxtErrorContext 等 公共类型(duck typing,版本无关)

NuxtPluginOptions

initNuxtPlugin(shell, options) 的第二参数(源 src/types/index.ts):

字段 类型 必填 说明
router AnyRouter 是 vue-router 实例(v4 / v5 均可,useRouter() 取得,仅依赖 afterEach / currentRoute 最小接口)。驱动 view 生命周期(手动 view 模式:注入 trackViewsManually + 调用 Shell.startView)
nuxtApp NuxtAppLike 否 NuxtApp 实例(useNuxtApp() 取得)。提供时启用错误双通道自动接管;不提供时仅启用路由视图采集,错误可经 addNuxtError 手动上报

NuxtErrorContext

addNuxtError 的第二参数(字段对齐 @arms/rum-browser-vue 的 VueErrorContext):

字段 类型 说明
component_stack string 组件链栈,如 'at <OrderList>\nat <UserPage>'(当前组件在前)
component_name string 出错组件名
lifecycle_hook string 生命周期钩子 / 错误来源信息(Vue errorHandler 的 info 参数,如 'hook:mounted')

版本要求

依赖 版本要求 说明
@arms/rum-core >=0.1.11 含 Shell.startView 与 IConfiguration.trackViewsManually(已发布)
@arms/rum-browser >=0.1.16 含 PvCollector 手动模式防护(已发布)
nuxt 3(>=3.7)|| 4 optional peer;3.7 起 defineNuxtPlugin 对象语法与 enforce 稳定
vue ^3.5.0 optional peer;本包经 nuxtApp.vueApp.config.errorHandler duck typing 访问,不直接依赖 vue 模块
vue-router ^4.0.0 || ^5.0.0 optional peer;仅依赖 afterEach / currentRoute 最小接口

版本口径说明:peerDependencies 中 nuxt 声明为 3 || 4,实际支持基线为 Nuxt ≥3.7 —— 更早版本的 defineNuxtPlugin 对象语法与 enforce 不稳定。vue peer 为 ^3.5.0,而 Nuxt 3.7-3.12 生态常配 vue 3.3 / 3.4 —— 三项框架 peer 均 optional(peerDependenciesMeta 标记),版本不满足仅产生安装告警、不阻塞安装(插件对框架实例 duck typing,实际兼容宽于声明口径)。

Nuxt 2 用户

Nuxt 2 / Vue 2 已 EOL(插件体系完全不同),本包不支持。请使用通用包 @arms/rum-browser(自动 PV + 全局异常采集,无 Nuxt 专属能力),或升级到 Nuxt 3 后接入本包。

已知限制

以下限制是当前 MVP 设计所固有的,后续版本计划改进。

单实例约束

插件为 collector 级单例(模块级状态持有 shell / ctx 引用)。重复调用 initNuxtPlugin 传入另一个 rum 实例时会打印 logger.warn 并跳过重复注册、仅刷新 shell 引用 —— 最后一次绑定的实例生效。微前端多子应用各自持有独立 RUM 实例的场景暂不支持。

source='vue' 错误不受 collectors.jsError 采样管控

本包上报的错误携带 source: 'vue',browser SDK 的 SessionProcessor 采样键映射当前不覆盖 'vue'(与 browser-vue 包同款已知约束)——这些错误会绕过 collectors.jsError 采样配置。如需禁用,请使用 collectors.exception(设置为 false)。另外,core reporter 对 exception 按 getErrorID(message + stack) 聚合且 key 不含 source —— 同一错误被全局通道与插件双通道捕获时会聚合合并;自动通道错误可经 filters.exception 过滤以保留富上下文事件。

errorHandler 覆盖边界

  • 组件 onErrorCaptured 返回 false:按 Vue 语义该错误被视为"已处理"并阻止传播,全局 errorHandler 不会触发 —— 插件捕获不到(Vue 框架行为);需观测时请在 onErrorCaptured 中手动调用 addNuxtError;
  • warnHandler 不覆盖:Vue 运行时警告不进入 RUM 异常事件;
  • unhandledrejection:由主包 @arms/rum-browser 的 jsError 采集器覆盖,无需本插件处理;
  • hydration mismatch 明细:Vue errorHandler 不捕获(vuejs/core#13154),不做监控承诺。

错误页为全新页面加载

Nuxt 渲染 error.vue 属全新页面加载,插件与会话上下文随之重置 —— 错误后首屏 view 重新计为 initial_load。

无 pages/ 目录的应用

仅单 app.vue 的 Nuxt 应用没有路由实例,插件因缺少有效 router 整体禁用(logger.error 自监控上报),仅 addNuxtError 手动错误上报可用。

错误去重窗口语义

双通道去重按 app 生命周期(WeakSet 按错误对象引用)—— 同一 Error 实例二次抛出会被去重丢弃。

初始化时序

initNuxtPlugin 可在 armsRum.init() 前后任意时序同步调用。初始化完成之前调用 addNuxtError 时安全降级:插件未接入则 warn + skip(不抛错);插件已接入但 init 未完成则排队,init 完成后自动补发。init 前触发的路由导航经 pending 队列兜底,collector setup 后自动补发首个 view(loading_type: 'initial_load'),首屏不丢失。

兼容性

环境 支持情况 说明
Vite / webpack 5 等 ✅ 经 exports 字段解析单入口(types / import / require / default 四条件)
SSR(Nuxt 服务端) ✅ 安全 源码零 nuxt / vue / vue-router 导入、零顶层 window / document 访问(唯一 DOM 触点 getCurrentUrl 在函数内 try-catch 防护);配合 .client.ts 后缀约定使用
CDN / <script> 标签 ❌ 不适用 本包不出 UMD dist 产物,仅经 bundler 消费 —— CDN 场景请直接使用主包 @arms/rum-browser

产物压缩说明:es / lib 产物已经过 terser 压缩与混淆,且不附带 sourcemap(与 browser-vue / browser-nextjs 包一致的体积/混淆 trade-off)。排查线上堆栈时请对照仓库源码与 CHANGELOG 版本定位对应发布版本。

Related Packages

nuxt-yup

yup implementation for nuxt

2,981 4
@errorgap/nuxt

Nuxt module for Errorgap error tracking (client and server).

988 0
nuxt-monitor

Local-first error monitoring for Nuxt. No DSN, no account, no sourcemap upload.

1,619 1
nuxt-google-auth

Google Identity Services integration for Nuxt 3 & 4 with a simple composable and...

19,921 3

Version History

Version Released Vue License
0.1.1 ^3.5.0 ISC
0.1.0 ^3.5.0 ISC