Nodejs知识点【持续更新...】

变量声明

  • var 存在变量提升特性。使用 var 声明的变量,无论是在代码的什么地方声明,都会被提升到当前作用域的最顶部
    在函数内部声明的变量,会被提升到函数顶部;全局声明的变量,会被提升到全局作用域顶部
  • let 关键字在ES6引入,块级作用域,仅在声明的块内(if、for等)有效,避免了变量提升和全局变量问题
  • const 关键字在ES6引入,块级作用域,声明常量,声明时必须初始化

闭包

闭包是指在一个函数内部创建另一个函数,并且内部函数可以访问外部函数的变量、参数以及其他内部函数,即使外部函数已经执行完毕
这种机制使得内部函数保留了对外部作用域的引用,即使外部作用域已经不再活跃

闭包用途:

  1. 封装,内部函数可以访问外部变量,外部函数不能访问内部变量
  2. 状态持续,闭包可以在函数调用之间保持状态(如计数器)
    function counter() {
      var count = 1;
      return function() {
        return count++;
      }
    }
    var testCounter = counter();
    console.log(testCounter ()); // 1
    console.log(testCounter ()); // 2
    console.log(testCounter ()); // 3
    
  3. 偏函数应用

注意:

  • 被闭包函数访问父级及以上的局部变量,会一直存在与内存中,不会被JavaScript垃圾回收机制回收。因此可能造成**内存泄漏**,导致网页性能问题
    • 解决方法:使用完变量后,手动对变量赋值 null
  • 可能造成内存泄漏:意外的全局变量、闭包、循环引用

参考:https://zhuanlan.zhihu.com/p/651784228

原型链

每个对象都隐含属性 __proto__,每个函数都包含属性 prototype
所有构造函数的原型链上层都是 Function 的原型
属性有如下关系

function a() {};
var c = new a();

c.__proto__ === a.prototype // true
a.prototype.__proto__ === Object.prototype // true
Function.prototype.__proto__ === a.prototype.__proto__ // true

手写Promise

class MyPromise {
  static PENDING = 'pending';
  static REJECTED = 'rejected';
  static FULFILLED = 'fulfilled';

  status;
  value;
  reason;

  constructor(executor) {
    this.status = MyPromise.PENDING;
    this.value = undefined;
    this.reason = undefined;

    const resolve = (value) => {
      if (this.status === MyPromise.PENDING) {
        this.status = MyPromise.FULFILLED;
        this.value = value;
      }
    };

    const reject = (reason) => {
      if (this.status === MyPromise.PENDING) {
        this.status = MyPromise.REJECTED;
        this.reason = reason;
      }
    };

    try {
      executor(resolve, reject);
    } catch (err) {
      reject(err);
    }
  }

  then(onFulfilled, onRejected) {
    if (this.status === MyPromise.FULFILLED) {
      onFulfilled(this.value);
    }
    if (this.status === MyPromise.REJECTED) {
      onRejected(this.reason);
    }
  }
}

module.exports = MyPromise;

什么是原型、原型链?

原型:每个函数都有 prototype,称为原型/原型对象,原型上可以挂在一些属性/方法,每个实例都可以使用。原型可以用作继承
原型链:每个对象都有 __proto__,这个属性指向它的原型对象,原型对象同时也是一个对象,拥有 __proto__属性,指向其原型对象,直到指向最顶层的 null,这种链式结构即为原型链

const a = new String('lan')

a.__proto__ === String.prototype
// true
a.__proto__.__proto__ === Object.prototype
// true
a.__proto__.__proto__.__proto__ === null
// true

事件循环

事件循环是指Nodejs执行非阻塞I/O操作,尽管JavaScript是单线程的,由于大多数内核都是多线程,Nodejs会尽可能将操作装载到系统内核,因此它可以在后台执行多个操作。当某一操作完成时,内核会告诉Nodejs,以便Nodejs可以将相应的回调添加到轮询队列中,最终执行

Nodejs中异步API分类:

  1. 定时器(setTimeoutsetInterval
  2. I/O操作(文件读写、数据库操作、网络请求)
  3. node独有(process.nextTicksetImmediate

同步方法执行完毕后,开始事件循环,事件循环自上而下循环执行,三个队列均为空时,事件循环会在Poll队列等待,等待新的事件出现后(异步执行完毕),恢复事件循环

其中:

  1. setImmediate比较特殊,它会直接进入Check队列
  2. setTimeout方法在浏览器环境的最小时间取值为4ms,Nodejs中为1ms
    事件循环

process.nextTick

process.nextTick具有异步特性,但不属于事件循环
在Nodejs的异步模块中,有一个特殊的nextTick队列,这个队列的优先级比事件循环要高
Timer -> Poll -> Check的一个循环成为一个Tickprocess.nextTick的作用就是将函数插入到每个Tick的头部

在这里插入图片描述

微任务队列

微任务队列主要用于处理Promise的回调函数,微任务队列在nextTick队列后,在事件循环之前

在这里插入图片描述

参考:https://www.bilibili.com/video/BV13A4y1Q7N5/?spm_id_from=333.788&vd_source=51b68c717347dd87b9675be5a4dfdf53

模块化

模块化优势:

  1. 避免污染命名空间污染
  2. 更好的分离, 按需加载
  3. 高复用性、高可维护性

引入过多<script>导致的问题

  1. 请求过多
  2. 过多依赖会导致我们不清楚模块之间的依赖关系,导致先后加载顺序出错
  3. 难以维护

存在以上原因,出现不同的模块化规范来约束(CommonJS、ES6、AMD、CMD)

参考:https://www.imooc.com/article/details/id/267469

CommonJS 规范

每个模块都有自己的作用域,每个模块的内部数据是私有的,通过暴露一些方法与其他模块进行通信

  1. 每个文件都是一个独立的模块,每个模块都有一个module对象用来做记录模块的信息
  2. 通过 module.exportsexports可以到处模块
    module.exportsexports 不能混用,否则 module.exports 会覆盖 exports
  3. 通过 require() 函数可以导入模块【如果有多个模块同时 require 同一个模块,获取到的对象是同一个,Node的缓存机制】

ES Module 规范

  1. 使用 export 导出模块
  2. 使用 import 导入模块
  3. 配置 package.jsontype 字段,启用 ES Module

CommonJS 与 ES Module

  1. CommonJS运行时加载,ES Module编译时加载,后者加载的时机更早
    加载时机
  2. 在 ES Module 中,没有 __filename__dirname
  3. 在 CommonJS中,this指向当前模块,在ES Module中,this指向 undefined
  4. 在 ES Module中,import 引入模块需要传递完整的扩展名,在 CommonJS中,require 可以省略
  5. ES Module默认运行在严格模式下

Cookies防范XSS攻击

XSS:跨站脚本攻击,攻击者在HTML页面中加入恶意JavaScript脚本,用户浏览页面时,嵌入的脚本代码便会执行

  1. 反射型XSS攻击
    攻击者针对站点定制攻击链接,发送给被攻击者点击
    http://www.xxx.com/search?query=<script>alert('XSS')</script>
    • 防范:
      a. 入参强校验、过滤
      b. 输出内容转义,避免特殊字符被浏览器解释为HTML标签
      c. 使用HTTP Only cookie
      d. 使用安全控件,验证码等
  2. 存储型XSS攻击
    攻击者将恶意脚本插入到输入表单中,在用户提交表单时存储到数据库中
    • 防范:
      a. 入参强校验、过滤
      b. 输出内容转移,避免恶意脚本被执行
      c. 白名单限制
      d. 使用HTTPS
  3. DOM型XSS攻击

参考:https://zhuanlan.zhihu.com/p/661920779

  • 23
    点赞
  • 22
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值