node - 内置模块 - path

63 阅读3分钟

path 模块是 Node.js 中处理文件路径的强大工具,能够简化路径操作并确保跨平台兼容性

POSIX

POSIX(Portable Operating System Interface,可移植操作系统接口)是一组标准,定义了操作系统如何提供服务(如文件操作、进程管理等),以实现跨平台兼容性。

早期操作系统分为 unix 「 符合posix 」和 macos 以及 windows 「 macos和windows不符合posix标准 」

这就导致了操作系统存在差异,例如不同系统上换行符不一致

  • unix系列系统 => \n
  • windows => \r\n
  • macos => \r

自2001年起,新版macos已经完全兼容POSXI,所以近代操作系统变成了

  • macos 和 unix系列系统 => \n
  • windows => \r

Node.js 提供了 os.EOL 来获取当前操作系统的换行符:

import os from 'node:os'

// 1. EOL => end of line => 换行符
// 2. EOL是特殊字符,直接输出会显示换行,必须通过JSON.stringify 序列化后才能看到字符串类型值
console.log(JSON.stringify(os.EOL))

通用的,windows 和 类unix系统「 含macos 」的文件路径换行符也是不一样

  • 类 Unix 系统(包括 macOS 和 Linux) 使用 / 作为路径分隔符。
  • Windows 使用 \

Node.js 提供了 path.sep 来获取当前操作系统的路径分隔符:

// sep => separator => 换行符
console.log(path.sep); // POSIX: '/', Windows: '\'

基本使用

获取文件路径信息

import path from 'node:path';

const filePath = '/home/user/docs/file.txt';

// 获取扩展名
console.log('扩展名:', path.extname(filePath)); // .txt

// 获取文件名
console.log('文件名:', path.basename(filePath)); // file.txt

// 获取文件名(剔除扩展名)
const extName = path.extname(filePath);
console.log('文件名(剔除扩展名):', path.basename(filePath, extName)); // file

// 获取目录名
console.log('目录名:', path.dirname(filePath)); // /home/user/docs

路径操作

// 组合路径
const newPath = path.join('/home', 'user', 'images', 'photo.jpg');
console.log('组合路径:', newPath); // /home/user/images/photo.jpg

// 将相对路径解析为绝对路径
console.log('绝对路径:', path.resolve('doc', 'file.txt'));
// 输出示例(假设当前工作目录为 /Users/klaus/Desktop/node-demo):
// /Users/klaus/Desktop/node-demo/doc/file.txt

// 计算相对路径
const from = '/home/user/docs';
const to = '/home/user/images';
// 从from到to,从docs目录下要访问images需要的相对路径
console.log('相对路径:', path.relative(from, to)); // ../images

// 判断是否是绝对路径
console.log(path.isAbsolute('/home/user/docs')); // true
console.log(path.isAbsolute('docs/file.txt'));   // false

路径对象

const filePath = '/home/user/docs/file.txt';
console.log(path.parse(filePath)); // 将路径字符串解析为标准化路径对象 「 反序列化行为 」
// 输出:
// {
//   root: '/',
//   dir: '/home/user/docs',
//   base: 'file.txt',
//   ext: '.txt',
//   name: 'file'
// }
const pathObject = {
  root: '/',
  dir: '/home/user/docs',
  base: 'file.txt',
  ext: '.txt',
  name: 'file'
};

// 将标准化路径对象转换为路径字符串 「 parse的逆向操作,序列化行为 」
console.log(path.format(pathObject)); // 输出: /home/user/docs/file.txt

__dirname__filename

在 Node.js 中,__dirname__filename 是每个CJS模块中提供的 伪全局变量,类似于 requiremodule.exports。它们的作用如下:

全局变量描述
__dirname当前模块所在目录的绝对路径
__filename当前模块文件的绝对路径

由于 Node.js 中每个文件都是独立的模块,因此 __dirname__filename 在所有模块中都可用。

// 默认会被认为CJS模块
console.log(__dirname) // /Users/klaus/Desktop/node-demo
console.log(__filename) // /Users/klaus/Desktop/node-demo/index.js

__dirname__filename 是 CJS(CommonJS)模块中的变量,在 ESM(ES Modules)中无法直接使用。如果需要在 ESM 中实现类似功能,则需要手动构建。

import { fileURLToPath } from 'node:url';
import path from 'node:path';

// ESM 模块中 每一个模块都是一个url
console.log(import.meta.url) // file:///Users/klaus/Desktop/node-demo/index.js

// 通过内置url模块的 fileURLToPath 方法 将url转换为文件路径
const __filename = fileURLToPath(import.meta.url); // /Users/klaus/Desktop/node-demo/index.js

// 通过内置path模块的 dirname 方法 将文件路径转换为目录路径
const __dirname = path.dirname(__filename); // /Users/klaus/Desktop/node-demo

console.log('__filename:', __filename);
console.log('__dirname:', __dirname);

process

Node.js 提供了全局对象 process,可以获取当前进程的相关信息

// 获取当前工作目录
console.log(process.cwd()) // /Users/klaus/Desktop/node-demo

console.log(process.env) // 环境变量

// node index.js --name=klaus --age=20 => 其中 --name=klaus --age=20 是命令行参数
// 输出内容类似于「 存在两个默认数组值 」:
// [
//   '/Users/klaus/Desktop/node-demo/node', // node 执行文件路径
//   '/Users/klaus/Desktop/node-demo/index.js', // 执行的文件路径
//   '--name=klaus', // 命令行参数
//   '--age=20' // 命令行参数
// ]
console.log(process.argv) // 命令行参数

// 获取平台信息
// darwin 是 macOS 和 iOS 的系统代码 「 基于 Unix 构建 」
console.log(process.platform) // darwin

// 获取node版本
console.log(process.version) //v23.10.0