菜单

NPM 集成

相关源文件

本文档涵盖了 Deno 的 NPM 包集成系统,该系统允许在 Deno 的运行时中运行 Node.js 包和 CommonJS 模块。这包括 require() 的实现、模块解析算法、CommonJS 分析以及缓存机制,使 Deno 能够无缝地与 NPM 生态系统协同工作。

有关 Node.js API polyfills 和内置模块实现的信息,请参阅 Node.js API Polyfills。有关兼容性测试框架,请参阅 兼容性测试

系统架构

Deno 中的 NPM 集成通过一个多层系统运行,该系统将 JavaScript 的 require() 调用桥接到基于 Rust 的模块解析和加载逻辑。

NPM 集成架构

来源:ext/node/ops/require.rs1-777 cli/node.rs1-221 cli/cache/module_info.rs1-442

模块解析系统

NPM 集成通过一套全面的操作来实现与 Node.js 兼容的模块解析,这些操作处理 require() 算法的各个方面。

核心解析操作

操作目的核心功能
op_require_node_module_paths生成模块搜索路径实现 Node.js 模块路径解析算法
op_require_resolve_lookup_paths确定相对导入的查找路径处理 ./../ 路径解析
op_require_resolve_exports解析 package.json 导出支持现代 package.json exports 字段
op_require_package_imports_resolve处理 package.json imports解析 package.json imports 字段映射
op_require_resolve_deno_dir解析 npm 包文件夹定位 Deno 的 npm 缓存目录中的包

解析流程图

来源:ext/node/ops/require.rs178-219 ext/node/ops/require.rs262-289 ext/node/ops/require.rs312-351 ext/node/ops/require.rs581-648

CommonJS 分析和支持

Deno 的 NPM 集成包含复杂的 CommonJS 分析,用于区分 CommonJS 和 ESM 模块,这对于正确处理 NPM 包至关重要。

CJS 分析架构

来源:cli/node.rs84-167 cli/node.rs51-60 cli/node.rs170-220

分析类型

CliCjsAnalysis 枚举代表了三种可能的分析结果

  • Esm: 模块被确定为 ECMAScript 模块
  • EsmAnalysis(ModuleExportsAndReExports): ESM,包含详细的导入/导出分析
  • Cjs(ModuleExportsAndReExports): CommonJS 模块,包含导出分析

来源:cli/node.rs51-60

缓存机制

NPM 集成包含复杂的缓存机制,以提高重复加载和分析模块时的性能。

缓存架构

来源:cli/cache/module_info.rs48-74 cli/node.rs62-67

缓存键结构

缓存系统使用多个维度来生成缓存键

缓存类型关键组件目的
ModuleInfoCachespecifier + media_type + source_hash缓存已解析的模块信息
NodeAnalysisCachespecifier + source_hash缓存 CJS/ESM 分析结果
ParsedSourceCachespecifier缓存 AST 解析结果

来源:cli/cache/module_info.rs85-106 cli/node.rs91-96

权限集成

NPM 集成通过在文件系统操作之前进行仔细的权限检查来遵守 Deno 的权限系统。

权限检查流程

来源:ext/node/ops/require.rs40-51 ext/node/ops/worker_threads.rs18-29

包含权限检查的操作

以下操作包含权限验证

  • op_require_stat - 在 stat 操作前检查读取权限
  • op_require_real_path - 在路径规范化之前验证权限
  • op_require_read_file - 在访问文件内容之前确保读取权限
  • op_require_try_self_parent_path - 检查父目录访问权限
  • op_require_package_imports_resolve - 验证引用文件的权限

来源: ext/node/ops/require.rs358-384 ext/node/ops/require.rs386-403 ext/node/ops/require.rs546-567 ext/node/ops/require.rs690-730

错误处理

NPM 集成通过 RequireErrorRequireErrorKind 类型提供了全面的错误处理,这些类型涵盖了模块解析和加载过程中的各种失败场景。

错误类别

错误类型描述JavaScript 类
UrlParse模块说明符中的 URL 无效继承自 url::ParseError
权限文件访问权限被拒绝继承自权限系统
PackageExportsResolvePackage.json exports 解析失败一般错误
PackageJsonLoad加载 package.json 失败一般错误
FilePathConversionURL 转换为文件路径失败一般错误
ReadModule文件读取操作失败继承的错误

来源: ext/node/ops/require.rs53-120