os 系统模块
os 模块是 Node.js 中内置的一个操作系统模块,它主要提供了对系统进行操作的一些方法,如获取内存信息、网络信息、系统名称、系统版本、系统目录等。
在 Node.js 中使用 os 模块之前,首先需要使用 require() 方法将 os 模块引入:
const os = require("os")方法速查表
| 方法 | 返回值类型 | 功能描述 |
|---|---|---|
freemem() | Number | 获取系统空闲内存(字节) |
totalmem() | Number | 获取系统总内存(字节) |
networkInterfaces() | Object | 获取网络接口信息 |
homedir() | String | 获取用户主目录 |
tmpdir() | String | 获取临时文件目录 |
hostname() | String | 获取主机名 |
type() | String | 获取操作系统类型 |
platform() | String | 获取操作系统平台 |
arch() | String | 获取 CPU 架构 |
release() | String | 获取系统发行版本 |
version() | String | 获取内核版本 |
uptime() | Number | 获取系统运行时间(秒) |
loadavg() | Array | 获取系统平均负载 |
cpus() | Array | 获取 CPU 信息 |
endianness() | String | 获取 CPU 字节序 |
userInfo() | Object | 获取当前用户信息 |
getPriority([pid]) | Number | 获取进程优先级 |
setPriority([pid], priority) | void | 设置进程优先级 |
availableParallelism() | Number | 获取可用并行度(v19.4.0+) |
获取内存相关信息
获取系统剩余内存 freemem
通过 os 模块的 freemem() 方法可以获取空闲的系统内存量,该方法返回一个整数(单位:字节)
os.freemem()返回值: 返回一个整数,表示空闲的系统内存量(单位:字节)
const os = require("os")
console.log("剩余内存:", os.freemem(), "B")
// 输出:剩余内存: 4485488640 B获取系统总内存 totalmem
通过 os 模块的 totalmem() 方法可以获取系统的总内存量,该方法返回一个整数(单位:字节)。
os.totalmem()返回值: 返回一个整数,表示系统的总内存量(单位:字节)
const os = require("os")
console.log("总内存:", os.totalmem(), "B")
// 输出:总内存: 17179869184 B综合示例:显示系统的内存使用情况
const os = require("os")
const freeMem = os.freemem() // 剩余内存(字节)
const totalMem = os.totalmem() // 总内存(字节)
const usedMem = totalMem - freeMem // 已使用内存(字节)
// 将单位转换为 GB
const freeGB = (freeMem / 1024 / 1024 / 1024).toFixed(2)
const totalGB = (totalMem / 1024 / 1024 / 1024).toFixed(2)
const usedGB = (usedMem / 1024 / 1024 / 1024).toFixed(2)
// 计算内存使用率
const usageRate = ((usedMem / totalMem) * 100).toFixed(2)
console.log("总内存:", totalGB, "GB")
console.log("已使用内存:", usedGB, "GB")
console.log("剩余内存:", freeGB, "GB")
console.log("内存使用率:", usageRate, "%")
// 输出示例:
// 总内存: 16.00 GB
// 已使用内存: 11.82 GB
// 剩余内存: 4.18 GB
// 内存使用率: 73.88 %获取网络相关信息
networkInterfaces
使用 os 模块可以获取计算机的网络信息,这需要通过 networkInterfaces() 方法实现,该方法的返回值是一个对象,该对象包含已分配了网络地址的网络接口信息。
语法:
os.networkInterfaces()返回值: 返回一个对象,包含网络接口信息
网络接口信息属性说明:
| 属性 | 类型 | 说明 |
|---|---|---|
| address | String | 一个字符串,用于指定分配的网络地址,即 IPv4 或 IPv6 |
| netmask | String | 一个字符串,指定 IPv4 或 IPv6 网络掩码 |
| family | String | 指定 Family 的字符串,值为 IPv4 或 IPv6 之一 |
| mac | String | 一个字符串,指定网络接口的 MAC 地址 |
| internal | Boolean | 布尔值,如果网络接口是不可远程访问的环回接口或类似接口,则为 true,否则为 false |
| scopeid | Number | 一个数字,指定 IPv6 的作用域 ID |
| cidr | String | 一个字符串,用于指定分配的 IPv4 或 IPv6 地址以及 CIDR 表示法中的路由前缀。如果网络掩码无效,则将其设置为 null |
示例:
const os = require("os")
console.log("该计算机的网络信息如下:\n")
console.log(os.networkInterfaces())获取本机 IP 地址的实用示例:
const os = require("os")
function getLocalIP() {
const interfaces = os.networkInterfaces()
for (const name of Object.keys(interfaces)) {
for (const iface of interfaces[name]) {
// 跳过内部(环回)地址和 IPv6 地址
if (iface.family === "IPv4" && !iface.internal) {
return iface.address
}
}
}
return "127.0.0.1"
}
console.log("本机 IP 地址:", getLocalIP())
// 输出:本机 IP 地址: 192.168.1.104networkInterfaces() 返回值的完整示例:
{
lo0: [
{
address: '127.0.0.1',
netmask: '255.0.0.0',
family: 'IPv4',
mac: '00:00:00:00:00:00',
internal: true,
cidr: '127.0.0.1/8'
},
{
address: '::1',
netmask: 'ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff',
family: 'IPv6',
mac: '00:00:00:00:00:00',
internal: true,
cidr: '::1/128',
scopeid: 0
}
],
en0: [
{
address: '192.168.1.104',
netmask: '255.255.255.0',
family: 'IPv4',
mac: '0e:7a:10:d8:77:1c',
internal: false,
cidr: '192.168.1.104/24'
}
]
// ... 其他网络接口
}获取系统相关目录
获取用户主目录 homedir
通过 os 模块的 homedir() 方法可以获取当前用户的主目录。
语法:
os.homedir()返回值: 返回一个字符串,表示当前用户的主目录路径
示例:
const os = require("os")
console.log("当前用户的主目录为:", os.homedir())
// macOS/Linux 输出:当前用户的主目录为: /Users/zhangzhengyang
// Windows 输出:当前用户的主目录为: C:\Users\username获取临时文件目录 tmpdir
通过 os 模块的 tmpdir() 方法可以获取本地计算机的临时文件目录。
语法:
os.tmpdir()返回值: 返回一个字符串,表示默认的临时文件目录路径
示例:
const os = require("os")
console.log("当前计算机的临时文件目录为:", os.tmpdir())
// macOS 输出:
// 当前计算机的临时文件目录为: /var/folders/kg/yy1xg95j3mvb05rd1m0r2dh40000gn/T
// Linux 输出:
// 当前计算机的临时文件目录为: /tmp
// Windows 输出:
// 当前计算机的临时文件目录为: C:\Users\username\AppData\Local\Temp获取系统相关信息
使用 os 模块可以获取与操作系统相关的信息,如主机名、系统名、系统 CPU 架构等。
系统信息方法总览
| 方法 | 返回值类型 | 说明 |
|---|---|---|
hostname() | String | 返回操作系统的主机名 |
type() | String | 返回操作系统名 |
platform() | String | 返回编译时的操作系统名 |
arch() | String | 返回操作系统的 CPU 架构 |
release() | String | 返回操作系统的发行版本 |
version() | String | 返回标识操作系统内核版本的字符串 |
loadavg() | Array | 返回一个包含 1、5、15 分钟平均负载的数组(UNIX 特定,Windows 返回 [0,0,0]) |
cpus() | Array | 返回一个对象数组,包含所安装的每个 CPU 内核的信息 |
uptime() | Number | 返回操作系统运行的时间,以秒为单位 |
endianness() | String | 获取 CPU 的字节序,可能返回的值为 BE(大端字节序)和 LE(小端字节序) |
getPriority(pid) | Number | 获取指定进程的调度优先级 |
setPriority(pid, priority) | - | 为指定的进程设置调度优先级 |
基础系统信息
hostname - 获取主机名
const os = require("os")
console.log("当前主机名:", os.hostname())
// 输出:当前主机名: MacBook-Pro.localtype - 获取操作系统类型
const os = require("os")
console.log("当前操作系统为:", os.type())
// Linux 输出:当前操作系统为: Linux
// macOS 输出:当前操作系统为: Darwin
// Windows 输出:当前操作系统为: Windows_NTplatform - 获取平台名称
const os = require("os")
console.log("当前操作系统编译时的名称为:", os.platform())
// 可能的值:aix、darwin、freebsd、linux、openbsd、sunos、win32
// macOS 输出:当前操作系统编译时的名称为: darwinarch - 获取 CPU 架构
const os = require("os")
console.log("操作系统的 CPU 架构为:", os.arch())
// 可能的值:arm、arm64、ia32、mips、mipsel、ppc、ppc64、s390、s390x、x32、x64
// 输出:操作系统的 CPU 架构为: x64release - 获取系统发行版本
const os = require("os")
console.log("当前操作系统的发行版本为:", os.release())
// macOS 输出:当前操作系统的发行版本为: 24.0.0
// Linux 输出:当前操作系统的发行版本为: 5.15.0-91-genericversion - 获取内核版本
const os = require("os")
console.log("操作系统内核版本:", os.version())
// macOS 输出:操作系统内核版本: Darwin Kernel Version 24.0.0...
// Linux 输出:操作系统内核版本: #1 SMP ...uptime - 获取系统运行时间
const os = require("os")
const uptimeSeconds = os.uptime()
const hours = Math.floor(uptimeSeconds / 3600)
const minutes = Math.floor((uptimeSeconds % 3600) / 60)
const seconds = Math.floor(uptimeSeconds % 60)
console.log(`系统运行时间:${hours}小时 ${minutes}分钟 ${seconds}秒`)
// 输出:系统运行时间:66小时 32分钟 1秒endianness - 获取字节序
const os = require("os")
console.log("CPU 字节序:", os.endianness())
// 输出:CPU 字节序: LE (小端字节序)
// 或:CPU 字节序: BE (大端字节序)loadavg - 获取系统平均负载
返回一个包含 1、5、15 分钟平均负载的数组。平均负载是 UNIX 特定的概念,在 Windows 上,其返回值始终为 [0, 0, 0]。
const os = require("os")
const loadAvg = os.loadavg()
console.log("系统平均负载:")
console.log("1 分钟:", loadAvg[0])
console.log("5 分钟:", loadAvg[1])
console.log("15 分钟:", loadAvg[2])
// 输出示例:
// 系统平均负载:
// 1 分钟: 2.5
// 5 分钟: 2.1
// 15 分钟: 1.8cpus - 获取 CPU 信息
返回一个对象数组,包含所安装的每个 CPU 内核的信息。
const os = require("os")
const cpus = os.cpus()
console.log("CPU 核心数:", cpus.length)
console.log("CPU 详细信息:")
cpus.forEach((cpu, index) => {
console.log(`核心 ${index + 1}:`)
console.log(" 型号:", cpu.model)
console.log(" 速度:", cpu.speed, "MHz")
console.log(" 时间统计:", cpu.times)
})
// 输出示例:
// CPU 核心数: 12
// CPU 详细信息:
// 核心 1:
// 型号: Intel(R) Core(TM) i7-9750H CPU @ 2.60GHz
// 速度: 2600 MHz
// 时间统计: { user: 28016960, nice: 0, sys: 19867260, idle: 122183510, irq: 0 }CPU 时间统计说明:
user: 用户模式下的 CPU 时间(毫秒)nice: 低优先级用户模式下的 CPU 时间(毫秒)sys: 系统模式下的 CPU 时间(毫秒)idle: 空闲时间(毫秒)irq: 中断请求时间(毫秒)
计算 CPU 使用率示例:
const os = require("os")
function getCPUUsage() {
const cpus = os.cpus()
let totalIdle = 0
let totalTick = 0
cpus.forEach((cpu) => {
for (const type in cpu.times) {
totalTick += cpu.times[type]
}
totalIdle += cpu.times.idle
})
const idle = totalIdle / cpus.length
const total = totalTick / cpus.length
const usage = 100 - ~~((100 * idle) / total)
return usage
}
console.log("CPU 使用率:", getCPUUsage(), "%")getPriority 和 setPriority - 进程优先级
getPriority(pid) - 获取进程优先级
const os = require("os")
const process = require("process")
// 获取当前进程的优先级
const currentPid = process.pid
const priority = os.getPriority(currentPid)
console.log("当前进程优先级:", priority)
// 输出:当前进程优先级: 0setPriority(pid, priority) - 设置进程优先级
const os = require("os")
const process = require("process")
// 设置当前进程的优先级
try {
// 使用常量设置优先级
os.setPriority(process.pid, os.constants.priority.PRIORITY_HIGH)
console.log("进程优先级已设置为 HIGH")
// 或直接使用数值
// os.setPriority(process.pid, -14) // 等同于 PRIORITY_HIGH
} catch (err) {
console.error("设置优先级失败:", err.message)
}获取用户信息
userInfo - 获取当前用户信息
返回关于当前有效用户的信息对象。
语法:
os.userInfo([options])参数:
options(可选):对象,可包含encoding属性设置返回字符串的编码
返回值: 返回一个对象,包含用户信息
返回对象属性说明:
| 属性 | 类型 | 说明 |
|---|---|---|
uid | Number | 用户的数字标识符(UNIX 特有,Windows 返回 -1) |
gid | Number | 用户组的数字标识符(UNIX 特有,Windows 返回 -1) |
username | String | 用户名 |
homedir | String | 用户主目录 |
shell | String | 用户默认 shell(Windows 返回 null) |
示例:
const os = require("os")
const userInfo = os.userInfo()
console.log("用户名:", userInfo.username)
console.log("用户主目录:", userInfo.homedir)
console.log("用户 ID:", userInfo.uid)
console.log("用户组 ID:", userInfo.gid)
console.log("默认 Shell:", userInfo.shell)
// macOS/Linux 输出示例:
// 用户名: zhangzhengyang
// 用户主目录: /Users/zhangzhengyang
// 用户 ID: 501
// 用户组 ID: 20
// 默认 Shell: /bin/zsh
// Windows 输出示例:
// 用户名: username
// 用户主目录: C:\Users\username
// 用户 ID: -1
// 用户组 ID: -1
// 默认 Shell: nullavailableParallelism - 获取可用并行度(v19.4.0+)
返回程序应使用的可用并行度(通常为 CPU 核心数)。这是 os.cpus().length 的推荐替代方法,因为它更准确且跨平台兼容性更好。
语法:
os.availableParallelism()返回值: 返回一个整数,表示可用的并行度
示例:
const os = require("os")
// 推荐方式(Node.js v19.4.0+)
const parallelism = os.availableParallelism()
console.log("可用并行度:", parallelism)
// 传统方式(兼容旧版本)
const cpuCount = os.cpus().length
console.log("CPU 核心数:", cpuCount)
// 应用场景:创建 Worker 线程池
const { Worker } = require("worker_threads")
const workerCount = os.availableParallelism?.() || os.cpus().length
console.log(`将创建 ${workerCount} 个 Worker 线程`)注意: 此方法在 Node.js v19.4.0 及以上版本可用,建议使用时检查版本兼容性。
os 模块常用属性
os 模块中除了上面介绍的方法,还提供了三个常用的属性:EOL、devNull 和 constants。
os.EOL - 行末标志
操作系统特定的行末标志。在 POSIX 系统(Linux、macOS)上是 \n,在 Windows 上是 \r\n。
示例:
const os = require("os")
const fs = require("fs")
// 跨平台写入文件时使用 EOL
const content = `第一行${os.EOL}第二行${os.EOL}第三行`
fs.writeFileSync("test.txt", content)
// 在 Windows 上会写入 \r\n,在 Unix 系统上会写入 \nos.devNull - 空设备路径
返回空设备的平台特定路径。
- Windows:
\\.\nul - POSIX(Linux/macOS):
/dev/null
示例:
const os = require("os")
const fs = require("fs")
console.log("空设备路径:", os.devNull)
// macOS/Linux 输出:空设备路径: /dev/null
// Windows 输出:空设备路径: \\.\nul
// 应用场景:丢弃不需要的输出
fs.writeFileSync(os.devNull, "这段内容将被丢弃")os.constants - 系统常量
os.constants 是一个对象,包含各种系统常量,主要用于系统级操作。
os.constants.signals - 信号常量
用于进程间通信的信号常量列表。
const os = require("os")
console.log("信号常量示例:")
console.log("SIGTERM:", os.constants.signals.SIGTERM)
console.log("SIGINT:", os.constants.signals.SIGINT)
console.log("SIGKILL:", os.constants.signals.SIGKILL)os.constants.errno - 错误常量
系统错误码常量列表,用于处理系统级错误。
const os = require("os")
console.log("错误常量示例:")
console.log("EACCES:", os.constants.errno.EACCES) // 权限被拒绝
console.log("EEXIST:", os.constants.errno.EEXIST) // 文件已存在
console.log("ENOENT:", os.constants.errno.ENOENT) // 文件不存在os.constants.dlopen - dlopen 常量
动态库加载相关的常量。
const os = require("os")
console.log("dlopen 常量:", os.constants.dlopen)os.constants.priority - 优先级常量
进程优先级常量列表,用于 setPriority() 方法。
const os = require("os")
console.log("优先级常量:", os.constants.priority)
// 输出:
// {
// PRIORITY_LOW: 19,
// PRIORITY_BELOW_NORMAL: 10,
// PRIORITY_NORMAL: 0,
// PRIORITY_ABOVE_NORMAL: -7,
// PRIORITY_HIGH: -14,
// PRIORITY_HIGHEST: -20
// }优先级说明:
PRIORITY_LOW(19): 最低优先级PRIORITY_BELOW_NORMAL(10): 低于正常优先级PRIORITY_NORMAL(0): 正常优先级(默认)PRIORITY_ABOVE_NORMAL(-7): 高于正常优先级PRIORITY_HIGH(-14): 高优先级PRIORITY_HIGHEST(-20): 最高优先级
使用优先级常量设置进程优先级:
const os = require("os")
const process = require("process")
// 使用常量设置优先级(推荐)
os.setPriority(process.pid, os.constants.priority.PRIORITY_HIGH)
// 或直接使用数值
os.setPriority(process.pid, -14) // 等同于 PRIORITY_HIGH综合应用示例
系统信息监控脚本
const os = require("os")
function formatBytes(bytes) {
return (bytes / 1024 / 1024 / 1024).toFixed(2) + " GB"
}
function formatUptime(seconds) {
const hours = Math.floor(seconds / 3600)
const minutes = Math.floor((seconds % 3600) / 60)
return `${hours}小时 ${minutes}分钟`
}
console.log("========== 系统信息 ==========")
console.log("主机名:", os.hostname())
console.log("操作系统:", os.type())
console.log("平台:", os.platform())
console.log("架构:", os.arch())
console.log("发行版本:", os.release())
console.log("内核版本:", os.version())
console.log("系统运行时间:", formatUptime(os.uptime()))
console.log("")
console.log("========== 内存信息 ==========")
console.log("总内存:", formatBytes(os.totalmem()))
console.log("剩余内存:", formatBytes(os.freemem()))
console.log("已使用内存:", formatBytes(os.totalmem() - os.freemem()))
const memUsage = (((os.totalmem() - os.freemem()) / os.totalmem()) * 100).toFixed(2)
console.log("内存使用率:", memUsage, "%")
console.log("")
console.log("========== CPU 信息 ==========")
const cpus = os.cpus()
console.log("CPU 核心数:", cpus.length)
console.log("CPU 型号:", cpus[0].model)
console.log("")
console.log("========== 网络信息 ==========")
const interfaces = os.networkInterfaces()
for (const name of Object.keys(interfaces)) {
console.log(`${name}:`)
interfaces[name].forEach((iface) => {
if (iface.family === "IPv4" && !iface.internal) {
console.log(` IPv4: ${iface.address}`)
}
})
}
console.log("")
console.log("========== 目录信息 ==========")
console.log("用户主目录:", os.homedir())
console.log("临时文件目录:", os.tmpdir())系统资源监控
const os = require("os")
function monitorSystem() {
setInterval(() => {
const totalMem = os.totalmem()
const freeMem = os.freemem()
const usedMem = totalMem - freeMem
const memUsage = ((usedMem / totalMem) * 100).toFixed(2)
console.log(`[${new Date().toLocaleTimeString()}] 内存使用率: ${memUsage}%`)
if (parseFloat(memUsage) > 80) {
console.warn("⚠️ 警告:内存使用率超过 80%!")
}
}, 5000) // 每 5 秒检查一次
}
// monitorSystem() // 取消注释以启用监控常见问题
Q1: freemem 和 totalmem 返回的字节数太大,如何转换为可读格式?
答: 可以编写工具函数进行转换:
const os = require("os")
function formatBytes(bytes, decimals = 2) {
if (bytes === 0) return "0 Bytes"
const k = 1024
const sizes = ["Bytes", "KB", "MB", "GB", "TB"]
const i = Math.floor(Math.log(bytes) / Math.log(k))
return parseFloat((bytes / Math.pow(k, i)).toFixed(decimals)) + " " + sizes[i]
}
console.log("总内存:", formatBytes(os.totalmem()))
console.log("剩余内存:", formatBytes(os.freemem()))
// 输出:总内存: 16.00 GB
// 输出:剩余内存: 4.18 GBQ2: 如何跨平台获取本机 IP 地址?
答: 使用 networkInterfaces() 方法,并过滤出 IPv4 非内部地址:
const os = require("os")
function getLocalIP() {
const interfaces = os.networkInterfaces()
for (const name of Object.keys(interfaces)) {
for (const iface of interfaces[name]) {
// 跳过内部地址和 IPv6
if (iface.family === "IPv4" && !iface.internal) {
return iface.address
}
}
}
return "127.0.0.1"
}
console.log("本机 IP:", getLocalIP())Q3: loadavg 在 Windows 上返回什么?
答: Windows 不支持平均负载概念,os.loadavg() 始终返回 [0, 0, 0]。建议在 Windows 上使用其他方式监控系统负载,如 WMI(Windows Management Instrumentation)。
Q4: 如何判断当前是哪个操作系统?
答: 使用 os.platform() 或 os.type() 方法:
const os = require("os")
// 方法一:platform()
const platform = os.platform()
if (platform === "win32") {
console.log("Windows 系统")
} else if (platform === "darwin") {
console.log("macOS 系统")
} else if (platform === "linux") {
console.log("Linux 系统")
}
// 方法二:type()
const type = os.type()
// Windows 返回 "Windows_NT"
// macOS 返回 "Darwin"
// Linux 返回 "Linux"Q5: 如何实现跨平台的换行符处理?
答: 使用 os.EOL 属性:
const os = require("os")
const fs = require("fs")
// 方式一:拼接字符串
const content = "第一行" + os.EOL + "第二行" + os.EOL + "第三行"
// 方式二:使用数组 join(推荐)
const lines = ["第一行", "第二行", "第三行"]
const text = lines.join(os.EOL)
fs.writeFileSync("output.txt", text)Q6: userInfo 和 homedir 有什么区别?
答: homedir() 仅返回用户主目录路径,而 userInfo() 返回包含更多用户信息的对象:
const os = require("os")
// homedir() - 仅返回目录路径
console.log(os.homedir()) // /Users/username
// userInfo() - 返回完整用户信息
console.log(os.userInfo())
// { uid: 501, gid: 20, username: 'username', homedir: '/Users/username', shell: '/bin/zsh' }注意事项
1. 跨平台兼容性
某些方法在不同平台上的行为可能不同:
| 方法 | Windows 行为 | POSIX 行为 |
|---|---|---|
loadavg() | 返回 [0, 0, 0] | 返回真实的平均负载 |
userInfo().uid/gid | 返回 -1 | 返回真实的用户/组 ID |
userInfo().shell | 返回 null | 返回默认 shell |
cpus() | 速度可能不准确 | 正常工作 |
2. 权限要求
以下操作可能需要特定权限:
setPriority():设置更高优先级可能需要管理员/root 权限getPriority():获取其他用户进程优先级可能需要权限
3. 性能建议
- 频繁调用
cpus()可能影响性能,建议缓存结果 - 实时监控场景建议设置合理的轮询间隔(如 5-10 秒)
- 使用
availableParallelism()替代cpus().length(Node.js v19.4.0+)
4. 版本兼容性
| 方法 | 引入版本 | 说明 |
|---|---|---|
availableParallelism() | v19.4.0 | 获取可用并行度 |
version() | v13.10.0 | 获取内核版本 |
devNull | v16.3.0 | 空设备路径 |
| 其他方法 | v0.1.x | 基础方法,广泛支持 |
建议在使用新方法前检查 Node.js 版本:
const semver = require("semver")
const nodeVersion = process.version
// 条件使用新 API
if (semver.gte(nodeVersion, "19.4.0")) {
const parallelism = os.availableParallelism()
} else {
const parallelism = os.cpus().length
}