CLI

使用 evlog map 的可观测性评分

根据 evlog 日志规则检查受支持的入口点,了解评分,并在添加 CI 门禁前修复一个具体缺口

在修改日志记录之前,请检查哪些受支持的入口点满足 evlog 的日志检查。evlog map 会读取源文件,并报告缺少的上下文、结构化错误以及其他已识别的模式。它的评分总结的是这些静态检查,而不是你的应用程序中能够解释生产故障的部分所占的百分比。

首先检查受支持的范围

CLI 目前为 Nuxt、Nitro、Next.js、TanStack Start 和 Hono 提供适配器。请从应用程序包中运行它,而不是从未检测到框架的 monorepo 根目录运行。适配器无法为不受支持的 Node.js 项目评分。

你可以在不将 evlog 安装到项目中的情况下扫描受支持的项目。不过,wide-eventcontext 等检查会识别 evlog 约定。即使现有的 Pino 或 LogTape 插桩能够产出有用的日志,也可能获得较低的评分。请使用报告来规划 evlog 的采用,而不是用它来给日志库排名。

此命令会检查项目,但不会写入 evlog.map.json。本页面上的示例使用 CLI 0.6.2 进行检查:

Terminal
npx @evlog/[email protected] map --no-write

扫描不会执行处理程序,也不要求有流量。它只能看到其适配器能够识别的入口点和代码模式。在解读数字之前,请检查检测到的框架和入口点数量。

阅读一份真实报告

此输出来自仓库在提交 42eb1ab2 时的 Next.js 示例。它检测到了五个入口点,其中两个未通过要求:

evlog map
█▀█ ▀▀█   score /100              evlog-nextjs-example · Next.js
█▀█   █   ▰▰▰▰▰▰▰▰▰▰▰▰▰▰▰▰▰▱▱▱    5 entry points scanned
▀▀▀   ▀   good                    ▆▆█▁█

COVERAGE
● API handlers       ▰▰▰▰▰▰▰▰▰▱   92  1 of 3 have gaps
● Pages              ▰▰▰▰▰▰▰▰▱▱   80  1 swallows fetch errors
● Money & auth       ▰▰▰▰▰▰▰▰▱▱   75  missing audit trails

FIX FIRST
1. POST   /api/checkout $ — moves money with no audit trail
   app/api/checkout/route.ts:3 · evlog.dev/use-cases/audit/overview
2. PAGE   / — swallows fetch errors — users see a blank page
   app/page.tsx:1 · evlog.dev/learn/lifecycle

✓ Already solid: /api/error · /api/health
▲ 87 → 100 by fixing the 2 above

────────────────────────────
how this score works → evlog.dev/cli/scoring
▸ evlog map --all every entry point · evlog map <file> inspect one
  --min-score 80 CI gate

87/100 的评分是对这些入口点上的检查进行加权平均的结果。它并不意味着应用程序 87% 的执行路径都已覆盖。FIX FIRST 会突出显示需要检查的要求,而预计达到的 100 表示这些静态要求将会通过。但这并不能证明日志已交付到后端,或在事故期间有用。

评分参考规定了权重、聚合公式、等级和敏感性分类。规则解释了每项检查能够识别的内容。

修复一个上下文缺口

在安装了 evlog 的 Next.js App Router 应用程序中,此处理程序已包装以进行日志记录,但没有添加应用程序上下文:

app/api/hello/route.ts, before
import { withEvlog } from 'evlog/next'

export const GET = withEvlog(async (request: Request) => {
  const name = new URL(request.url).searchParams.get('name') ?? 'world'
  return Response.json({ message: `Hello ${name}` })
})

直接检查该文件:

Terminal
npx @evlog/[email protected] map app/api/hello/route.ts --no-write

context 要求未通过,因为处理程序没有已识别的 set() 调用。在不记录用户姓名的情况下,附加一个有用的决策:

app/api/hello/route.ts, after
import { useLogger, withEvlog } from 'evlog/next'

export const GET = withEvlog(async (request: Request) => {
  const log = useLogger()
  const name = new URL(request.url).searchParams.get('name') ?? 'world'
  log.set({ greeting: { personalized: name !== 'world' } })
  return Response.json({ message: `Hello ${name}` })
})

再次运行相同的命令。现在 context 要求通过,移除了 15 分的扣分。在这个独立示例中,路由评分从 85 提升到 100。在更大的应用程序中,全局变化取决于所有参与评分的入口点及其权重。

通过检查只能证明该模式存在。它无法判断 greeting.personalized 是否是事故调查所需的字段。请分别检查事件输出和所需的业务字段。

了解高评分未覆盖的内容

  • 源代码模式无法证明运行时执行、完整的错误路径覆盖,或成功交付到后端。
  • 敏感性分类使用导入和路由路径。请检查报告的原因,了解资金、身份验证或个人数据标记。
  • 当前 CLI 在找不到可评分入口点时也可能显示 100。空扫描不能证明存在插桩,因此请首先检查数量和范围。
  • 通过分析器无法识别的包装器或抽象层进行日志记录,可能会产生误报。在应用建议之前,请查看代码。

高评分有助于检查既定约定,同时还应结合运行时测试和抽样的生产事件。

审查基线后添加 CI 门禁

固定 CLI 版本,并保持分析的包、配置和排除项一致。规则变化可能会在应用程序没有修改的情况下改变评分。

提交经过审查的 evlog.map.json 基线,并使用 --baseline 检测现有入口点上已识别要求或评分的回归。它不会跟踪每个上下文字段:移除一个 set() 调用后,只要仍有另一个调用满足 context,就可能不会被检测到。新入口点也需要审查。当你希望为当前聚合评分设置下限时,添加 --min-score,但要注意平均值可能会掩盖某个较弱的路由。

CI 指南介绍退出代码和门禁配置。有关命令选项和报告格式,请参阅 map 参考