1 小时速通 ,Node.js 入门要了解的知识点有哪些

发布于:2024-05-02 ⋅ 阅读:(20) ⋅ 点赞:(0)

👈👈👈 欢迎点赞收藏关注哟

首先分享之前的所有文章 >>>> 😜😜😜
文章合集 : 🎁
Github : 👉
CASE 备份 : 👉

一. 前言

最近在研究新的东西,难免用到了一些前端的工具 ,所以这篇文章就产生了。

  • 文章定位 : 这是一篇速通文 , 针对的是有其他程序领域的基础,但是没有接触或者接触得不深的伙伴。
  • 文章内容 : 快速一览 Node.js 的种种特性和用法。

Node.js 是什么 ?

  • 我们知道 JavaScript 是前端语言 , 它运行的介质通常在浏览器中 , 也就是客户端
  • 而 Node.js 作用是让 JavaScript 运行在服务端的平台
    • Node.js 不是一门独立的语言 ,也不算一个框架或者库
    • 更像一套运行环境 ,让 JS 脱离浏览器运行 ,并且可以和底层API发生交互

注意 :

  • 自行安装 Node 环境 ,此处就不深入了

二. Node.js 基础

2.1 npm : Node 包管理器

❓ 首先第一个问题 ,Node.JS 的包是什么 ?

node.js 的包和模块属于抽象的关系 ,一个包中通常包含一些特定的功能 ,使用时可以直接引入包从而直接使用这些功能。

  • 模块 : 文件和模块是一一对应的关系, 一个 node.js 文件就是一个模块
    • 通过 require 来引入一个模块 : require('http')
  • : 包是模块更深一层的抽象,将某个独立的功能封装起来 ,进行发布
  • 功能含义引入某个包从而使用其中的模块

❓ 第二个问题 :npm 是怎么管理的

  • npm(Node Package Manager)是 Node.js 默认的包管理工具
  • 用于安装、卸载、更新和管理 Node.js 的第三方包
  • npm 由 JavaScript 编写

就像大多数包管理工具一样 ,npm 同样区分 镜像库,私有库和公共注册表。基于不同的场景,可以将包上传到不同的环境中 。

以下是一些 npm 的常见命令 :

  • 全局包 : 安装在系统范围内的 npm 包 ,可以在任何项目中使用这些包 ,不需要重新安装
  • 项目包 : 只在该项目中使用,安装在项目 node_modules 目录中

// 安装包
- 基于名称安装 : npm install <package-name>
- 安装全局包 : npm install -g <package-name>
- 安装指定版本的包 : npm install <package-name>@<version>

// 卸载包
npm uninstall <package-name>

// 更新包
npm update <package-name>
- 强制重新安装 : npm update --force-reinstall <package-name>


// 查询包 
- 查询指定名称的包 : npm info <package-name>
- 通过关键字查询 : npm search <keyword>
- 查询当前安装的包 : npm ls [<directory>]
- 查询包的版本号 :npm view <package-name> versions


// 运行
- 发布本地包 : npm publish <package-name>
- 运行项目脚本 :npm run <script-name>
- 初始化项目 : npm init

2.2 常规的 Node.js 的结构

project-root/
├── node_modules     # node 项目依赖包
├── src/             # 源代码目录件
├── test/            # 测试目录
├── package.json     # 项目配置文件
├── package-lock.json # 依赖项锁定文件
└── README.md        # 项目说明文件
  • node_modules : 通过 install 或者 add 的方式安装包时 ,会将包及依赖安装到该目录中
  • package.json : 包描述文件,用来描述包的信息(名称,版本,依赖项)
  • package-lock.json : 记录了项目安装时所使用的所有依赖包及其确切版本号
    • 主要为了避免依赖冲突

其中值得关注的是 package.json 的写法

{
  "name": "my-app",  // Node 应用的名称
  "version": "0.1.0",  // 应用的版本
  "author": "作者",
  "keywords": "关键字",
  "private": true,  // 指示 JavaScript 类成员或模块的可见性
  "main": "main.js",  // 主要的入口函数
  "dependencies": {
      // 项目所需的第三方软件包
  },
  "scripts": {
      // 可从命令行运行的脚本
  },
  "eslintConfig": {
      // ESLint 配置规则和环境
  },
  "browserslist": {
      // 用于告知要支持哪些浏览器(及其版本)
  }
}

常见的就是上面的 ,详情可以看官方文档 @

2.3 Node.js 的组成结构

这里也引发了对 Node.js 性能的思考,Node 和大多数语言一样 ,都是由高层向系统调用的过程 :

  • 高级语言 (JavaScript/Java) 👉 C/C++ 系统语言 👉 硬件接口

image.png

  • 最上层的是 Node 标准库 ,主要是辅助 JS 开发 ,通过标准库可以调用下层的 API
  • 下层最主要的当然还是 V8 ,其次就是 IO 引擎
    • V8 引擎 : Google 开发的开源 JavaScript 引擎,用于执行 JavaScript 代码
      • 可以实现即时编译 ,垃圾回收等复杂功能
    • Libux / Libeio / Libev : 3 种不同的异步IO库,其中 Libev 是另外两个的基础库
    • IOCP : Windows 操作系统提供的异步 I/O 机制 ,
  • 除了这些 ,node 另外一大领域就是各种生态组件
    • 比如数据库方面的 Redis ,MySQL
    • 或者用于构建 Web 服务的 Express

三. Node.js 的常见使用

我们基于一个简单的案例来了解 Node 的定位 :

3.1 入门级使用

// 通过 Node.js 程序运行一个脚本
node helloworld.js

// 通过 Node.js 程序运行一段代码
node -e "console.log('Hello World');" 

// 进入命令行执行
> node
> console.log('Hello World');

你就说像不像安装 JDK 或者 Python环境 运行脚本的模式吧。

3.2 进阶 : Web 服务器

// S1 : 初始化一个 Npm 项目
npm init

// -- 本质上是为了生成一个 package.json (前提是已经安装好了Node环境)
{
  "name": "node-demo",
  "version": "1.0.0",
  "description": "This is Hello World",
  "main": "index.js",
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1"
  },
  "author": "",
  "license": "ISC"
}


// S2 : 创建一个 index.js (也就是上面说的 main 主函数)
// - 其实能看到,这些都是特性,需要一个入口来进入整个项目

var http = require('http');
http.createServer(function (req, res) {
    res.writeHead(200, { 'Content-Type': 'text/html' });
    res.write('<head><meta charset="utf-8"/></head>');
    res.write('<h1>这是一个Node 项目</h1>');
    res.write('<div>开启的Node端口为 3000</div>');
    res.end('<p>我仅仅返回了一段 HTML 代码,但是它在前端正常进行展示</p>');
}).listen(3000);
console.log("HTTP server is listening at port 3000.");

image.png

  • 这里并没有需要我们在 package.json 中专门引入什么 ,意味着 Web 服务是其本身自带的特性
  • 返回的直接是 HTML 代码,基于浏览器的特性,这里可以直接展示

至此 ,一个简简单单平平无奇的 Node 项目就搭建好了

3.3 初级选手 : 为 Node 引入依赖

我们为 Node 引入一些复杂的依赖包 ,从而实现更高级的功能 :

  • 这里演示使用的是 chokidar ,这是一个文件系统工具 ,可以监听到系统文件的变动
// S1 : 在项目中进行安装 
npm install chokidar 

从这里可以看到这些信息 :

  • 安装完成后 ,会自动在 package.json 中为我们添加 dependencies
  • 在项目 node_modules 中会添加对应的依赖 (注意,这里能看出全局依赖并没有在这个文件夹下面)
  • 引入的依赖其实也是一个 node 项目的传统结构

image.png

// S2 : 编译相关的代码
const chokidar = require('chokidar');

// 当前目录
chokidar.watch('.').on('all', (event, path) => {
  console.log(event, path);
});

image.png

  • 这里可以看到 ,数据就已经打印出来了,之前的操作历史清清楚楚

3.4 高级使用 :更加多姿多彩的用法

  • 用法太多了,出于整个系列的目的性,这里只展示 electron 的使用
// S1 : 整体没有区别,引入一个 eletron 组件
{
  "name": "my-electron-app",
  "version": "1.0.0",
  "description": "应用描述",
  "main": "main.js",
  "scripts": {
	"start": "electron .",
    "test": "echo \"Error: no test specified\" && exit 1"
  },
  "author": "Ant-Black",
  "license": "ISC",
  "devDependencies": {
    "electron": "^29.1.6"
  }
}


// S2 : 构建 main.js 里面的代码
const { app, BrowserWindow, ipcMain, dialog } = require('electron')
const path = require('path')

app.whenReady().then(() => {
    // 创建一个 BrowserWindow 和 Login 页面绑定
    const win = new BrowserWindow({
        width: 800,
        height: 600,
        webPreferences: {
            preload: path.join(__dirname, 'preload.js'),
            nodeIntegration: true,
            contextIsolation: false
        },
    })

    win.webContents.openDevTools()
    win.loadFile("login.html");
})

其实很简单不是。

四. Node.js 的基础原理

4.1 Node.js 在服务器里面的定位

当 Node.js 作为 Web 服务器的时候 ,它是和浏览器直接交互的。

我们来以 Java 这个典型的后端Web语言为例 :

  • Java : 浏览器 HTTP 服务器(Tomcat) 运行在服务器上面的 Java 应用
  • Node : 浏览器 Node

因为一个典型的 Java 应用是不会直接对外暴露 Web 能力 ,其底层还是通过 Web 服务器进行端口的开放。

Node 就像一个结合体 ,它既包含了 运行环境 ,又在其上直接集成了 Web 服务器 .

4.2 Node.js 的一些特性点

  • 单线程 + 异步 I/O 模型
  • 事件驱动

虽然我前端不熟 ,但是技术方案这一块都是通用的,区别的无非就是实现而已。我来简单解读一下这些特性 :

单线程 + 异步 I/O 模型 这东西说白了就快,它减少了多线程 线程切换 损耗的资源,同时通过 事件队列 避免了线程的阻塞。

这一套使用最有名的应该是 Redis , 高并发轻轻松松。

看到一张总结的很好的图片,这里引用一下 : 图片来源 @ Node.js开发指南

image.png

这里也简单展示下事件的使用:在很多高级组件里面能看到更加复杂的用法

// S1 : 准备了一个 EventEmitter 对象用于处理发送事件
var EventEmitter = require('events').EventEmitter;
var event = new EventEmitter();

// S2 : 做好事件的监听
event.on('hello_event', function() {
   console.log('hello_event occured.');
});

// S3 : 发送一个事件
setTimeout(function() {
  event.emit('hello_event');
}, 1000); 

五. 经典案例 和 Demo

5.1 可以做什么

工具的最终目的还是面向业务和生产 , Node.js 主要可以实现以下场景 :

搭建网站 :

以 React 为例 ,React 在 Node.js 中部署完成后 ,可以通过指定端口进行访问。

其本质上还是在浏览器中访问 HTML 文件,与常规 Nginx 部署最大的区别在于一个是静态文件,一个是在 Node.js 服务器生成 HTML 后进行返回。

搭建 Web 后端应用

这就和常规的后端语言差不多了 ,也就是常规的 增删改查 ,例如访问 Redis ,访问 MongoDB 等等。

以及可以实现一些更复杂的功能,比如构建特定功能的应用 : Web Socket 服务器

搭建桌面端

这也是我学习这一块的主要原因 ,我们可以基于 Electron 构建一个桌面端 。

对比其他的桌面端语言,这种方式固然在性能和体积等访问有诸多不足,但是适用性和美观上还是很强的。

对于一些对性能要求不高的情况下 ,是一个不错的选择。

搭建功能性工具

剩下的一大场景就是对某个功能进行实现的工具, 这些工具不复杂,但是很实用。

例如 : JS 编译器 ,命令行工具 ,单元测试工具

总结

这一篇主要是对 Node 进行一个大概的了解。阅读的时候顺便记录了一下,可能会有遗漏的地方。

以一个后端老鸟的角度来说 ,Node 更像一个结合体 , 它本身像运行环境一样保证了 JS 代码的运行 , 又在其上层封装了一层 Web 的能力。

这和其本身的定位有一定关系,前端最重要的领域还是在网站,我使用它还是看中它门槛相对较低,界面美观。

如果是纯脚本实现复杂功能,我可能会选择 Python ,服务端会考虑使用 Java 。

侧重不同 ,所以确实没必要做的那么纯粹。

参考文档

Node.js开发指南