构建NodeJS库--前端项目的打包发布

1. 前言

学习如何打包发布前端项目,需要学习以下相关知识:

  • package.json 如何初始化配置,以及学习npm配置项;
    • 模块类型type配置, 这是nodejs的package.json的配置
    • main 入口文件的配置
  • webpack 是一个用于现代 JavaScript 应用程序的 静态模块打包工具,使用说明,推荐阅读;
  • babel-loader JavaScript通常需要做语法转化和polyfills以便可以使用高级语法而不必担心浏览器兼容性问题,Babel的作用便在于此,而babel-loader正好可以与webpack结合使用;
  • eslint 一个好的项目离不开代码格式规范;
  • jest 一款js测试框架,写好测试用例覆盖测试的功能点,确保软件质量,推荐阅读;

2. 概念区别

Node.js是JavaScript的一种运行环境,是对Google V8引擎进行的封装。是一个服务器端的JavaScript的解释器。npm(Node Package Manager)是nodejs的包管理器。

有一些概念容易混淆,注意区分。

2.1 CommonJS vs Es module

关于type的配置值有:

  • module 可以指示 Node.js 通过使用.cjs扩展名命名特定文件,将其解释为CommonJS
  • commonjs 可以通过使用.mjs扩展名命名特定文件,指示 Node.js 将其解释为 ES module

ps:js文件两种类型都能识别。

ES module 更加现代化和灵活,支持动态导入、异步加载、静态作用域等特性,

而 CommonJS 更加简单和适用于早期的 Node.js 环境。

在实际开发中,需要根据具体的项目需求和环境来选择使用哪种模块系统。

看到深入浅出 Commonjs 和 Es Module一文描述的很详细,感兴趣可以详细了解。

2.2 package.json入口mainmodulebrower

总结:其他项目引用时,会根据项目自身的type来选择定义的lib的入口文件,三个配置的主要区别在于优先级。

一般通常认为browser = browser+mjs > module > browser+cjs > main

推荐阅读入口文件配置的区别一文。

2.3 ES5 vs ES6

  • ES5指的是ECMScript的第五个版本,发布于2009年,是目前最广泛使用的JavaScript版本。
  • ES6是ECMScript的第六个版本,也成为ES2015,发布于2015年,引入了许多新的语言特性和语法糖。
  • ES2015是ES6的官方名称,但是由于ES6引入了太多的新特性,因此人们通常使用ES2015来指代ES6。

推荐阅读ES5和ES6的区别以及ES6常用特性

2.4 webpack config中的 output.library.type

官方使用说明中配置可选项很多,这里介绍:

  • commonjs
  • module
  • umd 统一模块定义,这种模块语法,兼容了以上的CommonJS、AMD、ES Module使用方式,也就是Vue脚手lib模式打包的这种模式,设置改值后,注意globalObject配置项可设置值为'this'

推荐阅读CommonJS/AMD/UMD/ES Module介绍和区别

3. 项目实战

源码:https://github.com/SkylerHu/js-enum

3.1 目录结构

在这里插入图片描述

3.2 主要配置文件

3.2.1 .babelrc

{"presets": ["@babel/preset-env"],"plugins": ["@babel/plugin-proposal-class-properties"]
}

3.2.2 .eslintignore

# node_modules
node_modules/# build
build/# dist
dist/
docs/

3.2.3 .estlintrc.json

{"env": {"browser": true,"es6": true,"mocha": true,"jest": true,"node": true},"globals": {"dashjs": true,"WebKitMediaSource": true,"MediaSource": true,"WebKitMediaKeys": true,"MSMediaKeys": true,"MediaKeys": true},"parser": "babel-eslint","rules": {"no-caller": 2,"no-undef": 2,"no-unused-vars": 2,"no-use-before-define": 0,"object-curly-spacing": ["error", "always"],"strict": 0,"semi": 2,"no-loop-func": 0,"no-multi-spaces": "error","keyword-spacing": ["error",{"before": true,"after": true}],"quotes": ["error","single",{"allowTemplateLiterals": true}],"indent": ["error",2,{"SwitchCase": 1}]},"ignorePatterns": ["releases/**/*"],"overrides": [{"files": ["tests/**/*"],"env": {"jest": true}}]
}

3.2.3 jest.config.json

{"verbose": true,"collectCoverage": true,"coverageDirectory": "./.coverage","moduleFileExtensions": ["js","json"],"testMatch": ["**/tests/**/*.js"],"collectCoverageFrom": ["src/**/*.{js,jsx}","!**/node_modules/**"],"testEnvironment": "node"
}

3.2.2 package.json

{"author": "SkylerHu","name": "js-enumerate","version": "1.0.2","private": false,"type": "module","main": "dist/index.js","files": ["dist"],"publishConfig": {"access": "public","registry": "https://registry.npmjs.org/"},"engines": {"node": "^14.21.3"},"scripts": {"lint": "eslint .","lint:fix": "eslint . --fix","build": "webpack --config webpack.config.js","test": "jest"},"dependencies": {},"devDependencies": {"@babel/core": "^7.24.4","@babel/plugin-proposal-class-properties": "^7.18.6","@babel/preset-env": "^7.24.4","@jest/globals": "^29.7.0","babel-eslint": "^10.1.0","babel-loader": "^9.1.3","clean-webpack-plugin": "^4.0.0","eslint": "7.32.0","eslint-loader": "^4.0.2","identity-obj-proxy": "^3.0.0","jest": "^29.7.0","jest-environment-jsdom": "^29.7.0","webpack": "^5.91.0","webpack-cli": "^5.1.4"},"description": "Enum is a javascript enumeration module. It works with Node.js and the browser.","keywords": ["enum","enumerate","javascript","js-enum","js-enumerate","react-enum","vue-enum"],"homepage": "https://github.com/SkylerHu/js-enum","repository": {"type": "git","url": "git@github.com:SkylerHu/js-enum.git"},"bugs": {"url": "https://github.com/SkylerHu/js-enum/issues"},"license": "MIT"
}

3.2.3 webpack.config.js

import path from 'path';
import { CleanWebpackPlugin } from 'clean-webpack-plugin';import { fileURLToPath } from 'node:url';
import { dirname } from 'node:path';const __dirname = dirname(fileURLToPath(import.meta.url));const PATHS = {src: path.join(__dirname, 'src'),build: path.join(__dirname, 'dist'),
};const config = {mode: 'production',// devtool: 'source-map',entry: path.join(PATHS.src, 'index.js'),output: {path: PATHS.build,clean: true,filename: 'index.js',library: {name: 'Enum',type: 'umd', // 采用通用模块定义export: 'default', // 兼容 ES6 的模块系统、CommonJS 和 AMD 模块规范},globalObject: 'this',},resolve: {extensions: ['.js', '.jsx', '.json'],},module: {rules: [{test: /\.(js|jsx)$/,exclude: /node_modules/, //排除node_modules文件夹enforce: 'pre', //提前加载使用use: { //使用eslint-loader解析loader: 'eslint-loader'}},{// 使用 babel-loader 来编译处理 js 和 jsx 文件test: /\.(js|jsx)$/,exclude: /node_modules/,use: {loader: 'babel-loader',},}]},plugins: [new CleanWebpackPlugin(),],optimization: {minimize: true,},
};export default config;

3.3 如何构建发版

  • 安装依赖npm install .
  • 代码格式npm run lint
  • 测试用例npm run test
  • 构建npm run build
  • 发版npm publish ,具体命令可以npm help查看,也可以查看官方文档
    • 需要在nodejs.org上注册账号,可以npm adduser通过命令行操作;
    • publish前需要npm login登录账号;
    • 也可以直接npmrc配置中配置好账号,或者创建auth_token配置

3.4 其他注意的问题

  • 3.4.1 jestwebpack版本对node版本的要求,node版本可以通过nvm控制;
> jest
./node_modules/jest/node_modules/jest-cli/build/run.js:135if (error?.stack) {^
SyntaxError: Unexpected token '.'

升级node版本解决,该项目使用的node 14+

语法标准中,可选链运算符(?.) 要求node版本14+

  • 3.4.2 Babel编译缺少plugin
> jestFAIL  tests/test_enum.js● Test suite failed to runJest encountered an unexpected tokenJest failed to parse a file. This happens e.g. when your code or its dependencies use non-standard JavaScript syntax, or when Jest is not configured to support such syntax....Details:SyntaxError: ./src/index.js: Missing class properties transform.8 |9 | export default class Enum {> 10 |   #items = [];|   ^^^^^^^^^^^^11 |   #config = {};12 |   /**13 |    *

通过安装和配置@babel/plugin-proposal-class-properties解决,参考

  • 3.4.3 webpack配置output.type为umd时,注意配置globalObject: 'this'
file:///.../node_modules/js-enumerate/dist/index.js:1
ReferenceError: self is not definedat file:///Users/skyler/Documents/github/test/node_modules/js-enumerate/dist/index.js:1:190at ModuleJob.run (internal/modules/esm/module_job.js:183:25)at async Loader.import (internal/modules/esm/loader.js:178:24)at async Object.loadESM (internal/process/esm_loader.js:68:5)at async handleMainPromise (internal/modules/run_main.js:59:12)

报错参考typescript-webpack-library-generates-referenceerror-self-is-not-defined解决。

  • 3.4.4 当nodejs.org上仅publish一个版本,操作npm unpublish后,导致无法找寻项目名,24小时内无法再次publish
    • 具体阅读关于取消版本发布的说明;
npm ERR! code E403
npm ERR! 403 403 Forbidden - PUT https://registry.npmjs.org/js-enumerate - js-enumerate cannot be republished until 24 hours have passed.
npm ERR! 403 In most cases, you or one of your dependencies are requesting
npm ERR! 403 a package version that is forbidden by your security policy.npm ERR! A complete log of this run can be found in:
npm ERR!     ./.npm/_logs/2024-04-21T18_27_39_505Z-debug.log

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/643558.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Python程序设计教案

文章目录: 一:软件环境安装 1.软件环境 2.技巧 3.新建工程项目 二:相关 1.规范 2.关键字 3.Ascll码表 三:语法基础 1.各种符号 1.1 注释 1.2 占位置的 1.3 回车换行 2.输入输出 2.1 输入input 2.2 输出print …

每天五分钟计算机视觉:基于YOLO算法精确分类定位图片中的对象

滑动窗口的卷积的问题 滑动窗口的卷积实现效率很高,但是它依然不能够输出最精准的边界框,比如下面所示: 我们可以看到蓝色框不论在什么位置都不能很好的确定车的位置,有一个算法是YOLO 算法它能够帮助我们解决这个问题。 YOLO 算法 比如我们的输入图像是100*100,我们会…

如何理解自然语言处理中的位置编码(Positional Encoding)

在自然语言处理和特别是在使用Transformer模型中,位置编码(Positional Encoding)是一个关键的概念。它们的作用是为模型提供序列中各个元素的位置信息。由于Transformer架构本身并不像循环神经网络(RNN)那样具有处理序列的固有能力,位置编码因此显得尤为重要。 为什么需…

【webrtc】Chrome和Firefox在SDP协商过程中,针对localhost的不同处理

内网下chrome端webrtc协商失败 现象 我有一个webrtc服务器在局域网内,使用chrome浏览器访问时,发现webrtc在做媒体协商时失败。 具体表现是,在交换sdp后,ice的状态是oniceconnectionstatechange: failed 但是换成Firefox浏览器…

助力24五一杯数学建模比赛

完成助力美赛建模!!!!! 完成助力妈妈杯建模!!!! 完成助力华中杯建模!!!! 这边将在开赛后24小时内发布资料和初步思路 需…

ESP-IDF下载与安装完整流程

本文主要看参考官网说明,如下: Windows 平台工具链的标准设置 - ESP32 - — ESP-IDF 编程指南 latest 文档 (espressif.com) 一、概述 ESP-IDF需要安装一些必备工具,才能围绕ESP32构建固件,包括: PythonGit交叉编译…

Swift-28-值和引用类型、内存管理以及objectivc与swift混合调用

本小节的内容稍有点多,这三块内容基本没太大关系,只是笔者想在这一节中把swift的oop收下尾,所以全写在一起了。 值类型和引用类型 和其它语言一样,函数调用时对于参数到底是指针引用还是类似String这样的值传递(不可变…

【MySQL】A01、性能优化-语句分析

1、数据库优化方向 A、SQL及索引优化 根据需求写出良好的SQL,并创建有效的索引,实现某一种需求可以多种写法,这时候我们就要选择一种效率最高的写法。这个时候就要了解sql优化 B、数据库表结构优化 根据数据库的范式,设计表结构&…

【计算机网络】(三)物理层 - 通信基础

文章目录 【计算机网络】(三)物理层 - 通信基础前言3.1 物理层的基本概念3.2 数据通信的基础知识3.2.1 数据、信号、码元3.2.2 信源、信宿、信道3.2.3 编码、调制3.2.3.1 基带调制(编码)3.2.3.2 带通调制(调制&#xf…

系统安全与应用(1)

目录 1、账号安全管理 (1)禁止程序用户登录 (2)锁定禁用长期不使用的用户 (3)删除无用的账号 (4)禁止账号和密码的修改 2、密码安全管理 设置密码有效期 1)针对已…

2024 年选择安全运营中心 (SOC) 工具指南

安全运营中心 (SOC) 是对抗网络威胁的前线。他们使用各种安全控制措施来监控、检测和快速响应任何网络威胁。这些控制措施对于确保信息系统全天候安全至关重要。 大型组织中的现代 SOC 与各种安全供应商合作,处理 75 到 100 种不同的工具。让我们探讨一下您可能遇到…

数据结构基础:链表操作入门

数据结构基础:链表操作入门 数据结构基础:链表操作入门链表的基本概念链表的基本操作输出链表插入节点删除节点查找值 完整的链表操作示例结语 数据结构基础:链表操作入门 在计算机科学中,数据结构是组织和存储数据的方式&#x…