导读:本期聚焦于阿亮创作的《MongoDB聚合管道$listSessions怎么用?列出会话的操作详解》,敬请观看详情。会话是MongoDB中容易被人忽略但又十分重要的机制,复制集写操作、事务、因果一致性都依赖它。想知道当前实例上到底挂着哪些会话、各自的状态和过期时间是什么,$listSessions这个聚合阶段就派上用场了。本文从会话的基本概念讲起,说明$listSessions的作用范围与权限要求,给出直接调用以及配合$lookup关联users信息的完整示例,同时讲解过滤超时会话、统计会话数量的实用技巧,并列出常见的报错原因和排查思路,帮助你更好地管理和监控MongoDB的会话资源。

MongoDB从3.6版本开始引入了可重试写入、因果一致性和多文档事务,这些特性的背后都离不开一个共同的基础设施——会话(Session)。会话由服务端统一管理,保存在config.system.sessions集合以及每个实例的内存缓存中。当需要排查连接占用、事务残留或者只想看看当前有哪些活跃会话时,聚合管道阶段$listSessions就是官方提供的标准查询手段。这篇文章详细介绍它的使用方法、权限要求以及一些实用技巧。

MongoDB聚合管道$listSessions怎么用?列出会话的操作详解

$listSessions的基本概念与作用范围

首先要明确一点,$listSessions是聚合管道的一个阶段,而不是普通的查询命令。它只能作为aggregate操作的第一个阶段出现,如果放在其他阶段后面会直接报错。它的作用是把当前MongoDB实例内存缓存中的所有会话以文档流的形式吐出来,后续可以继续接$match、$project、$group等阶段做进一步处理。

这个阶段有个孪生兄弟叫$listLocalSessions。两者的区别在于:在副本集或分片集群环境中,$listSessions返回的是整个集群范围内缓存的会话(本质上依赖路由节点汇总),而$listLocalSessions只返回当前连接的那个节点本地缓存的会话。在单节点环境下两者结果基本一致,但在生产集群中排查问题时,分清这两个阶段的差别非常关键。

每个会话文档包含几个重要字段:_id是会话的UUID标识,lastUse记录最近一次使用时间,lastUseChopTime是内部维护的时间戳。如果会话正在执行事务,还会有transaction字段携带事务状态信息。理解这些字段是后续做过滤和统计的基础。

基本用法与代码示例

最直接的用法是对admin数据库执行聚合,注意$listSessions必须在admin库上运行,否则会报错。先给一个最简单的例子,列出当前所有会话:

use admin
db.aggregate([
  { $listSessions: {} }
])

参数传空对象表示不加任何过滤条件。你也可以传入{ allUsers: true }来列出所有用户的会话,但这个操作需要额外的权限,普通用户执行会抛出Unauthorized错误。还可以传入{ users: [ { user: "appUser", db: "admin" } ] }来只查看指定用户的会话,这在多业务共用一个集群时特别有用。

实际排查中很少需要看全部字段,通常会配合$match过滤掉已经超时的会话。会话默认超时时间是30分钟,可以通过服务端参数localLogicalSessionTimeoutMinutes调整。下面的例子筛选出最近十分钟内活跃的会话,并只保留关键信息:

use admin
db.aggregate([
  { $listSessions: { allUsers: true } },
  { $match: {
      lastUse: { $gte: new Date(Date.now() - 10 * 60 * 1000) }
  }},
  { $project: {
      _id: 1,
      lastUse: 1,
      username: 1
  }}
])

如果要统计当前活跃会话的数量,在管道末尾接一个$count阶段即可。这种写法在编写监控脚本时很方便,配合定时任务就能实现对会话数量的持续观测。

权限要求与常见报错排查

$listSessions对权限有明确要求。默认情况下,不传allUsers参数时,用户只能看到自己创建的会话;想要查看所有用户的会话,执行者必须拥有listAnySession权限动作,通常内置角色clusterManager或者自建包含该动作的角色可以满足。如果你的账户权限不足,会收到类似not authorized on admin to execute command的错误提示。

另一个常见报错是Unauthorized搭配错误信息listSessions may only be run against the admin database,这说明你没有切换到admin库。因为会话信息属于集群级元数据,MongoDB强制要求这类操作在admin库上执行,这一点和currentOp等命令的要求是一致的。

还有一种情况是管道阶段位置放错了。比如有人把$listSessions放在$match后面,会收到$listSessions is only valid as the first stage in a pipeline的报错。记住它必须是管道的第一个阶段,这一点在驱动程序中拼装管道时尤其容易疏忽。另外,如果查询结果里看到大量lastUse很旧的会话不必紧张,它们只是还没被后台清理任务回收,超过超时时间后MongoDB会自动将其标记为过期并清理。

实用技巧:结合$lookup关联用户信息

会话文档中的_id字段本身只有UUID,直接看并不知道是哪个业务建立的。这时可以利用$lookup把会话与config.system.sessions集合或者其他业务数据关联起来。下面演示一个将活跃会话按用户名分组统计的例子:

use admin
db.aggregate([
  { $listSessions: { allUsers: true } },
  { $group: {
      _id: "$username",
      sessionCount: { $sum: 1 },
      latestUse: { $max: "$lastUse" }
  }},
  { $sort: { sessionCount: -1 } }
])

这个管道可以快速回答“哪个用户持有的会话最多”这类问题。如果某个应用存在会话泄漏(比如驱动配置不当导致不断创建新会话而不复用),通过这个统计就能第一时间发现异常增长的用户,进而定位到具体的应用实例。

需要注意的是,$listSessions返回的是内存缓存中的快照,不保证强一致性,在会话数量极大的集群上执行也可能带来一定开销。建议在监控场景下控制执行频率,必要时优先使用$listLocalSessions缩小范围。掌握了这些用法之后,无论是日常运维还是故障排查,你都能对集群中的会话状况做到心中有数。

MongoDB聚合管道$listSessions修改时间:2026-09-10 22:06:39

免责声明:已尽一切努力确保本网站所含信息的准确性。网站作品多为原创整理与精心创作,观点力求客观中立。本站旨在免费分享,内容仅供个人学习、研究或参考使用。若引用了第三方作品,版权归原作者所有。如内容涉及您的权益,请联系我们进行处理Email:chomcom@qq.com。
引用或转载本作品时,请注明当前出处:https://www.ipipp.com/html/0910/54297.html,基于非商业用途的前提下,欢迎转载或二创本作品。
内容垂直聚焦
专注技术核心技术栏目,确保每篇文章深度聚焦于实用技能。从代码技巧到架构设计,为用户提供无干扰的纯技术知识沉淀,精准满足专业提升需求。
知识结构清晰
覆盖从开发到部署的全链路。AI、前端、编程、数据库、服务器、建站、系统层层递进,构建清晰学习路径,帮助用户系统化掌握开发与运维所需的核心技术。
深度技术解析
拒绝泛泛而谈,深入技术细节与实践难点。无论是数据库优化还是服务器配置,均结合真实场景与代码示例进行剖析,致力于提供可直接应用于工作的解决方案。
专业领域覆盖
精准对应开发生命周期。从前端界面到后端编程,从数据库操作到服务器运维,形成完整闭环,一站式满足全栈工程师和运维人员的技术需求。
即学即用高效
内容强调实操性,步骤清晰、代码完整。用户可根据教程直接复现和应用于自身项目,显著缩短从学习到实践的距离,快速解决开发中的具体问题。
持续更新保障
专注既定技术方向进行长期、稳定的内容输出。确保各栏目技术文章持续更新迭代,紧跟主流技术发展趋势,为用户提供经久不衰的学习价值。