Docs 菜单
Docs 主页
/
MongoDB Manual
/ / /

用于自托管部署的 UNIX 设置ulimit

在此页面上

  • 资源利用
  • 审查和设置资源限制

大多数 UNIX 这样的操作系统(包括 Linux 和 macOS)都提供了基于每个进程和每个用户限制和控制使用系统资源(例如线程、文件和网络连接)的方法。这些“ulimit”可防止单个用户使用过多的系统资源。有时,这些限制的默认值较低,可能会在 MongoDB 正常操作过程中导致许多问题。

mongodmongos 分别使用线程和文件描述符来跟踪连接和管理内部操作。本节概述了 MongoDB 的一般资源利用模式。将这些数字与有关您的部署及其用途的实际信息相结合,以确定理想的 ulimit 设置。

一般来说,所有的 mongodmongos 实例都会:

  • 使用两个文件描述符一个线程跟踪每个传入连接。

  • 像系统进程那样跟踪每个内部线程或 pthread

  • mongod 实例使用的每个数据文件都有 1 个文件描述符。

  • mongodstorage.journal.enabledtrue 时, 实例使用的每个日志文件有 1 个文件描述符。

  • 在副本集中,每个 mongod 都与副本集的所有其他节点保持连接。

mongod 为许多内部进程(包括 TTL 集合、复制和副本集运行状况检查)使用后台线程,这可能需要少量其他资源。

除了用于客户端连接的线程和文件描述符外,mongos 还必须与所有配置服务器和所有分片(包括所有副本集的所有节点)保持连接。

对于 mongos,请考虑以下行为:

  • mongos 实例维护一个与每个分片的连接池,这样 mongos 就可以重复使用连接并快速完成请求,而无需创建新的连接。

  • 您可以使用 net.maxIncomingConnections 运行时选项来限制传入连接数。通过限制传入连接数,可以防止 mongosmongod 实例上创建过多连接的级联效应。

您可以在系统提示符使用 ulimit 命令检查系统限制,如下例所示:

$ ulimit -a
-t: cpu time (seconds) unlimited
-f: file size (blocks) unlimited
-d: data seg size (kbytes) unlimited
-s: stack size (kbytes) 8192
-c: core file size (blocks) 0
-m: resident set size (kbytes) unlimited
-u: processes 64000
-n: file descriptors 64000
-l: locked-in-memory size (kb) unlimited
-v: address space (kb) unlimited
-x: file locks unlimited
-i: pending signals 192276
-q: bytes in POSIX msg queues 819200
-e: max nice 30
-r: max rt priority 65
-N 15: unlimited

ulimit 是指每个用户在各种资源方面的限制。因此,如果您的 mongod 实例以同时运行多个进程或多个 mongod 进程的用户身份执行,则可能会出现对这些资源的争用。另外,请注意 processes 值(即-u)是指不同进程和子进程线程的总数量。

在 Linux 上,您可以通过发出以下形式的命令来更改 ulimit 设置:

ulimit -n <value>

ulimit 有“硬”限制和“软”限制两种,它们都会影响 MongoDB 的性能。“硬”ulimit 是指用户在任何时间都可以拥有的最大活动进程数。这是上限:任何非 root 进程都无法提高“硬”ulimit。相反,“软”ulimit 是实际强制执行的会话或进程限制,但任何进程都可以将其提高,直到达到“硬”ulimit 允许的最大值。

如果连接数增长过高,较低的“软”ulimit 可能会导致 can't create new thread, closing connection 错误。因此,请务必将这ulimit 值均设置为推荐值。

ulimit 将同时修改“硬”和“软”值,除非在修改限制值时指定了 -H-S 修饰符。

对于许多 Linux 发行版,您可以通过将 -n 选项替换为 ulimit -a 输出中任何可能的值来更改值。

更改 ulimit 设置后,您必须重新启动该进程才能使用修改后的设置。在 Linux 上,您可以使用 /proc 文件系统来查看正在运行的进程的当前限制。

使用 ulimit 对系统限制所做的任何更改都可能会在系统重新启动后恢复,取决于您的系统配置和默认设置。检查您的发行版和操作系统文档,了解更多信息。

您通常应该使用 systemctl 启动 mongod,其中使用了 ulimit 设置:

systemctl start mongod.service

如果使用 systemctl 启动 mongodsystemd 将会覆盖一些 ulimit 设置。例如,如果按以下命令中的方式启动 mongod,则会使用用户切片(例如 user-1000.slicesystemd 设置:

mongod --config ~/mongod.conf

注意

systemd 用户切片限制了用户进程的资源。

对于使用brew 安装方法安装了 MongoDB Community 的 macOS 系统,当您通过brew services启动 MongoDB 时,会自动设置推荐的打开文件值。 有关更多信息,请参阅使用 brew 运行 MongoDB

对于运行 MongoDb 企业或使用 TGZ 安装方法的 macOS 系统,请使用 launchctl limit 命令设置 推荐值。请参阅操作系统文档,了解在正在运行的系统上更改系统限制的详细过程。

Red Hat Enterprise Linux 以及 CentOS 6 和 7 强制实施单独的最大进程限制 nproc,该限制会覆盖 ulimit 设置。该值在以下配置文件中定义,具体取决于版本:

版本
file
RHEL / CentOS 7
4096
/etc/security/limits.d/20-nproc.conf
RHEL / CentOS 6
1024
/etc/security/limits.d/90-nproc.conf

要为这些版本配置 nproc 值,请创建一个名为 /etc/security/limits.d/99-mongodb-nproc.conf 的文件,并使用新的 soft nprochard nproc 值来提高进程限制。有关推荐的值,请参阅建议的 ulimit 设置。

对于 RHEL/CentOS 8,不再需要单独设置 nproc 值。在 RHEL/CentOS 8 上,ulimit 命令足以配置所需的最大进程数。

每个部署都可能有独特的要求和设置,但以下阈值和设置对 mongodmongos 部署尤为重要:

  • -f (文件大小): unlimited

  • -t (CPU 时间): unlimited

  • -v (虚拟内存):unlimited[1]

  • -l (锁定内存大小): unlimited

  • -n (打开文件): 64000

  • -m (内存大小):unlimited [1] [2]

  • -u (进程/线程): 64000

请谨记,更改 ulimit 设置后,务必要重启 mongodmongos 实例,以确保更改生效。

  • mongodmongos 实例的传入连接需要两个文件描述符。

  • 对于 macOS 平台,建议的进程限制为 2500,这是该平台可以配置的最大值。

对于使用 Upstart 的 Linux 发行版,如果您将 mongod 和/或 mongos 实例作为 Upstart 服务启动,则可以在服务脚本内指定限制。可以使用 limit 节段执行此操作。

指定推荐的 ulimit 设置,如下例所示:

limit fsize unlimited unlimited # (file size)
limit cpu unlimited unlimited # (cpu time)
limit as unlimited unlimited # (virtual memory size)
limit memlock unlimited unlimited # (locked-in-memory size)
limit nofile 64000 64000 # (open files)
limit nproc 64000 64000 # (processes/threads)

每个 limit 节段将“软”限制设置为指定的第一个值,并将“硬”限制设置为指定的第二个值。

更改 limit 节段后,请使用以下方法重新启动应用程序服务,以确保更改生效:

restart <service name>

如果您将 mongod 和/或 mongos 实例作为 systemd 服务启动,则可以在其服务文件的 [Service] 部分中指定限制。服务文件位于类似 /etc/systemd/system/<process-name>.service 的位置。

您可以使用 资源限制指令 来设置限制

指定推荐的 ulimit 设置,如下例所示:

[Service]
# Other directives omitted
# (file size)
LimitFSIZE=infinity
# (cpu time)
LimitCPU=infinity
# (virtual memory size)
LimitAS=infinity
# (locked-in-memory size)
LimitMEMLOCK=infinity
# (open files)
LimitNOFILE=64000
# (processes/threads)
LimitNPROC=64000

每个 systemd 限制指令都会将“硬”和“软”限制均设置为指定值。

更改 limit 节段后,请使用以下方法重新启动应用程序服务,以确保更改生效:

systemctl restart <service name>

注意

如果是通过软件包管理器(例如 yumapt)安装的 MongoDB,则自动安装的服务文件中已包含这些 ulimit 值。

注意

本节仅适用于 Linux 操作系统。

/proc 文件系统将每个进程的限制存储在位于 /proc/<pid>/limits 的文件系统对象中,其中 <pid> 为进程的 PID,即进程标识符。您可以使用以下 bash 函数返回具有给定名称的一个或多个进程的 limits 对象的内容:

return-limits(){
for process in $@; do
process_pids=`ps -C $process -o pid --no-headers | cut -d " " -f 2`
if [ -z $@ ]; then
echo "[no $process running]"
else
for pid in $process_pids; do
echo "[$process #$pid -- limits]"
cat /proc/$pid/limits
done
fi
done
}

您可以复制此函数并粘贴到当前 shell 会话中,或将其作为脚本的一部分加载。通过以下任一调用方式来调用该函数:

return-limits mongod
return-limits mongos
return-limits mongod mongos
[1](12) 如果在运行 MongoDB 的系统上限制虚拟内存或常驻内存大小,操作系统将会拒绝满足额外的分配请求。
[2] ulimit-m 参数对内核版本高于 2.4.30 的 Linux 系统不起作用。如果您愿意,可以省略 -m

后退

健康管理器