node全局对象


1. node简介

node.js是一个基于Chrome V8引擎的JavaScript运行环境,使用了一个事件驱动、非阻塞式I/O模型, 让JavaScript 运行在服务端的开发平台
Node采用了一个称为“事件循环(event loop)”的架构,使得编写可扩展性高的服务器变得既容易又安全。提高服务器性能的技巧有多种多样。Node选择了一种既能提高性能,又能减低开发复杂度的架构。这是一个非常重要的特性。并发编程通常很复杂且布满地雷。Node绕过了这些,但仍提供很好的性能。

  • 事件驱动
    事件驱动就是当进来一个新的请求的时,请求将会被压入事件列队中,然后通过一个循环来检测队列中的事件状态变化,如果检测到有状态变化的事件,那么就执行该事件对应的处理代码,一般都是回调函数
  • 非阻塞式I/O模型
    Nodejs 采⽤了⾮阻塞型间的形式通知执⾏操作I/O 机制,在做I/O 操作的时候不会造成任何的阻塞,当完成之后,以时时间的形式通知执行操作
    例如在执⾏了访问数据库的代码之后,将⽴即转⽽执⾏其后⾯的代码,把数据库返回结果的处理代码放在回调函数中,从⽽提⾼了程序的执⾏效率
  1. node的优缺点
    优点

    • 处理⾼并发场景性能更佳
    • 适合I/O密集型应⽤,值的是应⽤在运⾏极限时,CPU占⽤率仍然⽐较低,⼤部分时间是在做I/O硬盘内存读写操

    缺点

    • nodejs是单线程
    • 不适合CPU密集型应⽤
    • 只⽀持单核CPU,不能充分利⽤CPU
    • 可靠性低,⼀旦代码某个环节崩溃,整个系统都崩溃
  2. 应用场景
    应⽤场景分类

    • 善于I/O,不善于计算。因为Nodejs是⼀个单线程,如果计算(同步)太多,则会阻塞这个线程
    • ⼤量并发的I/O,应⽤程序内部并不需要进⾏⾮常复杂的处理
    • 与websocket配合,开发⻓连接的实时交互应⽤程序

    具体场景可以表现

    • 第⼀⼤类:⽤⼾表单收集系统、后台管理系统、实时交互系统、考试系统、联⽹软件、⾼并发量的web应⽤程序
    • 第⼆⼤类:基于web、canvas等多⼈联⽹游戏等多⼈联⽹游戏
    • 第三⼤类:基于web的多⼈实时聊天客⼾端、聊天室、图⽂直播
    • 第四⼤类:单⻚⾯浏览器应⽤程序
    • 第五⼤类:操作数据库、为前端和移动端提供基于json 的API

2. 全局对象

1.global

global 最根本的作用是作为全局变量的宿主
当定义一个全局变量时,这个变量同时也会成为全局对象的属性。
注意:

在 Node.js 中你不可能在最外层定义变量,因为所有用户代码都是属于当前模块的, 而模块本身不是最外层上下文。
最好不要使用 var 定义变量以避免引入全局变量,因为全局变量会污染命名空间,提高代码的耦合风险。
在这里插入图片描述

2.__filename

表示当前正在执行的脚本的文件名。它将输出文件所在位置的绝对路径,且和命令行参数所指定的文件名不一定相同。 如果在模块中,返回的值是模块文件的路径。

console.log('_filename', __filename) // 当前文件的绝对路径

在这里插入图片描述

3.__dirname

表示当前执行脚本所在的目录。

console.log('__dirname', __dirname)  // 当前文件的目录的绝对路径

在这里插入图片描述

4.process

process 是一个全局变量,即 global 对象的属性。
用于描述当前Node.js 进程状态的对象,提供了一个与操作系统的简单接口。

  1. cwd()
    返回当前进程的工作目录 绝对路径
    console.log(process.cwd())
    
    在这里插入图片描述
  2. exit()
    强制退出当前node进程
    可传入退出码,0表示成功退出,默认为0
    可以根据退出码进行一些判定。
  3. argv
    argv 属性返回一个数组,由命令行执行脚本时的各个参数组成。它的第一个成员总是node,第二个成员是脚本文件名,其余成员是脚本文件的参数。
    console.log(process.argv);
    
    在这里插入图片描述
  4. platform
    获取当前的操作系统
    console.log(process.platform);
    
    在这里插入图片描述
  5. kill(pid)
    根据进程ID杀死进程
    process.kill(pid);
    
    在这里插入图片描述
  6. env
    获取环境变量对象
    console.log(process.env)
    
    在这里插入图片描述
  • 设置开发环境
    // 一版代码可能运行在不同的机器上,
    // 开发环境(代码需要压缩混淆)
    // 生产环境(不压缩不混淆)
    // 测试环境(多一些输出日志)
    // 环境变量设置node_env
    if (process.env.NODE_ENV == 'develop') {
       console.log('开发环境')
    } else if (process.env.NODE_ENV == 'test') {
       console.log('测试环境')
    } else if (process.env.NODE_ENV == 'production') {
      console.log('生产环境')
    }
    
  • 判断当前环境是浏览器还是nodejs
     try {
       if (global) {
         console.log('当前环境是nodejs');
          global.xxx = '挂载全局数据'
       }
     } catch(e) {
       if (window) {
           console.log('当前环境是浏览器');
          window.xxx = '挂载全局数据'
      }
    }
    

5.module

模块信息,用于记录当前模块的所有信息

在每个模块中,module 的自由变量是一个指向表示当前模块的对象的引用。
为了方便,module.exports 也可以通过全局模块的 exports 对象访问。
module 实际上不是全局的,而是每个模块本地的。

const a = require('./a.js') // 引入a.js文件
console.log(module)

在这里插入图片描述

6.exports

导出对象,默认为{}

exports是一个对于 module.exports 的更简短的引用形式。
exports 变量是在模块的文件级别作用域内有效的,它在模块被执行前被赋予 module.exports 的值。
它有一个快捷方式,以便 module.exports.f = …
可以被更简洁地写成 exports.f = …。
注意,就像任何变量,如果一个新的值被赋值给 exports,它就不再绑定到 module.exports:

  • module.exports

module.exports 对象是由模块系统创建的。
有时这是难以接受的;许多人希望他们的模块成为某个类的实例。
为了实现这个,需要将期望导出的对象赋值给 module.exports。
注意,将期望的对象赋值给 exports 会简单地重新绑定本地 exports 变量,这可能不是期望的。
注意,对 module.exports 的赋值必须立即完成。 不能在任何回调中完成。

module.exports 与 exports 的区别:

module.exports 是导出对象的真正引用。
exports 是 module.exports 的快捷方式。不能直接赋值 exports = …,否则会断开引用。

7.require

导入函数,使用该函数可以实现模块的依赖

  1. require.main

当 Node.js 直接运行一个文件时,require.main 会被设为它的 module。
这意味着可以通过 require.main === module 来判断一个文件是否被直接运行:
对于 foo.js 文件,如果通过 node foo.js 运行则为 true,但如果通过 require(‘./foo’) 运行则为 false。
因为 module 提供了一个 filename 属性(通常等同于 __filename),
所以可以通过检查 require.main.filename 来获取当前应用程序的入口点。

const a = require('./a.js') // 引入a.js文件
console.log(require.main)

在这里插入图片描述
2. require.cache

被引入的模块将被缓存在这个对象中。
从此对象中删除键值对将会导致下一次 require 重新加载被删除的模块。
注意不能删除 native addons(原生插件),因为它们的重载将会导致错误。

const a = require('./a.js') // 引入a.js文件
console.log(require.cache)

在这里插入图片描述
3. require.resolve(request[, options])

使用内部的 require() 机制查询模块的位置, 此操作只返回解析后的文件名,不会加载该模块。
request:需要解析的模块路径。
options.paths:解析模块的起点路径数组。此参数存在时,将使用这些路径而非默认解析路径。

const a = require('./a.js') // 引入a.js文件
console.log(require.resolve('./a'))

在这里插入图片描述
4. require.resolve.paths(request)

返回一个数组,其中包含解析 request 过程中被查询的路径。
request:被查询解析路径的模块的路径。

const a = require('./a.js') // 引入a.js文件
console.log(require.resolve.paths('./a'))

在这里插入图片描述

8.UMD模块

UMD模块是一种通用的模块定义规范,旨在使同一个模块能够在不同的环境中使用,包括浏览器和Node.js等。UMD规范通过兼容AMD(异步模块定义)和CommonJS规范,使得模块可以在不同的环境中运行

  • UMD模块的基本结构
    UMD模块的基本结构通常包含一个自执行函数,该函数接受两个参数:root和factory。root通常指向全局对象(如window),而factory是一个函数,用于定义模块的功能。
    	(function(root, factory) {
    	    if (typeof define === 'function' && define.amd) {
    	        // AMD    异步模块定义,加载前置
    	        define(['jquery', 'underscore'], factory);
    	    } else if (typeof exports === 'object') {
    	        // CommonJS
    	        module.exports = factory(require('jquery'), require('underscore'));
    	    } else {
    	        // 浏览器全局变量  window
    	        root.returnExports = factory(root.jQuery, root._);
    	    }
    	}(this, function($, _) {
    	    // 模块的具体实现
    	    function a() {} // 私有方法
    	    function b() {} // 公共方法,将被返回
    	    function c() {} // 公共方法,将被返回
    	    return { b: b, c: c }; // 返回公共方法
    }));
    
  • UMD模块的兼容性
    UMD规范的主要目的是兼容不同的模块加载器。实现方式:

    AMD‌:如果存在define函数且define.amd为真,则使用AMD规范。
    ‌CommonJS‌:如果存在exports对象,则使用CommonJS规范。
    ‌ 浏览器全局变量‌:如果以上条件都不满足,则将模块作为全局变量导出。

3、核心对象

核心对象通过require的方式引入,名称既是引用路径

1.path

path 模块是 Node.js 的核心模块之一,用于处理和操作文件和目录路径,提供跨平台的路径操作方法。
通过 path 模块,可以拼接、解析、格式化和规范化路径,避免因为操作系统的不同路径格式而导致的错误(如 Windows 使用反斜杠 \,而 Linux 和 macOS 使用正斜杠 /)。

  • 方法与属性
方法描述
path.basename(path[, ext])返回路径中的最后一部分(文件名)。可选参数 ext 用于去除文件扩展名。
path.dirname(path)返回路径中的目录部分。
path.extname(path)返回路径中文件的扩展名。
path.join([…paths])将多个路径拼接为一个路径,自动处理路径分隔符。
path.resolve([…paths])将路径序列解析为绝对路径,从右到左依次处理每个路径片段,直到构建出一个绝对路径为止。
path.normalize(path)规范化路径,删除冗余的 . 和 …,并根据当前操作系统替换路径分隔符。
path.isAbsolute(path)检查路径是否为绝对路径。
path.relative(from, to)返回从 from 路径到 to 路径的相对路径。
path.parse(path)将路径字符串解析为对象,包含 root、dir、base、ext 和 name 属性。
path.format(pathObject)将路径对象格式化为路径字符串,与 path.parse 相反。
path.sep提供当前操作系统的路径分隔符(POSIX 为 ‘/’,Windows 为 ‘’)
path.delimiter提供路径分隔符(环境变量中路径的分隔符),POSIX 为 :,Windows 为 ;。
const path = require('path');

// 获取文件名  返回路径的最后一部分
console.log('文件名:', path.basename('/foo/bar/baz.txt')); // 输出: 'baz.txt'

// 获取目录名   返回路径中的目录部分
console.log('目录名:', path.dirname('/foo/bar/baz.txt')); // 输出: '/foo/bar'

// 获取扩展名
console.log('扩展名:', path.extname('/foo/bar/baz.txt')); // 输出: '.txt'

// 拼接路径
console.log('拼接路径:', path.join('/foo', 'bar', 'baz/asdf', 'quux', '..')); // 输出: '/foo/bar/baz/asdf'

// 解析绝对路径
console.log('绝对路径:', path.resolve('/foo/bar', './baz')); // 输出: '/foo/bar/baz'

// 规范化路径
console.log('规范化路径:', path.normalize('/foo/bar//baz/asdf/quux/..')); // 输出: '/foo/bar/baz/asdf'

// 判断是否为绝对路径
console.log('是否为绝对路径:', path.isAbsolute('/foo/bar')); // 输出: true

// 相对路径
console.log('相对路径:', path.relative('/foo/bar/baz', '/foo/bar/qux')); // 输出: '../qux'

// 解析路径为对象
const parsedPath = path.parse('/home/user/dir/file.txt');
console.log('解析路径为对象:', parsedPath);
// 输出: { root: '/', dir: '/home/user/dir', base: 'file.txt', ext: '.txt', name: 'file' }

// 将对象格式化为路径
const formattedPath = path.format(parsedPath);
console.log('格式化路径:', formattedPath); // 输出: '/home/user/dir/file.txt'

在这里插入图片描述

2.url

URL 模块包含有助于解析 URL 的函数。URL 模块用于将网址分割成可读的部分。Nodejs 中的 Url 模块和查询字符串用于操作 URL 及其组件。

  • URL 类构造函数用于按以下方式创建 url 对象:
    const { URL } = require("url");
    const myurl = new URL(
      "https://github.com:80/waylau/harmonyos-tutorial?tab=readme-ov-file#89hj54kl"
    );
    const {
      href,
      origin,
      protocol,
      username,
      password,
      host,
      hostname,
      port,
      pathname,
      search,
      searchParams,
      hash,
    } = myurl;
    
    console.log("Href value :", href);
    console.log("Origin value :", origin);
    console.log("Protocol value :", protocol);
    console.log("Username value :", username);
    console.log("Password value :", password);
    console.log("Host value :", host);
    console.log("Hostname value :", hostname);
    console.log("Port value :", port);
    console.log("Pathname value :", pathname);
    console.log("Search value :", search);
    console.log("SearchParams value :", searchParams);
    console.log("Hash value :", hash)
    
    在这里插入图片描述
    修改url部分
    const myURL = new URL('http://github.com/page?name=anonymous');
    myURL.hostname = 'www.baidu.com';
    myURL.port = '8080';
    myURL.searchParams.set('name', 'admin');
    console.log(myURL.href);
    
    添加参数
    const myURL = new URL('http://www.github.com/page');
    myURL.searchParams.append('name', 'anonymous');
    console.log(myURL.href);
    
  • url.parse()
    将url字符串,解析成object
    const url = require("url");
    const hrefUrl = "https://github.com:80/waylau/harmonyos-tutorial?tab=readme-ov-file#89hj54kl"
    const obj = url.parse(hrefUrl)
    console.log(obj)
    
    在这里插入图片描述
  • url.format()
    将对象转成url字符串。
    const url = require("url");
    const components = {
      protocol: 'https',
      host: 'github.com',
      pathname: 'waylau/harmonyos-tutorial',
      search: '?tab=readme-ov-file',
      hash: '#89hj54kl'
    };
    let str = url.format(components)
    console.log(str)
    
    在这里插入图片描述

3.fs

文件系统模块(fs 模块)提供了丰富的 API,用于读取、写入、删除文件以及执行其他文件系统操作。
fs 模块既支持同步方法也支持异步方法,可以根据具体需求选择合适的方式来处理文件操作。

Node.js 文件系统(fs 模块)模块中的方法均有异步和同步版本
异步的方法函数最后一个参数为回调函数,回调函数的第一个参数包含了错误信息(error)。
建议使用异步方法,比起同步,异步方法性能更高,速度更快,而且没有阻塞。

  • 读取文件
    使用fs.readFile方法异步读取文件 使用fs.readFileSync方法同步读取文件
    var fs = require("fs");
    
    // 异步读取
    fs.readFile('c.js', function (err, data) {
       if (err) {
           return console.error(err);
       }
       console.log("异步读取: " + data.toString());
    });
    
    // 同步读取
    var data = fs.readFileSync('d.js');
    console.log("同步读取: " + data.toString());
    
    console.log("程序执行完毕。");
    
    在这里插入图片描述
  • 写入文件
    使用fs.writeFile方法异步写入文件,使用fs.writeFileSync方法同步写入文件

    会覆盖文件中的所有内容
    如果文件不存在,fs.writeFile将自动创建该文件;如果文件存在,将覆盖其中的内容。

    var fs = require("fs");
    fs.writeFile('c.js', 'Hello, World!', (err) => {
      if (err) {
          console.error('Error writing file:', err);
          return;
      }
      console.log('File written successfully');
    });
    
    fs.writeFileSync('d.js', 'Hello, World!');
    
    在这里插入图片描述
    在这里插入图片描述
  • 追加数据
    将数据追加到现有文件中
    使用fs.appendFile方法异步追加数据,使用fs.appendFileSync方法同步追加数据
    var fs = require("fs");
    fs.appendFile('c.js', '\nAppending C', (err) => {
      if (err) {
          console.error('Error appending to file:', err);
          return;
      }
    });
    fs.appendFileSync('d.js', '\nAppending D');
    
    在这里插入图片描述
    在这里插入图片描述
  • 删除文件
    使用fs.unlink方法异步删除文件,使用fs.unlinkSync方法同步删除文件
    var fs = require("fs");
    fs.unlink('c.js', (err) => {
      if (err) {
          console.error('Error deleting file:', err);
          return;
      }
      console.log('File deleted successfully');
    });
    fs.unlinkSync('d.js');
    
  • 创建目录
    使用fs.mkdir方法异步删除文件,使用fs.mkdirSync方法同步删除文件
    fs.mkdir('c', (err) => {
      if (err) {
          console.error('Error creating directory:', err);
          return;
      }
      console.log('Directory created successfully');
    });
    fs.mkdirSync('d');
    
  • 读取目录内容
    使用fs.readdir方法异步读取目录内容,使用fs.readdirSync方法同步读取目录内容
    var fs = require("fs");
    fs.readdir('c', (err, files) => {
      if (err) {
          console.error('Error reading directory:', err);
          return;
      }
      console.log('Directory contents:', files);
    });
    const files = fs.readdirSync('c');
    console.log(files)
    
    在这里插入图片描述
  • 检查文件或目录是否存在
    使用fs.access方法异步读取检查文件或目录是否存在,使用fs.accessSync方法同步检查文件或目录是否存在
    var fs = require("fs");
    fs.access('f', fs.constants.F_OK, (err) => {
      if (err) {
          console.log('File does not exist');
      } else {
          console.log('File exists');
      }
    });
    fs.accessSync('d', fs.constants.F_OK);
    

二、循环依赖

当两个或多个模块相互导入时,称为循环依赖。Node.js 能处理简单的循环依赖,但可能导致部分模块导出的对象未完全初始化。

// a.js
const b = require('./b');
console.log('a.js:', b.message);
module.exports = { message: 'Hello from a' };

// b.js
const a = require('./a');
console.log('b.js:', a.message);
module.exports = { message: 'Hello from b' };

// main.js
require('./a');
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

程楠楠&M

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值