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

Express Morgan日志器:如何记录未转义的查询字符串?

如何用Morgan记录未转义的查询字符串

绝对可以!Morgan的灵活性很强,你完全可以通过自定义日志token来实现记录未转义(或解码后)的查询字符串。下面是几种实用的方案:

方案1:直接截取原始查询字符串

Express的req.url(或req.originalUrl)保留了请求的原始URL,包括服务器接收到的编码后的查询字符串。我们可以自定义一个token来提取这部分内容:

const express = require('express');
const morgan = require('morgan');
const app = express();

// 自定义token:获取原始查询字符串(含?前缀)
morgan.token('raw-query', (req) => {
  const queryStartIndex = req.url.indexOf('?');
  return queryStartIndex !== -1 ? req.url.slice(queryStartIndex) : '';
});

// 用自定义token构建日志格式
app.use(morgan(':method :url :raw-query :status :response-time ms'));

// 测试路由
app.get('/demo', (req, res) => res.send('Success!'));

app.listen(3000);

当发起请求http://localhost:3000/demo?name=John%20Doe&tag=dev%23123时,日志会输出:

GET /demo?name=John%20Doe&tag=dev%23123 ?name=John%20Doe&tag=dev%23123 200 1.234 ms

方案2:记录解码后的可读查询字符串

如果你的需求是把编码字符(比如%20转空格、%23转#)显示为人类可读的格式,可以在自定义token里用decodeURIComponent解码:

// 自定义token:获取解码后的查询字符串
morgan.token('decoded-query', (req) => {
  const queryStartIndex = req.url.indexOf('?');
  if (queryStartIndex === -1) return '';
  const encodedQuery = req.url.slice(queryStartIndex);
  return decodeURIComponent(encodedQuery);
});

// 用引号包裹查询字符串,避免特殊字符干扰日志格式
app.use(morgan(':method :url "%decoded-query" :status :response-time ms'));

同样的请求,日志会输出:

GET /demo?name=John%20Doe&tag=dev%23123 "?name=John Doe&tag=dev#123" 200 1.567 ms

方案3:直接记录完整未转义URL

如果不需要拆分查询字符串,想直接记录整个原始URL,可以用req.originalUrl自定义token:

morgan.token('raw-full-url', (req) => req.originalUrl);

app.use(morgan(':method :raw-full-url :status :response-time ms'));

日志会直接输出完整的原始请求URL:

GET /demo?name=John%20Doe&tag=dev%23123 200 1.123 ms

注意事项

  • 如果查询字符串包含空格、引号等特殊字符,解码后可能干扰日志格式解析,建议用引号包裹查询字符串部分(如方案2所示)。
  • req.url可能被部分中间件修改,req.originalUrl始终保留请求的原始URL,可靠性更高。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.19 10:25:22