nodejs的模块引用原理

63 阅读2分钟

持续创作,加速成长!这是我参与「掘金日新计划 · 10 月更文挑战」的第10天,点击查看活动详情

今天学习了ts,一开始书中就讲解了前端模块。其中,ts中的动态查找就模仿了nodejs。所以,本文就来梳理下nodejs的模块解析流程。

前置概念

核心模块和文件模块。核心模块就是nodejs中自带模块,例如:fs、path、file等。文件模块则是用户自定义,或者第三方库的模块。

引用流程

直接上总流程:

require(X) from module at path Y
1. If X is a core module,
   a. return the core module
   b. STOP
2. If X begins with '/'
   a. set Y to be the filesystem root
3. If X begins with './' or '/' or '../'
   a. LOAD_AS_FILE(Y + X)
   b. LOAD_AS_DIRECTORY(Y + X)
   c. THROW "not found"
4. If X begins with '#'
   a. LOAD_PACKAGE_IMPORTS(X, dirname(Y))
5. LOAD_PACKAGE_SELF(X, dirname(Y))
6. LOAD_NODE_MODULES(X, dirname(Y))
7. THROW "not found"

流程解析

例如Y文件中require('X')。

如果X是核心模块,也就是fs等。就会直接从内存中读取,速度是最快的。因为核心模块在编译阶段就被处理成二进制,并且放到了内存。所以引用时,直接命中。

然后若X是'/'的话,就会相对于根目录。若X是'./'、'/'、'../'则相对于当前页面。

若是文件,根据扩展名解析文件内容。解析顺序如下:

  1. .js
  2. .json
  3. .node

若是目录,解析顺序如下:

  1. 查找目录下/package.json文件,并且解析出main字段 。
  2. 如没有,则直接查找index文件。
  3. 若是有,则直接根据main的字段目录查找。

#代表的是项目package.json中的import引入的第三方库。🉑️直接通过查找package.json中的import查找。

最后就是package中配置的文件,和node_modules中的第三方模块。

收获和体验

  • nodejs的模块引用,并不像想象的那么简单。
  • nodejs的模块主要有三种核心模块、相对模块、第三方模块。
  • 相对模块包含了文件和目录两种。
  • 第三方模块查找规则为,由当前文件位置出发,逐级向上查找。

结束语

本文通过对nodejs模块引用机制的探讨,来达到知其然,知其所以然。让大家将平时用到,但不注意的细节掌握。这样在面试和实际工作中都会事半功倍。

们是骄傲还是谦卑,全取决于事业的成就。——忒壬斯